/*--------------------------------------------------------------------------------------------- * Copyright (c) Microsoft Corporation. All rights reserved. * Licensed under the MIT License. See License.txt in the project root for license information. *--------------------------------------------------------------------------------------------*/ import 'vs/css!./media/extensionActions'; import { localize } from 'vs/nls'; import { TPromise } from 'vs/base/common/winjs.base'; import { Action } from 'vs/base/common/actions'; import severity from 'vs/base/common/severity'; import { IDisposable, dispose } from 'vs/base/common/lifecycle'; import { ReloadWindowAction } from 'vs/workbench/electron-browser/actions'; import { IExtension, ExtensionState, IExtensionsWorkbenchService, VIEWLET_ID, IExtensionsViewlet } from './extensions'; import { IInstantiationService } from 'vs/platform/instantiation/common/instantiation'; import { IMessageService, CloseAction } from 'vs/platform/message/common/message'; import { ToggleViewletAction } from 'vs/workbench/browser/viewlet'; import { IViewletService } from 'vs/workbench/services/viewlet/common/viewletService'; import { IWorkbenchEditorService } from 'vs/workbench/services/editor/common/editorService'; export class InstallAction extends Action { private static InstallLabel = localize('installAction', "Install"); private static InstallingLabel = localize('installing', "Installing"); private disposables: IDisposable[] = []; constructor( private extension: IExtension, @IExtensionsWorkbenchService private extensionsWorkbenchService: IExtensionsWorkbenchService ) { super('extensions.install', InstallAction.InstallLabel, 'extension-action install', false); this.disposables.push(this.extensionsWorkbenchService.onChange(() => this.update())); this.update(); } private update(): void { this.enabled = this.extensionsWorkbenchService.canInstall(this.extension) && this.extension.state === ExtensionState.Uninstalled; this.label = this.extension.state === ExtensionState.Installing ? InstallAction.InstallingLabel : InstallAction.InstallLabel; } run(): TPromise { return this.extensionsWorkbenchService.install(this.extension); } dispose(): void { super.dispose(); this.disposables = dispose(this.disposables); } } export class UninstallAction extends Action { private disposables: IDisposable[] = []; constructor( private extension: IExtension, @IExtensionsWorkbenchService private extensionsWorkbenchService: IExtensionsWorkbenchService, @IMessageService private messageService: IMessageService, @IInstantiationService private instantiationService: IInstantiationService ) { super('extensions.uninstall', localize('uninstall', "Uninstall"), 'extension-action uninstall', false); this.disposables.push(this.extensionsWorkbenchService.onChange(() => this.updateEnablement())); this.updateEnablement(); } private updateEnablement(): void { this.enabled = this.extension.state === ExtensionState.Installed || this.extension.state === ExtensionState.NeedsRestart; } run(): TPromise { if (!window.confirm(localize('deleteSure', "Are you sure you want to uninstall '{0}'?", this.extension.displayName))) { return TPromise.as(null); } return this.extensionsWorkbenchService.uninstall(this.extension).then(() => { this.messageService.show(severity.Info, { message: localize('postUninstallMessage', "{0} was successfully uninstalled. Restart to deactivate it.", this.extension.displayName), actions: [CloseAction, this.instantiationService.createInstance(ReloadWindowAction, ReloadWindowAction.ID, localize('restartNow', "Restart Now"))] }); }); } dispose(): void { super.dispose(); this.disposables = dispose(this.disposables); } } export class CombinedInstallAction extends Action { private installAction: InstallAction; private uninstallAction: UninstallAction; private disposables: IDisposable[] = []; constructor( private extension: IExtension, @IInstantiationService instantiationService: IInstantiationService ) { super('extensions.combinedInstall', '', '', false); this.installAction = instantiationService.createInstance(InstallAction, extension); this.uninstallAction = instantiationService.createInstance(UninstallAction, extension); this.disposables.push(this.installAction, this.uninstallAction); this.installAction.onDidChange(this.update, this, this.disposables); this.update(); } private update(): void { if (this.installAction.enabled) { this.enabled = true; this.label = this.installAction.label; this.class = this.installAction.class; } else if (this.uninstallAction.enabled) { this.enabled = true; this.label = this.uninstallAction.label; this.class = this.uninstallAction.class; } else if (this.extension.state === ExtensionState.Installing) { this.enabled = false; this.label = this.installAction.label; this.class = this.installAction.class; } else { this.enabled = false; } } run(): TPromise { if (this.installAction.enabled) { return this.installAction.run(); } else if (this.uninstallAction.enabled) { return this.uninstallAction.run(); } return TPromise.as(null); } dispose(): void { super.dispose(); this.disposables = dispose(this.disposables); } } export class UpdateAction extends Action { private static EnabledClass = 'extension-action update'; private static DisabledClass = `${ UpdateAction.EnabledClass } disabled`; private disposables: IDisposable[] = []; constructor( private extension: IExtension, @IExtensionsWorkbenchService private extensionsWorkbenchService: IExtensionsWorkbenchService ) { super('extensions.update', localize('updateAction', "Update"), UpdateAction.DisabledClass, false); this.disposables.push(this.extensionsWorkbenchService.onChange(() => this.updateEnablement())); this.updateEnablement(); } private updateEnablement(): void { const canInstall = this.extensionsWorkbenchService.canInstall(this.extension); const isInstalled = this.extension.state === ExtensionState.Installed || this.extension.state === ExtensionState.NeedsRestart; this.enabled = canInstall && isInstalled && this.extension.outdated; this.class = this.enabled ? UpdateAction.EnabledClass : UpdateAction.DisabledClass; } run(): TPromise { return this.extensionsWorkbenchService.install(this.extension); } dispose(): void { super.dispose(); this.disposables = dispose(this.disposables); } } export class EnableAction extends Action { private static EnabledClass = 'extension-action enable'; private static DisabledClass = `${ EnableAction.EnabledClass } disabled`; private disposables: IDisposable[] = []; constructor( private extension: IExtension, @IExtensionsWorkbenchService private extensionsWorkbenchService: IExtensionsWorkbenchService, @IInstantiationService private instantiationService: IInstantiationService ) { super('extensions.enable', localize('enableAction', "Enable"), EnableAction.DisabledClass, false); this.disposables.push(this.extensionsWorkbenchService.onChange(() => this.updateEnablement())); this.updateEnablement(); } private updateEnablement(): void { this.enabled = this.extension.state === ExtensionState.NeedsRestart; this.class = this.enabled ? EnableAction.EnabledClass : EnableAction.DisabledClass; } run(): TPromise { if (!window.confirm(localize('restart', "In order to enable this extension, this window of VS Code needs to be restarted.\n\nDo you want to continue?"))) { return TPromise.as(null); } const action = this.instantiationService.createInstance(ReloadWindowAction, ReloadWindowAction.ID, localize('restartNow', "Restart Now")); return action.run(); } dispose(): void { super.dispose(); this.disposables = dispose(this.disposables); } } export class OpenExtensionsViewletAction extends ToggleViewletAction { static ID = VIEWLET_ID; static LABEL = localize('toggleExtensionsViewlet', "Show Extensions"); constructor( id: string, label: string, @IViewletService viewletService: IViewletService, @IWorkbenchEditorService editorService: IWorkbenchEditorService ) { super(id, label, VIEWLET_ID, viewletService, editorService); } } export class InstallExtensionsAction extends OpenExtensionsViewletAction { static ID = 'workbench.extensions.action.installExtensions'; static LABEL = localize('installExtensions', "Install Extensions"); } export class ClearExtensionsInputAction extends Action { static ID = 'workbench.extensions.action.clearExtensionsInput'; static LABEL = localize('clearExtensionsInput', "Clear Extensions Input"); constructor( id: string, label: string, @IViewletService private viewletService: IViewletService, @IExtensionsWorkbenchService private extensionsWorkbenchService: IExtensionsWorkbenchService ) { super(id, label, 'clear-extensions', true); } run(): TPromise { return this.viewletService.openViewlet(VIEWLET_ID, true) .then(viewlet => viewlet as IExtensionsViewlet) .then(viewlet => { viewlet.search('', true); viewlet.focus(); }); } } export class ListOutdatedExtensionsAction extends Action { static ID = 'workbench.extensions.action.listOutdatedExtensions'; static LABEL = localize('showOutdatedExtensions', "Show Outdated Extensions"); constructor( id: string, label: string, @IViewletService private viewletService: IViewletService ) { super(id, label, null, true); } run(): TPromise { return this.viewletService.openViewlet(VIEWLET_ID, true) .then(viewlet => viewlet as IExtensionsViewlet) .then(viewlet => { viewlet.search('@outdated', true); viewlet.focus(); }); } protected isEnabled(): boolean { return true; } } export class ShowPopularExtensionsAction extends Action { static ID = 'workbench.extensions.action.showPopularExtensions'; static LABEL = localize('showPopularExtensions', "Show Popular Extensions"); constructor( id: string, label: string, @IViewletService private viewletService: IViewletService ) { super(id, label, null, true); } run(): TPromise { return this.viewletService.openViewlet(VIEWLET_ID, true) .then(viewlet => viewlet as IExtensionsViewlet) .then(viewlet => { viewlet.search('@popular', true); viewlet.focus(); }); } protected isEnabled(): boolean { return true; } } export class ShowRecommendedExtensionsAction extends Action { static ID = 'workbench.extensions.action.showRecommendedExtensions'; static LABEL = localize('showRecommendedExtensions', "Show Recommended Extension"); constructor( id: string, label: string, @IViewletService private viewletService: IViewletService ) { super(id, label, null, true); } run(): TPromise { return this.viewletService.openViewlet(VIEWLET_ID, true) .then(viewlet => viewlet as IExtensionsViewlet) .then(viewlet => { viewlet.search('@recommended', true); viewlet.focus(); }); } protected isEnabled(): boolean { return true; } } export class ShowInstalledExtensionsAction extends ClearExtensionsInputAction { static ID = 'workbench.extensions.action.showInstalledExtensions'; static LABEL = localize('showInstalledExtensions', "Show Installed Extensions"); }