Merge VS Code 1.21 source code (#1067)

* Initial VS Code 1.21 file copy with patches

* A few more merges

* Post npm install

* Fix batch of build breaks

* Fix more build breaks

* Fix more build errors

* Fix more build breaks

* Runtime fixes 1

* Get connection dialog working with some todos

* Fix a few packaging issues

* Copy several node_modules to package build to fix loader issues

* Fix breaks from master

* A few more fixes

* Make tests pass

* First pass of license header updates

* Second pass of license header updates

* Fix restore dialog issues

* Remove add additional themes menu items

* fix select box issues where the list doesn't show up

* formatting

* Fix editor dispose issue

* Copy over node modules to correct location on all platforms
This commit is contained in:
Karl Burtram
2018-04-04 15:27:51 -07:00
committed by GitHub
parent 5fba3e31b4
commit dafb780987
9412 changed files with 141255 additions and 98813 deletions

View File

@@ -14,25 +14,27 @@ import * as objects from 'vs/base/common/objects';
import uri from 'vs/base/common/uri';
import * as paths from 'vs/base/common/paths';
import { IJSONSchema } from 'vs/base/common/jsonSchema';
import { IModel } from 'vs/editor/common/editorCommon';
import { ITextModel } from 'vs/editor/common/model';
import { IEditor } from 'vs/platform/editor/common/editor';
import { ILifecycleService } from 'vs/platform/lifecycle/common/lifecycle';
import { IStorageService, StorageScope } from 'vs/platform/storage/common/storage';
import * as extensionsRegistry from 'vs/platform/extensions/common/extensionsRegistry';
import * as extensionsRegistry from 'vs/workbench/services/extensions/common/extensionsRegistry';
import { Registry } from 'vs/platform/registry/common/platform';
import { IExtensionService } from 'vs/platform/extensions/common/extensions';
import { IExtensionService } from 'vs/workbench/services/extensions/common/extensions';
import { IJSONContributionRegistry, Extensions as JSONExtensions } from 'vs/platform/jsonschemas/common/jsonContributionRegistry';
import { IConfigurationService } from 'vs/platform/configuration/common/configuration';
import { IFileService } from 'vs/platform/files/common/files';
import { IWorkspaceContextService, IWorkspaceFolder } from 'vs/platform/workspace/common/workspace';
import { IWorkspaceContextService, IWorkspaceFolder, WorkbenchState } from 'vs/platform/workspace/common/workspace';
import { IInstantiationService } from 'vs/platform/instantiation/common/instantiation';
import { ICommandService } from 'vs/platform/commands/common/commands';
import { IDebugConfigurationProvider, IRawAdapter, ICompound, IDebugConfiguration, IConfig, IEnvConfig, IGlobalConfig, IConfigurationManager, ILaunch } from 'vs/workbench/parts/debug/common/debug';
import { IDebugConfigurationProvider, IRawAdapter, ICompound, IDebugConfiguration, IConfig, IEnvConfig, IGlobalConfig, IConfigurationManager, ILaunch, IAdapterExecutable } from 'vs/workbench/parts/debug/common/debug';
import { Adapter } from 'vs/workbench/parts/debug/node/debugAdapter';
import { IWorkbenchEditorService } from 'vs/workbench/services/editor/common/editorService';
import { IQuickOpenService } from 'vs/platform/quickOpen/common/quickOpen';
import { IConfigurationResolverService } from 'vs/workbench/services/configurationResolver/common/configurationResolver';
import { isCodeEditor } from 'vs/editor/browser/editorBrowser';
import { launchSchemaId } from 'vs/workbench/services/configuration/common/configuration';
import { IPreferencesService } from 'vs/workbench/parts/preferences/common/preferences';
// debuggers extension point
export const debuggersExtPoint = extensionsRegistry.ExtensionsRegistry.registerExtensionPoint<IRawAdapter[]>('debuggers', [], {
@@ -102,11 +104,11 @@ export const debuggersExtPoint = extensionsRegistry.ExtensionsRegistry.registerE
}
},
osx: {
description: nls.localize('vscode.extension.contributes.debuggers.osx', "OS X specific settings."),
description: nls.localize('vscode.extension.contributes.debuggers.osx', "macOS specific settings."),
type: 'object',
properties: {
runtime: {
description: nls.localize('vscode.extension.contributes.debuggers.osx.runtime', "Runtime used for OSX."),
description: nls.localize('vscode.extension.contributes.debuggers.osx.runtime', "Runtime used for macOS."),
type: 'string'
}
}
@@ -147,14 +149,12 @@ const breakpointsExtPoint = extensionsRegistry.ExtensionsRegistry.registerExtens
});
// debug general schema
export const schemaId = 'vscode://schemas/launch';
const defaultCompound: ICompound = { name: 'Compound', configurations: [] };
const schema: IJSONSchema = {
id: schemaId,
id: launchSchemaId,
type: 'object',
title: nls.localize('app.launch.json.title', "Launch"),
required: ['version', 'configurations'],
required: [],
default: { version: '0.2.0', configurations: [], compounds: [] },
properties: {
version: {
@@ -186,7 +186,23 @@ const schema: IJSONSchema = {
type: 'array',
default: [],
items: {
type: 'string'
oneOf: [{
enum: [],
description: nls.localize('useUniqueNames', "Please use unique configuration names.")
}, {
type: 'object',
required: ['name'],
properties: {
name: {
enum: [],
description: nls.localize('app.launch.json.compound.name', "Name of compound. Appears in the launch configuration drop down menu.")
},
folder: {
enum: [],
description: nls.localize('app.launch.json.compound.folder', "Name of folder in which the compound is located.")
}
}
}]
},
description: nls.localize('app.launch.json.compounds.configurations', "Names of configurations that will be started as part of this compound.")
}
@@ -201,7 +217,7 @@ const schema: IJSONSchema = {
};
const jsonRegistry = <IJSONContributionRegistry>Registry.as(JSONExtensions.JSONContribution);
jsonRegistry.registerSchema(schemaId, schema);
jsonRegistry.registerSchema(launchSchemaId, schema);
const DEBUG_SELECTED_CONFIG_NAME_KEY = 'debug.selectedconfigname';
const DEBUG_SELECTED_ROOT = 'debug.selectedroot';
@@ -209,8 +225,8 @@ export class ConfigurationManager implements IConfigurationManager {
private adapters: Adapter[];
private breakpointModeIdsSet = new Set<string>();
private launches: ILaunch[];
private _selectedName: string;
private _selectedLaunch: ILaunch;
private selectedName: string;
private selectedLaunch: ILaunch;
private toDispose: IDisposable[];
private _onDidSelectConfigurationName = new Emitter<void>();
private providers: IDebugConfigurationProvider[];
@@ -232,7 +248,7 @@ export class ConfigurationManager implements IConfigurationManager {
this.registerListeners(lifecycleService);
this.initLaunches();
const previousSelectedRoot = this.storageService.get(DEBUG_SELECTED_ROOT, StorageScope.WORKSPACE);
const filtered = this.launches.filter(l => l.workspace.uri.toString() === previousSelectedRoot);
const filtered = this.launches.filter(l => l.uri.toString() === previousSelectedRoot);
this.selectConfiguration(filtered.length ? filtered[0] : undefined, this.storageService.get(DEBUG_SELECTED_CONFIG_NAME_KEY, StorageScope.WORKSPACE));
}
@@ -276,6 +292,14 @@ export class ConfigurationManager implements IConfigurationManager {
.then(results => results.reduce((first, second) => first.concat(second), []));
}
public debugAdapterExecutable(folderUri: uri | undefined, type: string): TPromise<IAdapterExecutable | undefined> {
const providers = this.providers.filter(p => p.type === type && p.debugAdapterExecutable);
if (providers.length === 1) {
return providers[0].debugAdapterExecutable(folderUri);
}
return TPromise.as(undefined);
}
private registerListeners(lifecycleService: ILifecycleService): void {
debuggersExtPoint.setHandler((extensions) => {
extensions.forEach(extension => {
@@ -293,7 +317,7 @@ export class ConfigurationManager implements IConfigurationManager {
if (duplicate) {
duplicate.merge(rawAdapter, extension.description);
} else {
this.adapters.push(new Adapter(rawAdapter, extension.description, this.configurationService, this.commandService));
this.adapters.push(new Adapter(this, rawAdapter, extension.description, this.configurationService, this.commandService));
}
});
});
@@ -310,6 +334,8 @@ export class ConfigurationManager implements IConfigurationManager {
items.defaultSnippets.push(...configurationSnippets);
}
});
this.setCompoundSchemaValues();
});
breakpointsExtPoint.setHandler(extensions => {
@@ -323,10 +349,12 @@ export class ConfigurationManager implements IConfigurationManager {
this.toDispose.push(this.contextService.onDidChangeWorkspaceFolders(() => {
this.initLaunches();
this.selectConfiguration();
this.setCompoundSchemaValues();
}));
this.toDispose.push(this.configurationService.onDidChangeConfiguration(e => {
if (e.affectsConfiguration('launch')) {
this.selectConfiguration();
this.setCompoundSchemaValues();
}
}));
@@ -335,42 +363,75 @@ export class ConfigurationManager implements IConfigurationManager {
private initLaunches(): void {
this.launches = this.contextService.getWorkspace().folders.map(folder => this.instantiationService.createInstance(Launch, this, folder));
if (this.launches.indexOf(this._selectedLaunch) === -1) {
this._selectedLaunch = undefined;
if (this.contextService.getWorkbenchState() === WorkbenchState.WORKSPACE) {
this.launches.push(this.instantiationService.createInstance(WorkspaceLaunch, this));
}
this.launches.push(this.instantiationService.createInstance(UserLaunch, this));
if (this.launches.indexOf(this.selectedLaunch) === -1) {
this.selectedLaunch = undefined;
}
}
private setCompoundSchemaValues(): void {
const compoundConfigurationsSchema = (<IJSONSchema>schema.properties['compounds'].items).properties['configurations'];
const launchNames = this.launches.map(l =>
l.getConfigurationNames(false)).reduce((first, second) => first.concat(second), []);
(<IJSONSchema>compoundConfigurationsSchema.items).oneOf[0].enum = launchNames;
(<IJSONSchema>compoundConfigurationsSchema.items).oneOf[1].properties.name.enum = launchNames;
const folderNames = this.contextService.getWorkspace().folders.map(f => f.name);
(<IJSONSchema>compoundConfigurationsSchema.items).oneOf[1].properties.folder.enum = folderNames;
jsonRegistry.registerSchema(launchSchemaId, schema);
}
public getLaunches(): ILaunch[] {
return this.launches;
}
public get selectedLaunch(): ILaunch {
return this._selectedLaunch;
public getLaunch(workspaceUri: uri): ILaunch {
if (!uri.isUri(workspaceUri)) {
return undefined;
}
return this.launches.filter(l => l.workspace && l.workspace.uri.toString() === workspaceUri.toString()).pop();
}
public get selectedName(): string {
return this._selectedName;
public get selectedConfiguration(): { launch: ILaunch, name: string } {
return {
launch: this.selectedLaunch,
name: this.selectedName
};
}
public get onDidSelectConfiguration(): Event<void> {
return this._onDidSelectConfigurationName.event;
}
public getWorkspaceLaunch(): ILaunch {
if (this.contextService.getWorkbenchState() === WorkbenchState.WORKSPACE) {
return this.launches[this.launches.length - 1];
}
return undefined;
}
public selectConfiguration(launch?: ILaunch, name?: string, debugStarted?: boolean): void {
const previousLaunch = this._selectedLaunch;
const previousName = this._selectedName;
const previousLaunch = this.selectedLaunch;
const previousName = this.selectedName;
if (!launch) {
launch = this.selectedLaunch && this.selectedLaunch.getConfigurationNames().length ? this.selectedLaunch : first(this.launches, l => !!l.getConfigurationNames().length, this.launches.length ? this.launches[0] : undefined);
}
this._selectedLaunch = launch;
this.selectedLaunch = launch;
const names = launch ? launch.getConfigurationNames() : [];
if (name && names.indexOf(name) >= 0) {
this._selectedName = name;
this.selectedName = name;
}
if (names.indexOf(this.selectedName) === -1) {
this._selectedName = names.length ? names[0] : undefined;
this.selectedName = names.length ? names[0] : undefined;
}
if (this.selectedLaunch !== previousLaunch || this.selectedName !== previousName) {
@@ -378,10 +439,10 @@ export class ConfigurationManager implements IConfigurationManager {
}
}
public canSetBreakpointsIn(model: IModel): boolean {
public canSetBreakpointsIn(model: ITextModel): boolean {
const modeId = model ? model.getLanguageIdentifier().language : null;
if (!modeId || modeId === 'jsonc') {
// do not allow breakpoints in our settings files
if (!modeId || modeId === 'jsonc' || modeId === 'log') {
// do not allow breakpoints in our settings files and output
return false;
}
if (this.configurationService.getValue<IDebugConfiguration>('debug').allowBreakpointsEverywhere) {
@@ -403,6 +464,7 @@ export class ConfigurationManager implements IConfigurationManager {
}
const editor = this.editorService.getActiveEditor();
let candidates: Adapter[];
if (editor) {
const codeEditor = editor.getControl();
if (isCodeEditor(codeEditor)) {
@@ -412,10 +474,16 @@ export class ConfigurationManager implements IConfigurationManager {
if (adapters.length === 1) {
return TPromise.as(adapters[0]);
}
if (adapters.length > 1) {
candidates = adapters;
}
}
}
return this.quickOpenService.pick([...this.adapters.filter(a => a.hasInitialConfiguration() || a.hasConfigurationProvider), { label: 'More...', separator: { border: true } }], { placeHolder: nls.localize('selectDebug', "Select Environment") })
if (!candidates) {
candidates = this.adapters.filter(a => a.hasInitialConfiguration() || a.hasConfigurationProvider);
}
return this.quickOpenService.pick([...candidates, { label: 'More...', separator: { border: true } }], { placeHolder: nls.localize('selectDebug', "Select Environment") })
.then(picked => {
if (picked instanceof Adapter) {
return picked;
@@ -430,8 +498,8 @@ export class ConfigurationManager implements IConfigurationManager {
private store(): void {
this.storageService.store(DEBUG_SELECTED_CONFIG_NAME_KEY, this.selectedName, StorageScope.WORKSPACE);
if (this._selectedLaunch) {
this.storageService.store(DEBUG_SELECTED_ROOT, this._selectedLaunch.workspace.uri.toString(), StorageScope.WORKSPACE);
if (this.selectedLaunch) {
this.storageService.store(DEBUG_SELECTED_ROOT, this.selectedLaunch.uri.toString(), StorageScope.WORKSPACE);
}
}
@@ -446,15 +514,32 @@ class Launch implements ILaunch {
private configurationManager: ConfigurationManager,
public workspace: IWorkspaceFolder,
@IFileService private fileService: IFileService,
@IWorkbenchEditorService private editorService: IWorkbenchEditorService,
@IConfigurationService private configurationService: IConfigurationService,
@IConfigurationResolverService private configurationResolverService: IConfigurationResolverService
@IWorkbenchEditorService protected editorService: IWorkbenchEditorService,
@IConfigurationService protected configurationService: IConfigurationService,
@IConfigurationResolverService private configurationResolverService: IConfigurationResolverService,
@IWorkspaceContextService protected contextService: IWorkspaceContextService
) {
// noop
}
public get uri(): uri {
return this.workspace.uri.with({ path: paths.join(this.workspace.uri.path, '/.vscode/launch.json') });
}
public get name(): string {
return this.workspace.name;
}
public get hidden(): boolean {
return false;
}
protected getConfig(): IGlobalConfig {
return this.configurationService.inspect<IGlobalConfig>('launch', { resource: this.workspace.uri }).workspaceFolder;
}
public getCompound(name: string): ICompound {
const config = this.configurationService.getValue<IGlobalConfig>('launch', { resource: this.workspace.uri });
const config = this.getConfig();
if (!config || !config.compounds) {
return null;
}
@@ -462,13 +547,13 @@ class Launch implements ILaunch {
return config.compounds.filter(compound => compound.name === name).pop();
}
public getConfigurationNames(): string[] {
const config = this.configurationService.getValue<IGlobalConfig>('launch', { resource: this.workspace.uri });
public getConfigurationNames(includeCompounds = true): string[] {
const config = this.getConfig();
if (!config || !config.configurations || !Array.isArray(config.configurations)) {
return [];
} else {
const names = config.configurations.filter(cfg => cfg && typeof cfg.name === 'string').map(cfg => cfg.name);
if (names.length > 0 && config.compounds) {
if (includeCompounds && config.compounds) {
if (config.compounds) {
names.push(...config.compounds.filter(compound => typeof compound.name === 'string' && compound.configurations && compound.configurations.length)
.map(compound => compound.name));
@@ -480,7 +565,8 @@ class Launch implements ILaunch {
}
public getConfiguration(name: string): IConfig {
const config = objects.deepClone(this.configurationService.getValue<IGlobalConfig>('launch', { resource: this.workspace.uri }));
// We need to clone the configuration in order to be able to make changes to it #42198
const config = objects.deepClone(this.getConfig());
if (!config || !config.configurations) {
return null;
}
@@ -488,6 +574,18 @@ class Launch implements ILaunch {
return config.configurations.filter(config => config && config.name === name).shift();
}
protected getWorkspaceForResolving(): IWorkspaceFolder {
if (this.workspace) {
return this.workspace;
}
if (this.contextService.getWorkspace().folders.length === 1) {
return this.contextService.getWorkspace().folders[0];
}
return undefined;
}
public resolveConfiguration(config: IConfig): TPromise<IConfig> {
const result = objects.deepClone(config) as IConfig;
// Set operating system specific properties #1873
@@ -504,22 +602,18 @@ class Launch implements ILaunch {
// massage configuration attributes - append workspace path to relatvie paths, substitute variables in paths.
Object.keys(result).forEach(key => {
result[key] = this.configurationResolverService.resolveAny(this.workspace, result[key]);
result[key] = this.configurationResolverService.resolveAny(this.getWorkspaceForResolving(), result[key]);
});
const adapter = this.configurationManager.getAdapter(result.type);
return this.configurationResolverService.resolveInteractiveVariables(result, adapter ? adapter.variables : null);
}
public get uri(): uri {
return this.workspace.uri.with({ path: paths.join(this.workspace.uri.path, '/.vscode/launch.json') });
}
public openConfigFile(sideBySide: boolean, type?: string): TPromise<IEditor> {
const resource = this.uri;
let configFileCreated = false;
let pinned = false;
return this.fileService.resolveContent(resource).then(content => content, err => {
return this.fileService.resolveContent(resource).then(content => content.value, err => {
// launch.json not found: create one by collecting launch configs from debugConfigProviders
@@ -537,20 +631,20 @@ class Launch implements ILaunch {
return undefined;
}
configFileCreated = true;
pinned = true; // pin only if config file is created #8727
return this.fileService.updateContent(resource, content).then(() => {
// convert string into IContent; see #32135
return { value: content };
return content;
});
});
}).then(content => {
if (!content) {
return undefined;
}
const index = content.value.indexOf(`"${this.configurationManager.selectedName}"`);
const index = content.indexOf(`"${this.configurationManager.selectedConfiguration.name}"`);
let startLineNumber = 1;
for (let i = 0; i < index; i++) {
if (content.value.charAt(i) === '\n') {
if (content.charAt(i) === '\n') {
startLineNumber++;
}
}
@@ -561,7 +655,7 @@ class Launch implements ILaunch {
options: {
forceOpen: true,
selection,
pinned: configFileCreated, // pin only if config file is created #8727
pinned,
revealIfVisible: true
},
}, sideBySide);
@@ -570,3 +664,68 @@ class Launch implements ILaunch {
});
}
}
class WorkspaceLaunch extends Launch implements ILaunch {
constructor(
configurationManager: ConfigurationManager,
@IFileService fileService: IFileService,
@IWorkbenchEditorService editorService: IWorkbenchEditorService,
@IConfigurationService configurationService: IConfigurationService,
@IConfigurationResolverService configurationResolverService: IConfigurationResolverService,
@IWorkspaceContextService contextService: IWorkspaceContextService
) {
super(configurationManager, undefined, fileService, editorService, configurationService, configurationResolverService, contextService);
}
get uri(): uri {
return this.contextService.getWorkspace().configuration;
}
get name(): string {
return nls.localize('workspace', "workspace");
}
protected getConfig(): IGlobalConfig {
return this.configurationService.inspect<IGlobalConfig>('launch').workspace;
}
openConfigFile(sideBySide: boolean, type?: string): TPromise<IEditor> {
return this.editorService.openEditor({ resource: this.contextService.getWorkspace().configuration });
}
}
class UserLaunch extends Launch implements ILaunch {
constructor(
configurationManager: ConfigurationManager,
@IFileService fileService: IFileService,
@IWorkbenchEditorService editorService: IWorkbenchEditorService,
@IConfigurationService configurationService: IConfigurationService,
@IConfigurationResolverService configurationResolverService: IConfigurationResolverService,
@IPreferencesService private preferencesService: IPreferencesService,
@IWorkspaceContextService contextService: IWorkspaceContextService
) {
super(configurationManager, undefined, fileService, editorService, configurationService, configurationResolverService, contextService);
}
get uri(): uri {
return this.preferencesService.userSettingsResource;
}
get name(): string {
return nls.localize('user settings', "user settings");
}
public get hidden(): boolean {
return true;
}
protected getConfig(): IGlobalConfig {
return this.configurationService.inspect<IGlobalConfig>('launch').user;
}
openConfigFile(sideBySide: boolean, type?: string): TPromise<IEditor> {
return this.preferencesService.openGlobalSettings();
}
}