Merge branch 'main' into notebook/dev

This commit is contained in:
Johannes Rieken 2021-06-03 16:36:47 +02:00
commit 8f9eedf001
No known key found for this signature in database
GPG key ID: 96634B5AF12F8798
22 changed files with 141 additions and 67 deletions

View file

@ -337,7 +337,7 @@
"postStartCommand",
"postAttachCommand"
],
"description": "The user command to wait for before continuing execution in the background while the UI is starting up. The default is \"updateConentCommand\"."
"description": "The user command to wait for before continuing execution in the background while the UI is starting up. The default is \"updateContentCommand\"."
},
"devPort": {
"type": "integer",
@ -694,7 +694,7 @@
"postStartCommand",
"postAttachCommand"
],
"description": "The user command to wait for before continuing execution in the background while the UI is starting up. The default is \"updateConentCommand\"."
"description": "The user command to wait for before continuing execution in the background while the UI is starting up. The default is \"updateContentCommand\"."
},
"devPort": {
"type": "integer",
@ -1027,7 +1027,7 @@
"postStartCommand",
"postAttachCommand"
],
"description": "The user command to wait for before continuing execution in the background while the UI is starting up. The default is \"updateConentCommand\"."
"description": "The user command to wait for before continuing execution in the background while the UI is starting up. The default is \"updateContentCommand\"."
},
"devPort": {
"type": "integer",
@ -1326,7 +1326,7 @@
"postStartCommand",
"postAttachCommand"
],
"description": "The user command to wait for before continuing execution in the background while the UI is starting up. The default is \"updateConentCommand\"."
"description": "The user command to wait for before continuing execution in the background while the UI is starting up. The default is \"updateContentCommand\"."
},
"devPort": {
"type": "integer",
@ -1594,7 +1594,7 @@
"postStartCommand",
"postAttachCommand"
],
"description": "The user command to wait for before continuing execution in the background while the UI is starting up. The default is \"updateConentCommand\"."
"description": "The user command to wait for before continuing execution in the background while the UI is starting up. The default is \"updateContentCommand\"."
},
"devPort": {
"type": "integer",

View file

@ -236,7 +236,7 @@
"postStartCommand",
"postAttachCommand"
],
"description": "The user command to wait for before continuing execution in the background while the UI is starting up. The default is \"updateConentCommand\"."
"description": "The user command to wait for before continuing execution in the background while the UI is starting up. The default is \"updateContentCommand\"."
},
"devPort": {
"type": "integer",

View file

@ -60,6 +60,11 @@ export class SettingsDocument {
return provideInstalledExtensionProposals(alreadyConfigured, `: [\n\t"ui"\n]`, range, true);
}
// remote.portsAttributes
if (location.path[0] === 'remote.portsAttributes' && location.path.length === 2 && location.isAtPropertyKey) {
return this.providePortsAttributesCompletionItem(range);
}
return this.provideLanguageOverridesCompletionItems(location, position);
}
@ -238,6 +243,31 @@ export class SettingsDocument {
return Promise.resolve([]);
}
private providePortsAttributesCompletionItem(range: vscode.Range): vscode.CompletionItem[] {
return [this.newSnippetCompletionItem(
{
label: '\"3000\"',
documentation: 'Single Port Attribute',
range,
snippet: '\n \"${1:3000}\": {\n \"label\": \"${2:Application}\",\n \"onAutoForward\": \"${3:openPreview}\"\n }\n'
}),
this.newSnippetCompletionItem(
{
label: '\"5000-6000\"',
documentation: 'Ranged Port Attribute',
range,
snippet: '\n \"${1:40000-55000}\": {\n \"onAutoForward\": \"${2:ignore}\"\n }\n'
}),
this.newSnippetCompletionItem(
{
label: '\".+\\\\/server.js\"',
documentation: 'Command Match Port Attribute',
range,
snippet: '\n \"${1:.+\\\\/server.js\}\": {\n \"label\": \"${2:Application}\",\n \"onAutoForward\": \"${3:openPreview}\"\n }\n'
})
];
}
private newSimpleCompletionItem(text: string, range: vscode.Range, description?: string, insertText?: string): vscode.CompletionItem {
const item = new vscode.CompletionItem(text);
item.kind = vscode.CompletionItemKind.Value;

View file

@ -23,7 +23,7 @@
"capabilities": {
"virtualWorkspaces": false,
"untrustedWorkspaces": {
"supported": true
"supported": false
}
},
"contributes": {

View file

@ -165,6 +165,7 @@ export class CenteredViewLayout implements IDisposable {
this.splitView = undefined;
this.emptyViews = undefined;
this.container.appendChild(this.view.element);
this.view.layout(this.width, this.height, 0, 0);
}
}

View file

@ -65,6 +65,7 @@ export interface NativeParsedArgs {
'install-source'?: string;
'disable-updates'?: boolean;
'disable-keytar'?: boolean;
'disable-workspace-trust'?: boolean;
'disable-crash-reporter'?: boolean;
'crash-reporter-directory'?: string;
'crash-reporter-id'?: string;

View file

@ -66,6 +66,9 @@ export interface IEnvironmentService {
extensionDevelopmentKind?: ExtensionKind[];
extensionTestsLocationURI?: URI;
// --- workspace trust
disableWorkspaceTrust: boolean;
// --- logging
logsPath: string;
logLevel?: string;

View file

@ -231,6 +231,9 @@ export abstract class AbstractNativeEnvironmentService implements INativeEnviron
get telemetryLogResource(): URI { return URI.file(join(this.logsPath, 'telemetry.log')); }
get disableTelemetry(): boolean { return !!this.args['disable-telemetry']; }
@memoize
get disableWorkspaceTrust(): boolean { return !!this.args['disable-workspace-trust']; }
get args(): NativeParsedArgs { return this._args; }
constructor(

View file

@ -97,6 +97,7 @@ export const OPTIONS: OptionDescriptions<Required<NativeParsedArgs>> = {
'disable-telemetry': { type: 'boolean' },
'disable-updates': { type: 'boolean' },
'disable-keytar': { type: 'boolean' },
'disable-workspace-trust': { type: 'boolean' },
'disable-crash-reporter': { type: 'boolean' },
'crash-reporter-directory': { type: 'string' },
'crash-reporter-id': { type: 'string' },

View file

@ -99,7 +99,7 @@ class IndexedDBFileSystemNode {
}
read(path: string) {
read(path: string): IndexedDBFileSystemEntry | undefined {
return this.doRead(path.split('/').filter(p => p.length));
}

View file

@ -40,10 +40,11 @@ export interface IWorkspaceTrustManagementService {
onDidChangeTrust: Event<boolean>;
onDidChangeTrustedFolders: Event<void>;
readonly workspaceTrustEnabled: boolean;
readonly workspaceResolved: Promise<void>;
readonly workspaceTrustInitialized: Promise<void>;
acceptsOutOfWorkspaceFiles: boolean;
isWorkpaceTrusted(): boolean;
canSetParentFolderTrust(): boolean;

View file

@ -105,15 +105,27 @@ export class MainThreadExtensionService implements MainThreadExtensionServiceSha
});
} else {
const enablementState = this._extensionEnablementService.getEnablementState(missingInstalledDependency);
this._notificationService.notify({
severity: Severity.Error,
message: localize('disabledDep', "Cannot activate the '{0}' extension because it depends on the '{1}' extension, which is disabled. Would you like to enable the extension and reload the window?", extName, missingInstalledDependency.manifest.displayName || missingInstalledDependency.manifest.name),
actions: {
primary: [new Action('enable', localize('enable dep', "Enable and Reload"), '', true,
() => this._extensionEnablementService.setEnablement([missingInstalledDependency], enablementState === EnablementState.DisabledGlobally ? EnablementState.EnabledGlobally : EnablementState.EnabledWorkspace)
.then(() => this._hostService.reload(), e => this._notificationService.error(e)))]
}
});
if (enablementState === EnablementState.DisabledByTrustRequirement || enablementState === EnablementState.DisabledByVirtualWorkspace) {
this._notificationService.notify({
severity: Severity.Error,
message: localize('notSupportedInWorkspace', "Cannot activate the '{0}' extension because it depends on the '{1}' extension which is not supported in the current workspace", extName, missingInstalledDependency.manifest.displayName || missingInstalledDependency.manifest.name),
});
} else if (this._extensionEnablementService.canChangeEnablement(missingInstalledDependency)) {
this._notificationService.notify({
severity: Severity.Error,
message: localize('disabledDep', "Cannot activate the '{0}' extension because it depends on the '{1}' extension which is disabled. Would you like to enable the extension and reload the window?", extName, missingInstalledDependency.manifest.displayName || missingInstalledDependency.manifest.name),
actions: {
primary: [new Action('enable', localize('enable dep', "Enable and Reload"), '', true,
() => this._extensionEnablementService.setEnablement([missingInstalledDependency], enablementState === EnablementState.DisabledGlobally ? EnablementState.EnabledGlobally : EnablementState.EnabledWorkspace)
.then(() => this._hostService.reload(), e => this._notificationService.error(e)))]
}
});
} else {
this._notificationService.notify({
severity: Severity.Error,
message: localize('disabledDepNoAction', "Cannot activate the '{0}' extension because it depends on the '{1}' extension which is disabled.", extName, missingInstalledDependency.manifest.displayName || missingInstalledDependency.manifest.name),
});
}
}
}

View file

@ -21,7 +21,7 @@ import { KeyChord, KeyCode, KeyMod } from 'vs/base/common/keyCodes';
import { ContextKeyExpr } from 'vs/platform/contextkey/common/contextkey';
import { IWorkbenchEnvironmentService } from 'vs/workbench/services/environment/common/environmentService';
import { IWorkspacesService, hasWorkspaceFileExtension } from 'vs/platform/workspaces/common/workspaces';
import { WORKSPACE_TRUST_ENABLED } from 'vs/workbench/services/workspaces/common/workspaceTrust';
import { WorkspaceTrustContext, WORKSPACE_TRUST_ENABLED } from 'vs/workbench/services/workspaces/common/workspaceTrust';
import { IsWebContext } from 'vs/platform/contextkey/common/contextkeys';
import { KeybindingWeight } from 'vs/platform/keybinding/common/keybindingsRegistry';
@ -269,7 +269,7 @@ class WorkspaceTrustManageAction extends Action2 {
super({
id: 'workbench.action.manageTrust',
title: { value: localize('manageTrustAction', "Manage Workspace Trust"), original: 'Manage Workspace Trust' },
precondition: ContextKeyExpr.and(IsWebContext.negate(), ContextKeyExpr.equals(`config.${WORKSPACE_TRUST_ENABLED}`, true)),
precondition: ContextKeyExpr.and(WorkspaceTrustContext.IsEnabled, IsWebContext.negate(), ContextKeyExpr.equals(`config.${WORKSPACE_TRUST_ENABLED}`, true)),
category: localize('workspacesCategory', "Workspaces"),
f1: true
});

View file

@ -4,23 +4,24 @@
*--------------------------------------------------------------------------------------------*/
import { Disposable } from 'vs/base/common/lifecycle';
import { IConfigurationService } from 'vs/platform/configuration/common/configuration';
import { IWorkspaceTrustManagementService, IWorkspaceTrustTransitionParticipant } from 'vs/platform/workspace/common/workspaceTrust';
import { IWorkbenchContribution } from 'vs/workbench/common/contributions';
import { IWorkbenchEnvironmentService } from 'vs/workbench/services/environment/common/environmentService';
import { IWorkbenchExtensionEnablementService } from 'vs/workbench/services/extensionManagement/common/extensionManagement';
import { IExtensionService } from 'vs/workbench/services/extensions/common/extensions';
import { isWorkspaceTrustEnabled } from 'vs/workbench/services/workspaces/common/workspaceTrust';
import { IHostService } from 'vs/workbench/services/host/browser/host';
export class ExtensionEnablementWorkspaceTrustTransitionParticipant extends Disposable implements IWorkbenchContribution {
constructor(
@IConfigurationService configurationService: IConfigurationService,
@IExtensionService extensionService: IExtensionService,
@IHostService hostService: IHostService,
@IWorkbenchEnvironmentService environmentService: IWorkbenchEnvironmentService,
@IWorkbenchExtensionEnablementService extensionEnablementService: IWorkbenchExtensionEnablementService,
@IWorkspaceTrustManagementService workspaceTrustManagementService: IWorkspaceTrustManagementService,
) {
super();
if (isWorkspaceTrustEnabled(configurationService)) {
if (workspaceTrustManagementService.workspaceTrustEnabled) {
// The extension enablement participant will be registered only after the
// workspace trust state has been initialized. There is no need to execute
// the participant as part of the initialization process, as the workspace
@ -33,9 +34,13 @@ export class ExtensionEnablementWorkspaceTrustTransitionParticipant extends Disp
await extensionEnablementService.updateEnablementByWorkspaceTrustRequirement();
} else {
// Trusted -> Untrusted
extensionService.stopExtensionHosts();
await extensionEnablementService.updateEnablementByWorkspaceTrustRequirement();
extensionService.startExtensionHosts();
if (environmentService.remoteAuthority) {
hostService.reload();
} else {
extensionService.stopExtensionHosts();
await extensionEnablementService.updateEnablementByWorkspaceTrustRequirement();
extensionService.startExtensionHosts();
}
}
}
};

View file

@ -59,7 +59,6 @@ import { ILogService } from 'vs/platform/log/common/log';
import * as Constants from 'vs/workbench/contrib/logs/common/logConstants';
import { infoIcon, manageExtensionIcon, syncEnabledIcon, syncIgnoredIcon, trustIcon, warningIcon } from 'vs/workbench/contrib/extensions/browser/extensionsIcons';
import { isWeb } from 'vs/base/common/platform';
import { isWorkspaceTrustEnabled } from 'vs/workbench/services/workspaces/common/workspaceTrust';
import { IExtensionManifestPropertiesService } from 'vs/workbench/services/extensions/common/extensionManifestPropertiesService';
import { IWorkspaceTrustManagementService } from 'vs/platform/workspace/common/workspaceTrust';
import { isVirtualWorkspace } from 'vs/platform/remote/common/remoteHosts';
@ -2091,9 +2090,8 @@ export class SystemDisabledWarningAction extends ExtensionAction {
@IWorkspaceTrustManagementService private readonly workspaceTrustService: IWorkspaceTrustManagementService,
@IExtensionsWorkbenchService private readonly extensionsWorkbenchService: IExtensionsWorkbenchService,
@IExtensionService private readonly extensionService: IExtensionService,
@IConfigurationService private readonly configurationService: IConfigurationService,
@IExtensionManifestPropertiesService private readonly extensionManifestPropertiesService: IExtensionManifestPropertiesService,
@IWorkspaceContextService private readonly contextService: IWorkspaceContextService,
@IWorkspaceContextService private readonly contextService: IWorkspaceContextService
) {
super('extensions.install', '', `${SystemDisabledWarningAction.CLASS} hide`, false);
this._register(this.labelService.onDidChangeFormatters(() => this.update(), this));
@ -2174,7 +2172,7 @@ export class SystemDisabledWarningAction extends ExtensionAction {
}
const untrustedSupportType = this.extensionManifestPropertiesService.getExtensionUntrustedWorkspaceSupportType(this.extension.local.manifest);
if (isWorkspaceTrustEnabled(this.configurationService) && untrustedSupportType !== true && !this.workspaceTrustService.isWorkpaceTrusted()) {
if (this.workspaceTrustService.workspaceTrustEnabled && untrustedSupportType !== true && !this.workspaceTrustService.isWorkpaceTrusted()) {
const untrustedDetails = getWorkpaceSupportTypeMessage(this.extension.local.manifest.capabilities?.untrustedWorkspaces);
this.enabled = true;
this.class = `${SystemDisabledWarningAction.TRUST_CLASS}`;

View file

@ -25,7 +25,7 @@ import { IStatusbarEntry, IStatusbarEntryAccessor, IStatusbarService, StatusbarA
import { IEditorRegistry, EditorDescriptor } from 'vs/workbench/browser/editor';
import { shieldIcon, WorkspaceTrustEditor } from 'vs/workbench/contrib/workspace/browser/workspaceTrustEditor';
import { WorkspaceTrustEditorInput } from 'vs/workbench/services/workspaces/browser/workspaceTrustEditorInput';
import { isWorkspaceTrustEnabled, WORKSPACE_TRUST_EMPTY_WINDOW, WORKSPACE_TRUST_ENABLED, WORKSPACE_TRUST_STARTUP_PROMPT, WORKSPACE_TRUST_UNTRUSTED_FILES } from 'vs/workbench/services/workspaces/common/workspaceTrust';
import { WorkspaceTrustContext, WORKSPACE_TRUST_EMPTY_WINDOW, WORKSPACE_TRUST_ENABLED, WORKSPACE_TRUST_STARTUP_PROMPT, WORKSPACE_TRUST_UNTRUSTED_FILES } from 'vs/workbench/services/workspaces/common/workspaceTrust';
import { IEditorInputSerializer, IEditorInputFactoryRegistry, EditorExtensions, EditorResourceAccessor } from 'vs/workbench/common/editor';
import { ITelemetryService } from 'vs/platform/telemetry/common/telemetry';
import { IWorkspaceContextService, WorkbenchState } from 'vs/platform/workspace/common/workspace';
@ -168,7 +168,7 @@ export class WorkspaceTrustUXHandler extends Disposable implements IWorkbenchCon
await this.workspaceTrustManagementService.workspaceTrustInitialized;
if (isWorkspaceTrustEnabled(configurationService)) {
if (this.workspaceTrustManagementService.workspaceTrustEnabled) {
this.registerListeners();
this.createStatusbarEntry();
@ -537,7 +537,7 @@ export class WorkspaceTrustUXHandler extends Disposable implements IWorkbenchCon
if (e.fromCache) {
return;
}
if (!isWorkspaceTrustEnabled(this.configurationService)) {
if (!this.workspaceTrustManagementService.workspaceTrustEnabled) {
return;
}
const trusted = this.workspaceTrustManagementService.isWorkpaceTrusted();
@ -629,7 +629,7 @@ registerAction2(class extends Action2 {
id: MenuId.GlobalActivity,
group: '6_workspace_trust',
order: 40,
when: ContextKeyExpr.and(IsWebContext.negate(), ContextKeyExpr.equals(`config.${WORKSPACE_TRUST_ENABLED}`, true))
when: ContextKeyExpr.and(WorkspaceTrustContext.IsEnabled, IsWebContext.negate(), ContextKeyExpr.equals(`config.${WORKSPACE_TRUST_ENABLED}`, true))
},
});
}
@ -704,7 +704,6 @@ Registry.as<IConfigurationRegistry>(ConfigurationExtensions.Configuration)
*/
class WorkspaceTrustTelemetryContribution extends Disposable implements IWorkbenchContribution {
constructor(
@IConfigurationService private readonly configurationService: IConfigurationService,
@IExtensionService private readonly extensionService: IExtensionService,
@ITelemetryService private readonly telemetryService: ITelemetryService,
@IWorkspaceContextService private readonly workspaceContextService: IWorkspaceContextService,
@ -720,7 +719,7 @@ class WorkspaceTrustTelemetryContribution extends Disposable implements IWorkben
}
private logInitialWorkspaceTrustInfo(): void {
if (!isWorkspaceTrustEnabled(this.configurationService)) {
if (!this.workspaceTrustManagementService.workspaceTrustEnabled) {
return;
}
@ -738,7 +737,7 @@ class WorkspaceTrustTelemetryContribution extends Disposable implements IWorkben
}
private async logWorkspaceTrustChangeEvent(isTrusted: boolean): Promise<void> {
if (!isWorkspaceTrustEnabled(this.configurationService)) {
if (!this.workspaceTrustManagementService.workspaceTrustEnabled) {
return;
}
@ -798,7 +797,7 @@ class WorkspaceTrustTelemetryContribution extends Disposable implements IWorkben
}
private async logWorkspaceTrustRequest(): Promise<void> {
if (!isWorkspaceTrustEnabled(this.configurationService)) {
if (!this.workspaceTrustManagementService.workspaceTrustEnabled) {
return;
}

View file

@ -246,6 +246,9 @@ export class BrowserWorkbenchEnvironmentService implements IWorkbenchEnvironment
get skipReleaseNotes(): boolean { return false; }
@memoize
get disableWorkspaceTrust(): boolean { return true; }
private payload: Map<string, string> | undefined;
constructor(

View file

@ -55,6 +55,7 @@ export class TestExtensionEnablementService extends ExtensionEnablementService {
const storageService = createStorageService(instantiationService);
const extensionManagementService = instantiationService.get(IExtensionManagementService) || instantiationService.stub(IExtensionManagementService, { onDidInstallExtension: new Emitter<DidInstallExtensionEvent>().event, onDidUninstallExtension: new Emitter<DidUninstallExtensionEvent>().event } as IExtensionManagementService);
const extensionManagementServerService = instantiationService.get(IExtensionManagementServerService) || instantiationService.stub(IExtensionManagementServerService, <IExtensionManagementServerService>{ localExtensionManagementServer: { extensionManagementService } });
const workspaceTrustManagementService = instantiationService.get(IWorkspaceTrustManagementService) || instantiationService.stub(IWorkspaceTrustManagementService, new TestWorkspaceTrustManagementService());
super(
storageService,
new GlobalExtensionEnablementService(storageService),
@ -69,9 +70,9 @@ export class TestExtensionEnablementService extends ExtensionEnablementService {
instantiationService.get(INotificationService) || instantiationService.stub(INotificationService, new TestNotificationService()),
instantiationService.get(IHostService),
new class extends mock<IExtensionBisectService>() { override isDisabledByBisect() { return false; } },
instantiationService.get(IWorkspaceTrustManagementService) || instantiationService.stub(IWorkspaceTrustManagementService, new TestWorkspaceTrustManagementService()),
workspaceTrustManagementService,
new class extends mock<IWorkspaceTrustRequestService>() { override requestWorkspaceTrust(options?: WorkspaceTrustRequestOptions): Promise<boolean> { return Promise.resolve(true); } },
instantiationService.get(IExtensionManifestPropertiesService) || instantiationService.stub(IExtensionManifestPropertiesService, new ExtensionManifestPropertiesService(TestProductService, new TestConfigurationService()))
instantiationService.get(IExtensionManifestPropertiesService) || instantiationService.stub(IExtensionManifestPropertiesService, new ExtensionManifestPropertiesService(TestProductService, new TestConfigurationService(), workspaceTrustManagementService))
);
}

View file

@ -13,8 +13,9 @@ import { createDecorator } from 'vs/platform/instantiation/common/instantiation'
import { registerSingleton } from 'vs/platform/instantiation/common/extensions';
import { ExtensionUntrustedWorkspaceSupport } from 'vs/base/common/product';
import { Disposable } from 'vs/base/common/lifecycle';
import { isWorkspaceTrustEnabled, WORKSPACE_TRUST_EXTENSION_SUPPORT } from 'vs/workbench/services/workspaces/common/workspaceTrust';
import { WORKSPACE_TRUST_EXTENSION_SUPPORT } from 'vs/workbench/services/workspaces/common/workspaceTrust';
import { isBoolean } from 'vs/base/common/types';
import { IWorkspaceTrustManagementService } from 'vs/platform/workspace/common/workspaceTrust';
export const IExtensionManifestPropertiesService = createDecorator<IExtensionManifestPropertiesService>('extensionManifestPropertiesService');
@ -51,6 +52,7 @@ export class ExtensionManifestPropertiesService extends Disposable implements IE
constructor(
@IProductService private readonly productService: IProductService,
@IConfigurationService private readonly configurationService: IConfigurationService,
@IWorkspaceTrustManagementService private readonly workspaceTrustManagementService: IWorkspaceTrustManagementService
) {
super();
@ -124,7 +126,7 @@ export class ExtensionManifestPropertiesService extends Disposable implements IE
getExtensionUntrustedWorkspaceSupportType(manifest: IExtensionManifest): ExtensionUntrustedWorkpaceSupportType {
// Workspace trust feature is disabled, or extension has no entry point
if (!isWorkspaceTrustEnabled(this.configurationService) || !manifest.main) {
if (!this.workspaceTrustManagementService.workspaceTrustEnabled || !manifest.main) {
return true;
}

View file

@ -12,11 +12,13 @@ import { TestInstantiationService } from 'vs/platform/instantiation/test/common/
import { IConfigurationService } from 'vs/platform/configuration/common/configuration';
import { IProductService } from 'vs/platform/product/common/productService';
import { isWeb } from 'vs/base/common/platform';
import { TestWorkspaceTrustManagementService } from 'vs/workbench/services/workspaces/test/common/testWorkspaceTrustService';
import { IWorkspaceTrustManagementService } from 'vs/platform/workspace/common/workspaceTrust';
suite('ExtensionManifestPropertiesService - ExtensionKind', () => {
function check(manifest: Partial<IExtensionManifest>, expected: ExtensionKind[]): void {
const extensionManifestPropertiesService = new ExtensionManifestPropertiesService(TestProductService, new TestConfigurationService());
const extensionManifestPropertiesService = new ExtensionManifestPropertiesService(TestProductService, new TestConfigurationService(), new TestWorkspaceTrustManagementService());
assert.deepStrictEqual(extensionManifestPropertiesService.deduceExtensionKind(<IExtensionManifest>manifest), expected);
}
@ -80,6 +82,7 @@ if (!isWeb) {
test('test extension workspace trust request when main entry point is missing', () => {
instantiationService.stub(IProductService, <Partial<IProductService>>{});
instantiationService.stub(IWorkspaceTrustManagementService, new TestWorkspaceTrustManagementService());
const extensionMaifest = getExtensionManifest();
assertUntrustedWorkspaceSupport(extensionMaifest, true);
@ -87,7 +90,7 @@ if (!isWeb) {
test('test extension workspace trust request when workspace trust is disabled', async () => {
instantiationService.stub(IProductService, <Partial<IProductService>>{});
await testConfigurationService.setUserConfiguration('security', { workspace: { trust: { enabled: false } } });
instantiationService.stub(IWorkspaceTrustManagementService, new TestWorkspaceTrustManagementService(false));
const extensionMaifest = getExtensionManifest({ main: './out/extension.js' });
assertUntrustedWorkspaceSupport(extensionMaifest, true);
@ -95,6 +98,7 @@ if (!isWeb) {
test('test extension workspace trust request when override exists in settings.json', async () => {
instantiationService.stub(IProductService, <Partial<IProductService>>{});
instantiationService.stub(IWorkspaceTrustManagementService, new TestWorkspaceTrustManagementService());
await testConfigurationService.setUserConfiguration('extensions', { supportUntrustedWorkspaces: { 'pub.a': { supported: true } } });
const extensionMaifest = getExtensionManifest({ main: './out/extension.js', capabilities: { untrustedWorkspaces: { supported: 'limited' } } });
@ -103,6 +107,7 @@ if (!isWeb) {
test('test extension workspace trust request when override for the version exists in settings.json', async () => {
instantiationService.stub(IProductService, <Partial<IProductService>>{});
instantiationService.stub(IWorkspaceTrustManagementService, new TestWorkspaceTrustManagementService());
await testConfigurationService.setUserConfiguration('extensions', { supportUntrustedWorkspaces: { 'pub.a': { supported: true, version: '1.0.0' } } });
const extensionMaifest = getExtensionManifest({ main: './out/extension.js', capabilities: { untrustedWorkspaces: { supported: 'limited' } } });
@ -111,6 +116,7 @@ if (!isWeb) {
test('test extension workspace trust request when override for a different version exists in settings.json', async () => {
instantiationService.stub(IProductService, <Partial<IProductService>>{});
instantiationService.stub(IWorkspaceTrustManagementService, new TestWorkspaceTrustManagementService());
await testConfigurationService.setUserConfiguration('extensions', { supportUntrustedWorkspaces: { 'pub.a': { supported: true, version: '2.0.0' } } });
const extensionMaifest = getExtensionManifest({ main: './out/extension.js', capabilities: { untrustedWorkspaces: { supported: 'limited' } } });
@ -119,6 +125,7 @@ if (!isWeb) {
test('test extension workspace trust request when default exists in product.json', () => {
instantiationService.stub(IProductService, <Partial<IProductService>>{ extensionUntrustedWorkspaceSupport: { 'pub.a': { default: true } } });
instantiationService.stub(IWorkspaceTrustManagementService, new TestWorkspaceTrustManagementService());
const extensionMaifest = getExtensionManifest({ main: './out/extension.js' });
assertUntrustedWorkspaceSupport(extensionMaifest, true);
@ -126,6 +133,7 @@ if (!isWeb) {
test('test extension workspace trust request when override exists in product.json', () => {
instantiationService.stub(IProductService, <Partial<IProductService>>{ extensionUntrustedWorkspaceSupport: { 'pub.a': { override: 'limited' } } });
instantiationService.stub(IWorkspaceTrustManagementService, new TestWorkspaceTrustManagementService());
const extensionMaifest = getExtensionManifest({ main: './out/extension.js', capabilities: { untrustedWorkspaces: { supported: true } } });
assertUntrustedWorkspaceSupport(extensionMaifest, 'limited');
@ -133,6 +141,7 @@ if (!isWeb) {
test('test extension workspace trust request when value exists in package.json', () => {
instantiationService.stub(IProductService, <Partial<IProductService>>{});
instantiationService.stub(IWorkspaceTrustManagementService, new TestWorkspaceTrustManagementService());
const extensionMaifest = getExtensionManifest({ main: './out/extension.js', capabilities: { untrustedWorkspaces: { supported: 'limited' } } });
assertUntrustedWorkspaceSupport(extensionMaifest, 'limited');
@ -140,6 +149,7 @@ if (!isWeb) {
test('test extension workspace trust request when no value exists in package.json', () => {
instantiationService.stub(IProductService, <Partial<IProductService>>{});
instantiationService.stub(IWorkspaceTrustManagementService, new TestWorkspaceTrustManagementService());
const extensionMaifest = getExtensionManifest({ main: './out/extension.js' });
assertUntrustedWorkspaceSupport(extensionMaifest, false);

View file

@ -10,7 +10,6 @@ import { splitName } from 'vs/base/common/labels';
import { Disposable, IDisposable, toDisposable } from 'vs/base/common/lifecycle';
import { LinkedList } from 'vs/base/common/linkedList';
import { Schemas } from 'vs/base/common/network';
import { isWeb } from 'vs/base/common/platform';
import Severity from 'vs/base/common/severity';
import { URI } from 'vs/base/common/uri';
import { localize } from 'vs/nls';
@ -35,18 +34,10 @@ export const WORKSPACE_TRUST_EXTENSION_SUPPORT = 'extensions.supportUntrustedWor
export const WORKSPACE_TRUST_STORAGE_KEY = 'content.trust.model.key';
export const WorkspaceTrustContext = {
IsTrusted: new RawContextKey<boolean>('isWorkspaceTrusted', false, localize('workspaceTrustCtx', "Whether the current workspace has been trusted by the user."))
IsEnabled: new RawContextKey<boolean>('isWorkspaceTrustEnabled', false, localize('workspaceTrustEnabledCtx', "Whether the workspace trust feature is enabled.")),
IsTrusted: new RawContextKey<boolean>('isWorkspaceTrusted', false, localize('workspaceTrustedCtx', "Whether the current workspace has been trusted by the user."))
};
export function isWorkspaceTrustEnabled(configurationService: IConfigurationService): boolean {
if (isWeb) {
return false;
}
return (configurationService.inspect<boolean>(WORKSPACE_TRUST_ENABLED).userValue ?? configurationService.inspect<boolean>(WORKSPACE_TRUST_ENABLED).defaultValue) ?? false;
}
export class CanonicalWorkspace implements IWorkspace {
constructor(
private readonly originalWorkspace: IWorkspace,
@ -75,8 +66,6 @@ export class CanonicalWorkspace implements IWorkspace {
}
}
export class WorkspaceTrustManagementService extends Disposable implements IWorkspaceTrustManagementService {
_serviceBrand: undefined;
@ -231,7 +220,7 @@ export class WorkspaceTrustManagementService extends Disposable implements IWork
}
private calculateWorkspaceTrust(): boolean {
if (!isWorkspaceTrustEnabled(this.configurationService)) {
if (!this.workspaceTrustEnabled) {
return true;
}
@ -258,7 +247,7 @@ export class WorkspaceTrustManagementService extends Disposable implements IWork
}
private async updateWorkspaceTrust(trusted?: boolean): Promise<void> {
if (!isWorkspaceTrustEnabled(this.configurationService)) {
if (!this.workspaceTrustEnabled) {
return;
}
@ -295,7 +284,7 @@ export class WorkspaceTrustManagementService extends Disposable implements IWork
private doGetUriTrustInfo(uri: URI): IWorkspaceTrustUriInfo {
// Return trusted when workspace trust is disabled
if (!isWorkspaceTrustEnabled(this.configurationService)) {
if (!this.workspaceTrustEnabled) {
return { trusted: true, uri };
}
@ -350,6 +339,14 @@ export class WorkspaceTrustManagementService extends Disposable implements IWork
return this._workspaceResolvedPromise;
}
get workspaceTrustEnabled(): boolean {
if (this.environmentService.disableWorkspaceTrust) {
return false;
}
return this.configurationService.getValue<boolean>(WORKSPACE_TRUST_ENABLED) ?? false;
}
get workspaceTrustInitialized(): Promise<void> {
return this._workspaceTrustInitializedPromise;
}
@ -434,7 +431,7 @@ export class WorkspaceTrustManagementService extends Disposable implements IWork
async getUriTrustInfo(uri: URI): Promise<IWorkspaceTrustUriInfo> {
// Return trusted when workspace trust is disabled
if (!isWorkspaceTrustEnabled(this.configurationService)) {
if (!this.workspaceTrustEnabled) {
return { trusted: true, uri };
}
@ -488,6 +485,7 @@ export class WorkspaceTrustRequestService extends Disposable implements IWorkspa
private _trusted!: boolean;
private _modalTrustRequestPromise?: Promise<boolean | undefined>;
private _modalTrustRequestResolver?: (trusted: boolean | undefined) => void;
private readonly _ctxWorkspaceTrustEnabled: IContextKey<boolean>;
private readonly _ctxWorkspaceTrustState: IContextKey<boolean>;
private readonly _onDidInitiateWorkspaceTrustRequest = this._register(new Emitter<WorkspaceTrustRequestOptions | undefined>());
@ -505,7 +503,9 @@ export class WorkspaceTrustRequestService extends Disposable implements IWorkspa
this._register(this.workspaceTrustManagementService.onDidChangeTrust(trusted => this.trusted = trusted));
this._ctxWorkspaceTrustEnabled = WorkspaceTrustContext.IsEnabled.bindTo(contextKeyService);
this._ctxWorkspaceTrustState = WorkspaceTrustContext.IsTrusted.bindTo(contextKeyService);
this._ctxWorkspaceTrustEnabled.set(this.workspaceTrustManagementService.workspaceTrustEnabled);
this.trusted = this.workspaceTrustManagementService.isWorkpaceTrusted();
}

View file

@ -21,10 +21,10 @@ export class TestWorkspaceTrustManagementService implements IWorkspaceTrustManag
private _onDidInitiateWorkspaceTrustRequestOnStartup = new Emitter<void>();
onDidInitiateWorkspaceTrustRequestOnStartup = this._onDidInitiateWorkspaceTrustRequestOnStartup.event;
private trusted: boolean;
constructor(trusted: boolean = true) {
this.trusted = trusted;
constructor(
private enabled: boolean = true,
private trusted: boolean = true) {
}
get acceptsOutOfWorkspaceFiles(): boolean {
@ -71,14 +71,18 @@ export class TestWorkspaceTrustManagementService implements IWorkspaceTrustManag
return this.trusted;
}
get workspaceResolved(): Promise<void> {
return Promise.resolve();
get workspaceTrustEnabled(): boolean {
return this.enabled;
}
get workspaceTrustInitialized(): Promise<void> {
return Promise.resolve();
}
get workspaceResolved(): Promise<void> {
return Promise.resolve();
}
async setWorkspaceTrust(trusted: boolean): Promise<void> {
if (this.trusted !== trusted) {
this.trusted = trusted;