Skip to content

Commit 2e77c9d

Browse files
committed
Scan extensions
1 parent a6703ec commit 2e77c9d

2 files changed

Lines changed: 63 additions & 7 deletions

File tree

channel.ts

Lines changed: 62 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -10,9 +10,11 @@ import { URITransformer, IRawURITransformer, transformOutgoingURIs } from "vs/ba
1010
import { IServerChannel } from "vs/base/parts/ipc/common/ipc";
1111
import { IDiagnosticInfo } from "vs/platform/diagnostics/common/diagnosticsService";
1212
import { IEnvironmentService } from "vs/platform/environment/common/environment";
13+
import { IExtensionDescription, ExtensionIdentifier } from "vs/platform/extensions/common/extensions";
1314
import { FileDeleteOptions, FileOverwriteOptions, FileType, IStat, IWatchOptions, FileOpenOptions } from "vs/platform/files/common/files";
1415
import { ILogService } from "vs/platform/log/common/log";
1516
import { IRemoteAgentEnvironment } from "vs/platform/remote/common/remoteAgentEnvironment";
17+
import { ExtensionScanner, ExtensionScannerInput } from "vs/workbench/services/extensions/node/extensionPoints";
1618
import { DiskFileSystemProvider } from "vs/workbench/services/files/node/diskFileSystemProvider";
1719

1820
/**
@@ -157,17 +159,20 @@ export class FileProviderChannel implements IServerChannel {
157159
* See: src/vs/workbench/services/remote/common/remoteAgentEnvironmentChannel.ts.
158160
*/
159161
export class ExtensionEnvironmentChannel implements IServerChannel {
160-
public constructor(private readonly environment: IEnvironmentService) {}
162+
public constructor(
163+
private readonly environment: IEnvironmentService,
164+
private readonly log: ILogService,
165+
) {}
161166

162167
public listen(_: unknown, event: string): Event<any> {
163168
throw new Error(`Invalid listen "${event}"`);
164169
}
165170

166-
public async call(context: any, command: string, _args?: any): Promise<any> {
171+
public async call(context: any, command: string, args?: any): Promise<any> {
167172
switch (command) {
168173
case "getEnvironmentData":
169174
return transformOutgoingURIs(
170-
await this.getEnvironmentData(),
175+
await this.getEnvironmentData(args.language),
171176
getUriTransformer(context.remoteAuthority),
172177
);
173178
case "getDiagnosticInfo": return this.getDiagnosticInfo();
@@ -176,22 +181,73 @@ export class ExtensionEnvironmentChannel implements IServerChannel {
176181
throw new Error(`Invalid call "${command}"`);
177182
}
178183

179-
private async getEnvironmentData(): Promise<IRemoteAgentEnvironment> {
184+
private async getEnvironmentData(locale: string): Promise<IRemoteAgentEnvironment> {
180185
return {
181186
pid: process.pid,
182187
appRoot: URI.file(this.environment.appRoot),
183188
appSettingsHome: this.environment.appSettingsHome,
184189
settingsPath: this.environment.machineSettingsHome,
185190
logsPath: URI.file(this.environment.logsPath),
186191
extensionsPath: URI.file(this.environment.extensionsPath),
187-
extensionHostLogsPath: URI.file(path.join(this.environment.logsPath, "extension-host")), // TODO
192+
extensionHostLogsPath: URI.file(path.join(this.environment.logsPath, "extension-host")),
188193
globalStorageHome: URI.file(this.environment.globalStorageHome),
189194
userHome: URI.file(this.environment.userHome),
190-
extensions: [], // TODO
195+
extensions: await this.scanExtensions(locale),
191196
os: OS,
192197
};
193198
}
194199

200+
private async scanExtensions(locale: string): Promise<IExtensionDescription[]> {
201+
const root = getPathFromAmdModule(require, "");
202+
const pkg = require.__$__nodeRequire(path.resolve(root, "../package.json")) as any;
203+
204+
const translations = {}; // TODO: translations
205+
206+
// TODO: there is also this.environment.extensionDevelopmentLocationURI to look into.
207+
const scanBuiltin = async (): Promise<IExtensionDescription[]> => {
208+
const input = new ExtensionScannerInput(
209+
pkg.version, pkg.commit, locale, !!process.env.VSCODE_DEV,
210+
path.resolve(root, "../extensions"),
211+
true,
212+
false,
213+
translations,
214+
);
215+
const extensions = await ExtensionScanner.scanExtensions(input, this.log);
216+
// TODO: there is more to do if process.env.VSCODE_DEV is true.
217+
return extensions;
218+
};
219+
220+
const scanInstalled = async (): Promise<IExtensionDescription[]> => {
221+
const input = new ExtensionScannerInput(
222+
pkg.version, pkg.commit, locale, !!process.env.VSCODE_DEV,
223+
this.environment.extensionsPath, false, true, translations,
224+
);
225+
return ExtensionScanner.scanExtensions(input, this.log);
226+
};
227+
228+
return Promise.all([scanBuiltin(), scanInstalled()]).then((allExtensions) => {
229+
// It's possible to get duplicates.
230+
const uniqueExtensions = new Map<string, IExtensionDescription>();
231+
allExtensions.forEach((extensions) => {
232+
extensions.forEach((extension) => {
233+
const id = ExtensionIdentifier.toKey(extension.identifier);
234+
if (uniqueExtensions.has(id)) {
235+
const oldPath = uniqueExtensions.get(id)!.extensionLocation.fsPath;
236+
const newPath = extension.extensionLocation.fsPath;
237+
this.log.warn(
238+
`Extension ${id} in ${oldPath} has been overridden ${newPath}`,
239+
);
240+
}
241+
uniqueExtensions.set(id, extension);
242+
});
243+
});
244+
245+
const finalExtensions = <IExtensionDescription[]>[];
246+
uniqueExtensions.forEach((e) => finalExtensions.push(e));
247+
return finalExtensions;
248+
});
249+
}
250+
195251
private getDiagnosticInfo(): Promise<IDiagnosticInfo> {
196252
throw new Error("not implemented");
197253
}

server.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -127,7 +127,7 @@ export class Server {
127127
);
128128
this.ipc.registerChannel(
129129
"remoteextensionsenvironment",
130-
new ExtensionEnvironmentChannel(this.environmentService),
130+
new ExtensionEnvironmentChannel(this.environmentService, this.logService),
131131
);
132132
});
133133
}

0 commit comments

Comments
 (0)