{verified === true ? (
diff --git a/packages/vsx-registry/src/browser/vsx-extensions-contribution.ts b/packages/vsx-registry/src/browser/vsx-extensions-contribution.ts
index f7ebc5f95a616..08782d516a2d5 100644
--- a/packages/vsx-registry/src/browser/vsx-extensions-contribution.ts
+++ b/packages/vsx-registry/src/browser/vsx-extensions-contribution.ts
@@ -114,6 +114,18 @@ export class VSXExtensionsContribution extends AbstractViewContribution
this.installAnotherVersion(extension),
});
+ commands.registerCommand(VSXExtensionsCommands.DISABLE, {
+ isVisible: (extension: VSXExtension) => extension.installed && !extension.disabled,
+ isEnabled: (extension: VSXExtension) => extension.installed && !extension.disabled,
+ execute: async (extension: VSXExtension) => extension.disable(),
+ });
+
+ commands.registerCommand(VSXExtensionsCommands.ENABLE, {
+ isVisible: (extension: VSXExtension) => extension.installed && extension.disabled,
+ isEnabled: (extension: VSXExtension) => extension.installed && extension.disabled,
+ execute: async (extension: VSXExtension) => extension.enable(),
+ });
+
commands.registerCommand(VSXExtensionsCommands.COPY, {
execute: (extension: VSXExtension) => this.copy(extension)
});
@@ -152,6 +164,15 @@ export class VSXExtensionsContribution extends AbstractViewContribution;
/**
* Single source for all extensions
*/
protected readonly extensions = new Map();
protected readonly onDidChangeEmitter = new Emitter();
- protected _installed = new Set();
+ protected disabled = new Set();
+ protected uninstalled = new Set();
+ protected deployed = new Set();
+ protected _installed = new Set();
protected _recommended = new Set();
protected _searchResult = new Set();
+ protected builtins = new Set();
protected _searchError?: string;
protected searchCancellationTokenSource = new CancellationTokenSource();
@@ -61,6 +66,12 @@ export class VSXExtensionsModel {
@inject(HostedPluginSupport)
protected readonly pluginSupport: HostedPluginSupport;
+ @inject(HostedPluginWatcher)
+ protected pluginWatcher: HostedPluginWatcher;
+
+ @inject(HostedPluginServer)
+ protected readonly pluginServer: HostedPluginServer;
+
@inject(VSXExtensionFactory)
protected readonly extensionFactory: VSXExtensionFactory;
@@ -128,8 +139,24 @@ export class VSXExtensionsModel {
this.updateSearchResult();
}
+ isBuiltIn(id: string): boolean {
+ return this.builtins.has(id as PluginIdentifiers.UnversionedId);
+ }
+
isInstalled(id: string): boolean {
- return this._installed.has(id);
+ return this._installed.has(id as PluginIdentifiers.UnversionedId);
+ }
+
+ isUninstalled(id: string): boolean {
+ return this.uninstalled.has(id as PluginIdentifiers.UnversionedId);
+ }
+
+ isDeployed(id: string): boolean {
+ return this.deployed.has(id as PluginIdentifiers.UnversionedId);
+ }
+
+ isDisabled(id: string): boolean {
+ return this.disabled.has(id as PluginIdentifiers.UnversionedId);
}
getExtension(id: string): VSXExtension | undefined {
@@ -187,12 +214,15 @@ export class VSXExtensionsModel {
protected async initInstalled(): Promise {
await this.pluginSupport.willStart;
- this.pluginSupport.onDidChangePlugins(() => this.updateInstalled());
try {
await this.updateInstalled();
} catch (e) {
console.error(e);
}
+
+ this.pluginWatcher.onDidDeploy(() => {
+ this.updateInstalled();
+ });
}
protected async initSearchResult(): Promise {
@@ -223,10 +253,10 @@ export class VSXExtensionsModel {
return this.searchCancellationTokenSource = new CancellationTokenSource();
}
- protected setExtension(id: string): VSXExtension {
+ protected setExtension(id: string, version?: string): VSXExtension {
let extension = this.extensions.get(id);
if (!extension) {
- extension = this.extensionFactory({ id });
+ extension = this.extensionFactory({ id, version, model: this });
this.extensions.set(id, extension);
}
return extension;
@@ -328,19 +358,41 @@ export class VSXExtensionsModel {
}
protected async updateInstalled(): Promise {
+ const [deployed, uninstalled, disabled] = await Promise.all(
+ [this.pluginServer.getDeployedPluginIds(), this.pluginServer.getUninstalledPluginIds(), this.pluginServer.getDisabledPluginIds()]);
+
+ this.uninstalled = new Set();
+ uninstalled.forEach(id => this.uninstalled.add(PluginIdentifiers.unversionedFromVersioned(id)));
+ this.disabled = new Set();
+ disabled.forEach(id => this.disabled.add(PluginIdentifiers.unversionedFromVersioned(id)));
+ this.deployed = new Set();
+ deployed.forEach(id => this.deployed.add(PluginIdentifiers.unversionedFromVersioned(id)));
+
const prevInstalled = this._installed;
+ const installedVersioned = new Set();
return this.doChange(async () => {
- const plugins = this.pluginSupport.plugins;
- const currInstalled = new Set();
+ const currInstalled = new Set();
const refreshing = [];
- for (const plugin of plugins) {
- if (plugin.model.engine.type === 'vscode') {
- const version = plugin.model.version;
- const id = plugin.model.id;
- this._installed.delete(id);
- const extension = this.setExtension(id);
- currInstalled.add(extension.id);
- refreshing.push(this.refresh(id, version));
+ for (const versionedId of deployed) {
+ installedVersioned.add(versionedId);
+ const idAndVersion = PluginIdentifiers.idAndVersionFromVersionedId(versionedId);
+ if (idAndVersion) {
+ this._installed.delete(idAndVersion.id);
+ this.setExtension(idAndVersion.id, idAndVersion.version);
+ currInstalled.add(idAndVersion.id);
+ refreshing.push(this.refresh(idAndVersion.id, idAndVersion.version));
+ }
+ }
+ for (const versionedId of disabled) {
+ const idAndVersion = PluginIdentifiers.idAndVersionFromVersionedId(versionedId);
+ installedVersioned.add(versionedId);
+ if (idAndVersion && !this.isUninstalled(idAndVersion.id)) {
+ if (!currInstalled.has(idAndVersion.id)) {
+ this._installed.delete(idAndVersion.id);
+ this.setExtension(idAndVersion.id, idAndVersion.version);
+ currInstalled.add(idAndVersion.id);
+ refreshing.push(this.refresh(idAndVersion.id, idAndVersion.version));
+ }
}
}
for (const id of this._installed) {
@@ -348,10 +400,33 @@ export class VSXExtensionsModel {
if (!extension) { continue; }
refreshing.push(this.refresh(id, extension.version));
}
+ await Promise.all(refreshing);
const installed = new Set([...prevInstalled, ...currInstalled]);
const installedSorted = Array.from(installed).sort((a, b) => this.compareExtensions(a, b));
this._installed = new Set(installedSorted.values());
- await Promise.all(refreshing);
+
+ const missingIds = new Set();
+ for (const id of installedVersioned) {
+ const unversionedId = PluginIdentifiers.unversionedFromVersioned(id);
+ const plugin = this.pluginSupport.getPlugin(unversionedId);
+ if (plugin) {
+ if (plugin.type === PluginType.System) {
+ this.builtins.add(unversionedId);
+ } else {
+ this.builtins.delete(unversionedId);
+ }
+ } else {
+ missingIds.add(id);
+ }
+ }
+ const missing = await this.pluginServer.getDeployedPlugins([...missingIds.values()]);
+ for (const plugin of missing) {
+ if (plugin.type === PluginType.System) {
+ this.builtins.add(PluginIdentifiers.componentsToUnversionedId(plugin.metadata.model));
+ } else {
+ this.builtins.delete(PluginIdentifiers.componentsToUnversionedId(plugin.metadata.model));
+ }
+ }
});
}
@@ -362,7 +437,7 @@ export class VSXExtensionsModel {
const updateRecommendationsForScope = (scope: PreferenceInspectionScope, root?: URI) => {
const { recommendations, unwantedRecommendations } = this.getRecommendationsForScope(scope, root);
- recommendations.forEach(recommendation => allRecommendations.add(recommendation));
+ recommendations.forEach(recommendation => allRecommendations.add(recommendation.toLowerCase()));
unwantedRecommendations.forEach(unwantedRecommendation => allUnwantedRecommendations.add(unwantedRecommendation));
};
@@ -449,15 +524,12 @@ export class VSXExtensionsModel {
* @param extension the extension to refresh.
*/
protected shouldRefresh(extension?: VSXExtension): boolean {
- if (extension === undefined) {
- return true;
- }
- return !extension.builtin;
+ return extension === undefined || extension.plugin === undefined;
}
protected onDidFailRefresh(id: string, error: unknown): VSXExtension | undefined {
const cached = this.getExtension(id);
- if (cached && cached.installed) {
+ if (cached && cached.deployed) {
return cached;
}
console.error(`[${id}]: failed to refresh, reason:`, error);
diff --git a/packages/vsx-registry/src/browser/vsx-language-quick-pick-service.ts b/packages/vsx-registry/src/browser/vsx-language-quick-pick-service.ts
index 717a35d1fe048..9c0b90311acde 100644
--- a/packages/vsx-registry/src/browser/vsx-language-quick-pick-service.ts
+++ b/packages/vsx-registry/src/browser/vsx-language-quick-pick-service.ts
@@ -71,7 +71,7 @@ export class VSXLanguageQuickPickService extends LanguageQuickPickService {
});
try {
const extensionUri = VSCodeExtensionUri.fromId(`${extension.extension.namespace}.${extension.extension.name}`).toString();
- await this.pluginServer.deploy(extensionUri);
+ await this.pluginServer.install(extensionUri);
} finally {
progress.cancel();
}