Add cli arguments

This commit is contained in:
Asher 2019-07-02 16:55:54 -05:00
parent 6a35ab1dc0
commit 770e0db7b8
No known key found for this signature in database
GPG key ID: D63C1EF81242354A
8 changed files with 164 additions and 52 deletions

View file

@ -13,7 +13,8 @@ import { IEnvironmentService } from "vs/platform/environment/common/environment"
import { IExtensionDescription, ExtensionIdentifier } from "vs/platform/extensions/common/extensions";
import { FileDeleteOptions, FileOverwriteOptions, FileType, IStat, IWatchOptions, FileOpenOptions } from "vs/platform/files/common/files";
import { ILogService } from "vs/platform/log/common/log";
import { IProductService } from "vs/platform/product/common/product";
import pkg from "vs/platform/product/node/package";
import product from "vs/platform/product/node/product";
import { IRemoteAgentEnvironment } from "vs/platform/remote/common/remoteAgentEnvironment";
import { ExtensionScanner, ExtensionScannerInput } from "vs/workbench/services/extensions/node/extensionPoints";
import { DiskFileSystemProvider } from "vs/workbench/services/files/node/diskFileSystemProvider";
@ -200,14 +201,13 @@ export class ExtensionEnvironmentChannel implements IServerChannel {
private async scanExtensions(locale: string): Promise<IExtensionDescription[]> {
const root = getPathFromAmdModule(require, "");
const product = require.__$__nodeRequire(path.resolve(root, "../package.json")) as IProductService;
const translations = {}; // TODO: translations
// TODO: there is also this.environment.extensionDevelopmentLocationURI to look into.
const scanBuiltin = async (): Promise<IExtensionDescription[]> => {
const input = new ExtensionScannerInput(
product.version, product.commit, locale, !!process.env.VSCODE_DEV,
pkg.version, product.commit, locale, !!process.env.VSCODE_DEV,
path.resolve(root, "../extensions"),
true,
false,
@ -220,7 +220,7 @@ export class ExtensionEnvironmentChannel implements IServerChannel {
const scanInstalled = async (): Promise<IExtensionDescription[]> => {
const input = new ExtensionScannerInput(
product.version, product.commit, locale, !!process.env.VSCODE_DEV,
pkg.version, product.commit, locale, !!process.env.VSCODE_DEV,
this.environment.extensionsPath, false, true, translations,
);
return ExtensionScanner.scanExtensions(input, this.log);

65
cli.ts Normal file
View file

@ -0,0 +1,65 @@
import * as os from "os";
import { validatePaths } from "vs/code/node/paths";
import { parseMainProcessArgv } from "vs/platform/environment/node/argvHelper";
import { ParsedArgs } from "vs/platform/environment/common/environment";
import { buildHelpMessage, buildVersionMessage } from "vs/platform/environment/node/argv";
import product from "vs/platform/product/node/product";
import pkg from "vs/platform/product/node/package";
import { MainServer, WebviewServer } from "vs/server/server";
import "vs/server/tar";
interface IMainCli {
main: (argv: ParsedArgs) => Promise<void>;
}
const main = async (): Promise<void> => {
const args = validatePaths(parseMainProcessArgv(process.argv));
if (!product.extensionsGallery) {
product.extensionsGallery = {
serviceUrl: process.env.SERVICE_URL || "https://v1.extapi.coder.com",
itemUrl: process.env.ITEM_URL || "",
controlUrl: "",
recommendationsUrl: "",
};
}
if (args.help) {
const executable = `${product.applicationName}${os.platform() === "win32" ? ".exe" : ""}`;
return console.log(buildHelpMessage(product.nameLong, executable, pkg.version));
}
if (args.version) {
return console.log(buildVersionMessage(pkg.version, product.commit));
}
const shouldSpawnCliProcess = (): boolean => {
return !!args["install-source"]
|| !!args["list-extensions"]
|| !!args["install-extension"]
|| !!args["uninstall-extension"]
|| !!args["locate-extension"]
|| !!args["telemetry"];
};
if (shouldSpawnCliProcess()) {
const cli = await new Promise<IMainCli>((c, e) => require(["vs/code/node/cliProcessMain"], c, e));
await cli.main(args);
// There is some WriteStream instance keeping it open so force an exit.
return process.exit(0);
}
const webviewServer = new WebviewServer();
const server = new MainServer(webviewServer, args);
// The main server inserts webview server address to the root HTML, so we'll
// need to wait for it to listen otherwise the address will be null.
await webviewServer.listen(8444);
await server.listen(8443);
console.log(`Main server serving ${server.address}`);
console.log(`Webview server serving ${webviewServer.address}`);
};
main().catch((error) => {
console.error(error);
process.exit(1);
});

View file

@ -1,12 +0,0 @@
import { MainServer, WebviewServer } from "./server";
const webviewServer = new WebviewServer();
const server = new MainServer(webviewServer);
webviewServer.listen(8444).then(async () => {
await server.listen(8443);
console.log(`Main server serving ${server.address}`);
console.log(`Webview server serving ${webviewServer.address}`);
}).catch((error) => {
console.error(error);
process.exit(1);
});

View file

@ -1 +1 @@
require("../../bootstrap-amd").load("vs/server/entry");
require("../../bootstrap-amd").load("vs/server/cli");

View file

@ -5,6 +5,13 @@
"build": "echo TODO && exit 1"
},
"devDependencies": {
"@types/tar-stream": "^1.6.1",
"nodemon": "^1.19.1"
},
"dependencies": {
"tar-stream": "^2.1.0"
},
"resolutions": {
"@types/node": "^10.12.12"
}
}

View file

@ -5,16 +5,13 @@ import * as path from "path";
import * as util from "util";
import * as url from "url";
import { getPathFromAmdModule } from "vs/base/common/amd";
import { Emitter } from "vs/base/common/event";
import { sanitizeFilePath } from "vs/base/common/extpath";
import { getMediaMime } from "vs/base/common/mime";
import { extname } from "vs/base/common/path";
import { UriComponents, URI } from "vs/base/common/uri";
import { IPCServer, ClientConnectionEvent } from "vs/base/parts/ipc/common/ipc";
import { validatePaths } from "vs/code/node/paths";
import { LogsDataCleaner } from "vs/code/electron-browser/sharedProcess/contrib/logsDataCleaner";
import { parseMainProcessArgv } from "vs/platform/environment/node/argvHelper";
import { IEnvironmentService, ParsedArgs } from "vs/platform/environment/common/environment";
import { EnvironmentService } from "vs/platform/environment/node/environmentService";
import { InstantiationService } from "vs/platform/instantiation/common/instantiationService";
@ -23,6 +20,7 @@ import { getLogLevel, ILogService } from "vs/platform/log/common/log";
import { LogLevelSetterChannel } from "vs/platform/log/common/logIpc";
import { SpdLogService } from "vs/platform/log/node/spdlogService";
import { IProductConfiguration } from "vs/platform/product/common/product";
import product from "vs/platform/product/node/product";
import { ConnectionType, ConnectionTypeRequest } from "vs/platform/remote/common/remoteAgentConnection";
import { REMOTE_FILE_SYSTEM_CHANNEL_NAME } from "vs/platform/remote/common/remoteAgentFileSystemChannel";
import { RemoteExtensionLogFileName } from "vs/workbench/services/remote/common/remoteAgentService";
@ -123,7 +121,7 @@ export class MainServer extends Server {
private readonly services = new ServiceCollection();
public constructor(private readonly webviewServer: WebviewServer) {
public constructor(private readonly webviewServer: WebviewServer, args: ParsedArgs) {
super();
this.server.on("upgrade", async (request, socket) => {
@ -134,10 +132,6 @@ export class MainServer extends Server {
protocol.dispose(error);
}
});
}
public async listen(port: number): Promise<void> {
const args = validatePaths(parseMainProcessArgv(process.argv));
const environmentService = new EnvironmentService(args, process.execPath);
this.services.set(IEnvironmentService, environmentService);
@ -163,8 +157,6 @@ export class MainServer extends Server {
new ExtensionEnvironmentChannel(environmentService, logService),
);
});
await super.listen(port);
}
protected async handleRequest(
@ -203,9 +195,7 @@ export class MainServer extends Server {
REMOTE_USER_DATA_URI: transformer.transformOutgoing(
(this.services.get(IEnvironmentService) as EnvironmentService).webUserDataHome,
),
PRODUCT_CONFIGURATION: require.__$__nodeRequire(
path.resolve(getPathFromAmdModule(require, ""), "../product.json"),
),
PRODUCT_CONFIGURATION: product,
CONNECTION_AUTH_TOKEN: "",
};

44
tar.ts
View file

@ -1,10 +1,5 @@
/*---------------------------------------------------------------------------------------------
* Copyright (c) Microsoft Corporation. All rights reserved.
* Licensed under the MIT License. See License.txt in the project root for license information.
*--------------------------------------------------------------------------------------------*/
import * as nls from "vs/nls";
import * as vszip from "vszip";
import * as vszip from "vs/base/node/zip";
import * as fs from "fs";
import * as path from "path";
import * as tarStream from "tar-stream";
@ -12,6 +7,10 @@ import { promisify } from "util";
import { CancellationToken } from "vs/base/common/cancellation";
import { mkdirp } from "vs/base/node/pfs";
// We will be overriding these, so keep a reference to the original.
const vszipExtract = vszip.extract;
const vszipBuffer = vszip.buffer;
export interface IExtractOptions {
overwrite?: boolean;
@ -29,8 +28,8 @@ export interface IFile {
}
/**
* Override the standard VS Code behavior for zipping
* extensions to use the TAR format instead of ZIP.
* Override the standard VS Code behavior for zipping extensions to use the TAR
* format instead of ZIP.
*/
export const zip = (tarPath: string, files: IFile[]): Promise<string> => {
return new Promise<string>((c, e): void => {
@ -63,10 +62,9 @@ export const zip = (tarPath: string, files: IFile[]): Promise<string> => {
};
/**
* Override the standard VS Code behavior for extracting
* archives, to first attempt to process the archive as a TAR
* and then fallback on the original implementation, for processing
* ZIPs.
* Override the standard VS Code behavior for extracting archives to first
* attempt to process the archive as a TAR and then fall back to the original
* implementation for processing ZIPs.
*/
export const extract = (archivePath: string, extractPath: string, options: IExtractOptions = {}, token: CancellationToken): Promise<void> => {
return new Promise<void>((c, e): void => {
@ -76,15 +74,15 @@ export const extract = (archivePath: string, extractPath: string, options: IExtr
return;
}
vszip.extract(archivePath, extractPath, options, token).then(c).catch(e);
vszipExtract(archivePath, extractPath, options, token).then(c).catch(e);
});
});
};
/**
* Override the standard VS Code behavior for buffering
* archives, to first process the Buffer as a TAR and then
* fallback on the original implementation, for processing ZIPs.
* Override the standard VS Code behavior for buffering archives to first
* process the Buffer as a TAR and then fall back to the original
* implementation for processing ZIPs.
*/
export const buffer = (targetPath: string, filePath: string): Promise<Buffer> => {
return new Promise<Buffer>((c, e): void => {
@ -104,16 +102,16 @@ export const buffer = (targetPath: string, filePath: string): Promise<Buffer> =>
return;
}
vszip.buffer(targetPath, filePath).then(c).catch(e);
vszipBuffer(targetPath, filePath).then(c).catch(e);
});
});
};
/**
* Override the standard VS Code behavior for extracting assets
* from archive Buffers to use the TAR format instead of ZIP.
* Override the standard VS Code behavior for extracting assets from archive
* Buffers to use the TAR format instead of ZIP.
*/
export const extractAssets = (tarPath: string, match: RegExp, callback: (path: string, data: Buffer) => void): Promise<void> => {
const extractAssets = (tarPath: string, match: RegExp, callback: (path: string, data: Buffer) => void): Promise<void> => {
return new Promise<void>(async (c, e): Promise<void> => {
try {
const buffer = await promisify(fs.readFile)(tarPath);
@ -217,3 +215,9 @@ const extractTar = (tarPath: string, targetPath: string, options: IExtractOption
}
});
};
// Override original functionality so we can use tar instead of zip.
const target = vszip as typeof vszip;
target.zip = zip;
target.extract = extract;
target.buffer = buffer;

View file

@ -2,6 +2,18 @@
# yarn lockfile v1
"@types/node@*", "@types/node@^10.12.12":
version "10.14.10"
resolved "https://registry.yarnpkg.com/@types/node/-/node-10.14.10.tgz#e491484c6060af8d461e12ec81c0da8a3282b8de"
integrity sha512-V8wj+w2YMNvGuhgl/MA5fmTxgjmVHVoasfIaxMMZJV6Y8Kk+Ydpi1z2whoShDCJ2BuNVoqH/h1hrygnBxkrw/Q==
"@types/tar-stream@^1.6.1":
version "1.6.1"
resolved "https://registry.yarnpkg.com/@types/tar-stream/-/tar-stream-1.6.1.tgz#67d759068ff781d976cad978893bb7a334ec8809"
integrity sha512-pYCDOPuRE+4tXFk1rSMYiuI+kSrXiJ4av1bboQbkcEBA2rqwEWfIn9kdMSH+5nYu58WksHuxwx+7kVbtg0Le7w==
dependencies:
"@types/node" "*"
abbrev@1:
version "1.1.1"
resolved "https://registry.yarnpkg.com/abbrev/-/abbrev-1.1.1.tgz#f8f2c887ad10bf67f634f005b6987fed3179aac8"
@ -110,6 +122,13 @@ binary-extensions@^1.0.0:
resolved "https://registry.yarnpkg.com/binary-extensions/-/binary-extensions-1.12.0.tgz#c2d780f53d45bba8317a8902d4ceeaf3a6385b14"
integrity sha512-DYWGk01lDcxeS/K9IHPGWfT8PsJmbXRtRd2Sx72Tnb8pcYZQFF1oSDb8hJtS1vhp212q1Rzi5dUf9+nq0o9UIg==
bl@^3.0.0:
version "3.0.0"
resolved "https://registry.yarnpkg.com/bl/-/bl-3.0.0.tgz#3611ec00579fd18561754360b21e9f784500ff88"
integrity sha512-EUAyP5UHU5hxF8BPT0LKW8gjYLhq1DQIcneOX/pL/m2Alo+OYDQAJlHq+yseMP50Os2nHXOSic6Ss3vSQeyf4A==
dependencies:
readable-stream "^3.0.1"
boxen@^1.2.1:
version "1.3.0"
resolved "https://registry.yarnpkg.com/boxen/-/boxen-1.3.0.tgz#55c6c39a8ba58d9c61ad22cd877532deb665a20b"
@ -376,6 +395,13 @@ duplexer3@^0.1.4:
resolved "https://registry.yarnpkg.com/duplexer3/-/duplexer3-0.1.4.tgz#ee01dd1cac0ed3cbc7fdbea37dc0a8f1ce002ce2"
integrity sha1-7gHdHKwO08vH/b6jfcCo8c4ALOI=
end-of-stream@^1.4.1:
version "1.4.1"
resolved "https://registry.yarnpkg.com/end-of-stream/-/end-of-stream-1.4.1.tgz#ed29634d19baba463b6ce6b80a37213eab71ec43"
integrity sha512-1MkrZNvWTKCaigbn+W15elq2BB/L22nqrSY5DKlo3X6+vclJm8Bb5djXJBmEX6fS3+zCh/F4VBK5Z2KxJt4s2Q==
dependencies:
once "^1.4.0"
escape-string-regexp@^1.0.5:
version "1.0.5"
resolved "https://registry.yarnpkg.com/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz#1b61c0562190a8dff6ae3bb2cf0200ca130b86d4"
@ -458,6 +484,11 @@ fragment-cache@^0.2.1:
dependencies:
map-cache "^0.2.2"
fs-constants@^1.0.0:
version "1.0.0"
resolved "https://registry.yarnpkg.com/fs-constants/-/fs-constants-1.0.0.tgz#6be0de9be998ce16af8afc24497b9ee9b7ccd9ad"
integrity sha512-y6OAwoSIf7FyjMIv94u+b5rdheZEjzR63GTyZJm5qh4Bi+2YgwLCcI/fPFZkL5PSixOt6ZNKm+w+Hfp/Bciwow==
fs-minipass@^1.2.5:
version "1.2.5"
resolved "https://registry.yarnpkg.com/fs-minipass/-/fs-minipass-1.2.5.tgz#06c277218454ec288df77ada54a03b8702aacb9d"
@ -1120,7 +1151,7 @@ object.pick@^1.3.0:
dependencies:
isobject "^3.0.1"
once@^1.3.0:
once@^1.3.0, once@^1.4.0:
version "1.4.0"
resolved "https://registry.yarnpkg.com/once/-/once-1.4.0.tgz#583b1aa775961d4b113ac17d9c50baef9dd76bd1"
integrity sha1-WDsap3WWHUsROsF9nFC6753Xa9E=
@ -1238,6 +1269,15 @@ readable-stream@^2.0.2, readable-stream@^2.0.6:
string_decoder "~1.1.1"
util-deprecate "~1.0.1"
readable-stream@^3.0.1, readable-stream@^3.1.1:
version "3.4.0"
resolved "https://registry.yarnpkg.com/readable-stream/-/readable-stream-3.4.0.tgz#a51c26754658e0a3c21dbf59163bd45ba6f447fc"
integrity sha512-jItXPLmrSR8jmTRmRWJXCnGJsfy85mB3Wd/uINMXA65yrnFo0cPClFIUWzo2najVNSl+mx7/4W8ttlLWJe99pQ==
dependencies:
inherits "^2.0.3"
string_decoder "^1.1.1"
util-deprecate "^1.0.1"
readdirp@^2.2.1:
version "2.2.1"
resolved "https://registry.yarnpkg.com/readdirp/-/readdirp-2.2.1.tgz#0e87622a3325aa33e892285caf8b4e846529a525"
@ -1466,6 +1506,13 @@ string-width@^1.0.1:
is-fullwidth-code-point "^2.0.0"
strip-ansi "^4.0.0"
string_decoder@^1.1.1:
version "1.2.0"
resolved "https://registry.yarnpkg.com/string_decoder/-/string_decoder-1.2.0.tgz#fe86e738b19544afe70469243b2a1ee9240eae8d"
integrity sha512-6YqyX6ZWEYguAxgZzHGL7SsCeGx3V2TtOTqZz1xSTSWnqsbWwbptafNyvf/ACquZUXV3DANr5BDIwNYe1mN42w==
dependencies:
safe-buffer "~5.1.0"
string_decoder@~1.1.1:
version "1.1.1"
resolved "https://registry.yarnpkg.com/string_decoder/-/string_decoder-1.1.1.tgz#9cf1611ba62685d7030ae9e4ba34149c3af03fc8"
@ -1504,6 +1551,17 @@ supports-color@^5.2.0, supports-color@^5.3.0:
dependencies:
has-flag "^3.0.0"
tar-stream@^2.1.0:
version "2.1.0"
resolved "https://registry.yarnpkg.com/tar-stream/-/tar-stream-2.1.0.tgz#d1aaa3661f05b38b5acc9b7020efdca5179a2cc3"
integrity sha512-+DAn4Nb4+gz6WZigRzKEZl1QuJVOLtAwwF+WUxy1fJ6X63CaGaUAxJRD2KEn1OMfcbCjySTYpNC6WmfQoIEOdw==
dependencies:
bl "^3.0.0"
end-of-stream "^1.4.1"
fs-constants "^1.0.0"
inherits "^2.0.3"
readable-stream "^3.1.1"
tar@^4:
version "4.4.8"
resolved "https://registry.yarnpkg.com/tar/-/tar-4.4.8.tgz#b19eec3fde2a96e64666df9fdb40c5ca1bc3747d"
@ -1636,7 +1694,7 @@ use@^3.1.0:
resolved "https://registry.yarnpkg.com/use/-/use-3.1.1.tgz#d50c8cac79a19fbc20f2911f56eb973f4e10070f"
integrity sha512-cwESVXlO3url9YWlFW/TA9cshCEhtu7IKJ/p5soJ/gGpj7vbvFrAY/eIioQ6Dw23KjZhYgiIo8HOs1nQ2vr/oQ==
util-deprecate@~1.0.1:
util-deprecate@^1.0.1, util-deprecate@~1.0.1:
version "1.0.2"
resolved "https://registry.yarnpkg.com/util-deprecate/-/util-deprecate-1.0.2.tgz#450d4dc9fa70de732762fbd2d4a28981419a0ccf"
integrity sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=