mirror of
https://github.com/microsoft/vscode.git
synced 2026-04-29 04:53:33 +01:00
Merge branch 'master' into joh/eol
This commit is contained in:
@@ -34,6 +34,7 @@ import { ExtHostLanguages } from 'vs/workbench/api/node/extHostLanguages';
|
||||
import { ExtHostLanguageFeatures } from 'vs/workbench/api/node/extHostLanguageFeatures';
|
||||
import { ExtHostApiCommands } from 'vs/workbench/api/node/extHostApiCommands';
|
||||
import { computeDiff } from 'vs/workbench/api/node/extHostFunctions';
|
||||
import { ExtHostTask } from 'vs/workbench/api/node/extHostTask';
|
||||
import * as extHostTypes from 'vs/workbench/api/node/extHostTypes';
|
||||
import URI from 'vs/base/common/uri';
|
||||
import Severity from 'vs/base/common/severity';
|
||||
@@ -111,6 +112,7 @@ export function createApiFactory(initData: IInitData, threadService: IThreadServ
|
||||
const extHostQuickOpen = col.define(ExtHostContext.ExtHostQuickOpen).set<ExtHostQuickOpen>(new ExtHostQuickOpen(threadService));
|
||||
const extHostTerminalService = col.define(ExtHostContext.ExtHostTerminalService).set<ExtHostTerminalService>(new ExtHostTerminalService(threadService));
|
||||
const extHostSCM = col.define(ExtHostContext.ExtHostSCM).set<ExtHostSCM>(new ExtHostSCM(threadService));
|
||||
const extHostTask = col.define(ExtHostContext.ExtHostTask).set<ExtHostTask>(new ExtHostTask(threadService));
|
||||
col.define(ExtHostContext.ExtHostExtensionService).set(extensionService);
|
||||
col.finish(false, threadService);
|
||||
|
||||
@@ -412,7 +414,10 @@ export function createApiFactory(initData: IInitData, threadService: IThreadServ
|
||||
},
|
||||
getConfiguration: (section?: string): vscode.WorkspaceConfiguration => {
|
||||
return extHostConfiguration.getConfiguration(section);
|
||||
}
|
||||
},
|
||||
registerTaskProvider: proposedApiFunction(extension, (provider: vscode.TaskProvider) => {
|
||||
return extHostTask.registerTaskProvider(extension, provider);
|
||||
})
|
||||
};
|
||||
|
||||
class SCM {
|
||||
@@ -494,7 +499,12 @@ export function createApiFactory(initData: IInitData, threadService: IThreadServ
|
||||
ViewColumn: extHostTypes.ViewColumn,
|
||||
WorkspaceEdit: extHostTypes.WorkspaceEdit,
|
||||
// functions
|
||||
computeDiff
|
||||
computeDiff,
|
||||
FileLocationKind: extHostTypes.FileLocationKind,
|
||||
ApplyToKind: extHostTypes.ApplyToKind,
|
||||
RevealKind: extHostTypes.RevealKind,
|
||||
ShellTask: extHostTypes.ShellTask,
|
||||
ProcessTask: extHostTypes.ProcessTask
|
||||
};
|
||||
};
|
||||
}
|
||||
|
||||
@@ -33,6 +33,7 @@ import { MainThreadTerminalService } from './mainThreadTerminalService';
|
||||
import { MainThreadWorkspace } from './mainThreadWorkspace';
|
||||
import { MainProcessExtensionService } from './mainThreadExtensionService';
|
||||
import { MainThreadFileSystemEventService } from './mainThreadFileSystemEventService';
|
||||
import { MainThreadTask } from './mainThreadTask';
|
||||
import { MainThreadSCM } from './mainThreadSCM';
|
||||
|
||||
// --- other interested parties
|
||||
@@ -86,6 +87,7 @@ export class ExtHostContribution implements IWorkbenchContribution {
|
||||
col.define(MainContext.MainThreadTerminalService).set(create(MainThreadTerminalService));
|
||||
col.define(MainContext.MainThreadWorkspace).set(create(MainThreadWorkspace));
|
||||
col.define(MainContext.MainThreadSCM).set(create(MainThreadSCM));
|
||||
col.define(MainContext.MainThreadTask).set(create(MainThreadTask));
|
||||
if (this.extensionService instanceof MainProcessExtensionService) {
|
||||
col.define(MainContext.MainProcessExtensionService).set(<MainProcessExtensionService>this.extensionService);
|
||||
}
|
||||
|
||||
@@ -34,10 +34,10 @@ import { IWorkspaceConfigurationValues } from 'vs/workbench/services/configurati
|
||||
|
||||
import { IPickOpenEntry, IPickOptions } from 'vs/platform/quickOpen/common/quickOpen';
|
||||
import { SaveReason } from 'vs/workbench/services/textfile/common/textfiles';
|
||||
import { IWorkspaceSymbol } from 'vs/workbench/parts/search/common/search';
|
||||
import { IApplyEditsOptions, IUndoStopOptions, TextEditorRevealType, ITextEditorConfigurationUpdate, IResolvedTextEditorConfiguration, ISelectionChangeEvent } from './mainThreadEditor';
|
||||
|
||||
import { InternalTreeExplorerNodeContent } from 'vs/workbench/parts/explorers/common/treeExplorerViewModel';
|
||||
import { TaskSet } from 'vs/workbench/parts/tasks/common/tasks';
|
||||
|
||||
export interface IEnvironment {
|
||||
enableProposedApi: boolean;
|
||||
@@ -237,6 +237,11 @@ export abstract class MainThreadWorkspaceShape {
|
||||
$applyWorkspaceEdit(edits: IResourceEdit[]): TPromise<boolean> { throw ni(); }
|
||||
}
|
||||
|
||||
export abstract class MainThreadTaskShape {
|
||||
$registerTaskProvider(handle: number): TPromise<any> { throw ni(); }
|
||||
$unregisterTaskProvider(handle: number): TPromise<any> { throw ni(); }
|
||||
}
|
||||
|
||||
export abstract class MainProcessExtensionServiceShape {
|
||||
$localShowMessage(severity: Severity, msg: string): void { throw ni(); }
|
||||
$onExtensionActivated(extensionId: string): void { throw ni(); }
|
||||
@@ -383,8 +388,8 @@ export abstract class ExtHostLanguageFeaturesShape {
|
||||
$provideDocumentFormattingEdits(handle: number, resource: URI, options: modes.FormattingOptions): TPromise<editorCommon.ISingleEditOperation[]> { throw ni(); }
|
||||
$provideDocumentRangeFormattingEdits(handle: number, resource: URI, range: editorCommon.IRange, options: modes.FormattingOptions): TPromise<editorCommon.ISingleEditOperation[]> { throw ni(); }
|
||||
$provideOnTypeFormattingEdits(handle: number, resource: URI, position: editorCommon.IPosition, ch: string, options: modes.FormattingOptions): TPromise<editorCommon.ISingleEditOperation[]> { throw ni(); }
|
||||
$provideWorkspaceSymbols(handle: number, search: string): TPromise<IWorkspaceSymbol[]> { throw ni(); }
|
||||
$resolveWorkspaceSymbol(handle: number, symbol: IWorkspaceSymbol): TPromise<IWorkspaceSymbol> { throw ni(); }
|
||||
$provideWorkspaceSymbols(handle: number, search: string): TPromise<modes.SymbolInformation[]> { throw ni(); }
|
||||
$resolveWorkspaceSymbol(handle: number, symbol: modes.SymbolInformation): TPromise<modes.SymbolInformation> { throw ni(); }
|
||||
$provideRenameEdits(handle: number, resource: URI, position: editorCommon.IPosition, newName: string): TPromise<modes.WorkspaceEdit> { throw ni(); }
|
||||
$provideCompletionItems(handle: number, resource: URI, position: editorCommon.IPosition): TPromise<modes.ISuggestResult> { throw ni(); }
|
||||
$resolveCompletionItem(handle: number, resource: URI, position: editorCommon.IPosition, suggestion: modes.ISuggestion): TPromise<modes.ISuggestion> { throw ni(); }
|
||||
@@ -411,6 +416,10 @@ export abstract class ExtHostSCMShape {
|
||||
$onInputBoxValueChange(value: string): TPromise<void> { throw ni(); }
|
||||
}
|
||||
|
||||
export abstract class ExtHostTaskShape {
|
||||
$provideTasks(handle: number): TPromise<TaskSet> { throw ni(); }
|
||||
}
|
||||
|
||||
// --- proxy identifiers
|
||||
|
||||
export const MainContext = {
|
||||
@@ -433,7 +442,8 @@ export const MainContext = {
|
||||
MainThreadTerminalService: createMainId<MainThreadTerminalServiceShape>('MainThreadTerminalService', MainThreadTerminalServiceShape),
|
||||
MainThreadWorkspace: createMainId<MainThreadWorkspaceShape>('MainThreadWorkspace', MainThreadWorkspaceShape),
|
||||
MainProcessExtensionService: createMainId<MainProcessExtensionServiceShape>('MainProcessExtensionService', MainProcessExtensionServiceShape),
|
||||
MainThreadSCM: createMainId<MainThreadSCMShape>('MainThreadSCM', MainThreadSCMShape)
|
||||
MainThreadSCM: createMainId<MainThreadSCMShape>('MainThreadSCM', MainThreadSCMShape),
|
||||
MainThreadTask: createMainId<MainThreadTaskShape>('MainThreadTask', MainThreadTaskShape)
|
||||
};
|
||||
|
||||
export const ExtHostContext = {
|
||||
@@ -451,5 +461,6 @@ export const ExtHostContext = {
|
||||
ExtHostQuickOpen: createExtId<ExtHostQuickOpenShape>('ExtHostQuickOpen', ExtHostQuickOpenShape),
|
||||
ExtHostExtensionService: createExtId<ExtHostExtensionServiceShape>('ExtHostExtensionService', ExtHostExtensionServiceShape),
|
||||
ExtHostTerminalService: createExtId<ExtHostTerminalServiceShape>('ExtHostTerminalService', ExtHostTerminalServiceShape),
|
||||
ExtHostSCM: createExtId<ExtHostSCMShape>('ExtHostSCM', ExtHostSCMShape)
|
||||
ExtHostSCM: createExtId<ExtHostSCMShape>('ExtHostSCM', ExtHostSCMShape),
|
||||
ExtHostTask: createExtId<ExtHostTaskShape>('ExtHostTask', ExtHostTaskShape)
|
||||
};
|
||||
|
||||
@@ -15,7 +15,7 @@ import * as modes from 'vs/editor/common/modes';
|
||||
import { ICommandHandlerDescription } from 'vs/platform/commands/common/commands';
|
||||
import { ExtHostCommands } from 'vs/workbench/api/node/extHostCommands';
|
||||
import { IOutline } from 'vs/editor/contrib/quickOpen/common/quickOpen';
|
||||
import { IWorkspaceSymbolProvider, IWorkspaceSymbol } from 'vs/workbench/parts/search/common/search';
|
||||
import { IWorkspaceSymbolProvider } from 'vs/workbench/parts/search/common/search';
|
||||
import { ICodeLensData } from 'vs/editor/contrib/codelens/common/codelens';
|
||||
|
||||
export class ExtHostApiCommands {
|
||||
@@ -171,18 +171,7 @@ export class ExtHostApiCommands {
|
||||
description: `
|
||||
Render the html of the resource in an editor view.
|
||||
|
||||
Links contained in the document will be handled by VS Code whereby it supports \`file\`-resources and
|
||||
[virtual](https://github.com/Microsoft/vscode/blob/master/src/vs/vscode.d.ts#L3295)-resources
|
||||
as well as triggering commands using the \`command\`-scheme. Use the query part of a command-uri to pass along JSON-encoded
|
||||
arguments - note that URL-encoding must be applied. The snippet below defines a command-link that calls the _previewHtml_
|
||||
command and passes along an uri:
|
||||
\`\`\`
|
||||
let href = encodeURI('command:vscode.previewHtml?' + JSON.stringify(someUri));
|
||||
let html = '<a href="' + href + '">Show Resource...</a>.';
|
||||
\`\`\`
|
||||
|
||||
The body element of the displayed html is dynamically annotated with one of the following css classes in order to
|
||||
communicate the kind of color theme vscode is currently using: \`vscode-light\`, \`vscode-dark\`, or \`vscode-high-contrast\'.
|
||||
See [working with the html preview](https://code.visualstudio.com/docs/extensionAPI/vscode-api-commands#working-with-the-html-preview) for more information about the html preview's intergration with the editor and for best practices for extension authors.
|
||||
`,
|
||||
args: [
|
||||
{ name: 'uri', description: 'Uri of the resource to preview.', constraint: value => value instanceof URI || typeof value === 'string' },
|
||||
@@ -250,7 +239,7 @@ export class ExtHostApiCommands {
|
||||
* @return A promise that resolves to an array of symbol information.
|
||||
*/
|
||||
private _executeWorkspaceSymbolProvider(query: string): Thenable<types.SymbolInformation[]> {
|
||||
return this._commands.executeCommand<[IWorkspaceSymbolProvider, IWorkspaceSymbol[]][]>('_executeWorkspaceSymbolProvider', { query }).then(value => {
|
||||
return this._commands.executeCommand<[IWorkspaceSymbolProvider, modes.SymbolInformation[]][]>('_executeWorkspaceSymbolProvider', { query }).then(value => {
|
||||
const result: types.SymbolInformation[] = [];
|
||||
if (Array.isArray(value)) {
|
||||
for (let tuple of value) {
|
||||
@@ -382,7 +371,7 @@ export class ExtHostApiCommands {
|
||||
};
|
||||
return this._commands.executeCommand<IOutline>('_executeDocumentSymbolProvider', args).then(value => {
|
||||
if (value && Array.isArray(value.entries)) {
|
||||
return value.entries.map(typeConverters.SymbolInformation.fromOutlineEntry);
|
||||
return value.entries.map(typeConverters.toSymbolInformation);
|
||||
}
|
||||
return undefined;
|
||||
});
|
||||
|
||||
@@ -4,6 +4,7 @@
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
'use strict';
|
||||
|
||||
import { ok } from 'vs/base/common/assert';
|
||||
import { regExpLeadsToEndlessLoop } from 'vs/base/common/strings';
|
||||
import { MirrorModel2 } from 'vs/editor/common/model/mirrorModel2';
|
||||
import URI from 'vs/base/common/uri';
|
||||
@@ -12,6 +13,7 @@ import * as vscode from 'vscode';
|
||||
import { getWordAtText, ensureValidWordDefinition } from 'vs/editor/common/model/wordHelper';
|
||||
import { MainThreadDocumentsShape } from './extHost.protocol';
|
||||
import { ITextSource } from 'vs/editor/common/model/textSource';
|
||||
import { TPromise } from 'vs/base/common/winjs.base';
|
||||
|
||||
const _modeId2WordDefinition = new Map<string, RegExp>();
|
||||
export function setWordDefinitionFor(modeId: string, wordDefinition: RegExp): void {
|
||||
@@ -26,23 +28,26 @@ export class ExtHostDocumentData extends MirrorModel2 {
|
||||
private _proxy: MainThreadDocumentsShape;
|
||||
private _languageId: string;
|
||||
private _isDirty: boolean;
|
||||
private _textLines: vscode.TextLine[];
|
||||
private _document: vscode.TextDocument;
|
||||
private _textLines: vscode.TextLine[] = [];
|
||||
private _isDisposed: boolean = false;
|
||||
|
||||
constructor(proxy: MainThreadDocumentsShape, uri: URI, lines: string[], eol: string,
|
||||
languageId: string, versionId: number, isDirty: boolean) {
|
||||
|
||||
languageId: string, versionId: number, isDirty: boolean
|
||||
) {
|
||||
super(uri, lines, eol, versionId);
|
||||
this._proxy = proxy;
|
||||
this._languageId = languageId;
|
||||
this._isDirty = isDirty;
|
||||
this._textLines = [];
|
||||
}
|
||||
|
||||
dispose(): void {
|
||||
this._textLines.length = 0;
|
||||
// we don't really dispose documents but let
|
||||
// extensions still read from them. some
|
||||
// operations, live saving, will now error tho
|
||||
ok(!this._isDisposed);
|
||||
this._isDisposed = true;
|
||||
this._isDirty = false;
|
||||
super.dispose();
|
||||
}
|
||||
|
||||
equalLines({ lines }: ITextSource): boolean {
|
||||
@@ -68,31 +73,40 @@ export class ExtHostDocumentData extends MirrorModel2 {
|
||||
get languageId() { return data._languageId; },
|
||||
get version() { return data._versionId; },
|
||||
get isDirty() { return data._isDirty; },
|
||||
save() { return data._proxy.$trySaveDocument(data._uri); },
|
||||
save() { return data._save(); },
|
||||
getText(range?) { return range ? data._getTextInRange(range) : data.getText(); },
|
||||
get eol() { return data._eol === '\n' ? EndOfLine.LF : EndOfLine.CRLF; },
|
||||
get lineCount() { return data._lines.length; },
|
||||
lineAt(lineOrPos) { return data.lineAt(lineOrPos); },
|
||||
offsetAt(pos) { return data.offsetAt(pos); },
|
||||
positionAt(offset) { return data.positionAt(offset); },
|
||||
validateRange(ran) { return data.validateRange(ran); },
|
||||
validatePosition(pos) { return data.validatePosition(pos); },
|
||||
getWordRangeAtPosition(pos, regexp?) { return data.getWordRangeAtPosition(pos, regexp); }
|
||||
lineAt(lineOrPos) { return data._lineAt(lineOrPos); },
|
||||
offsetAt(pos) { return data._offsetAt(pos); },
|
||||
positionAt(offset) { return data._positionAt(offset); },
|
||||
validateRange(ran) { return data._validateRange(ran); },
|
||||
validatePosition(pos) { return data._validatePosition(pos); },
|
||||
getWordRangeAtPosition(pos, regexp?) { return data._getWordRangeAtPosition(pos, regexp); }
|
||||
};
|
||||
}
|
||||
return this._document;
|
||||
return Object.freeze(this._document);
|
||||
}
|
||||
|
||||
_acceptLanguageId(newLanguageId: string): void {
|
||||
ok(!this._isDisposed);
|
||||
this._languageId = newLanguageId;
|
||||
}
|
||||
|
||||
_acceptIsDirty(isDirty: boolean): void {
|
||||
ok(!this._isDisposed);
|
||||
this._isDirty = isDirty;
|
||||
}
|
||||
|
||||
private _save(): TPromise<boolean> {
|
||||
if (this._isDisposed) {
|
||||
return TPromise.wrapError<boolean>('Document has been closed');
|
||||
}
|
||||
return this._proxy.$trySaveDocument(this._uri);
|
||||
}
|
||||
|
||||
private _getTextInRange(_range: vscode.Range): string {
|
||||
let range = this.validateRange(_range);
|
||||
let range = this._validateRange(_range);
|
||||
|
||||
if (range.isEmpty) {
|
||||
return '';
|
||||
@@ -116,7 +130,7 @@ export class ExtHostDocumentData extends MirrorModel2 {
|
||||
return resultLines.join(lineEnding);
|
||||
}
|
||||
|
||||
lineAt(lineOrPosition: number | vscode.Position): vscode.TextLine {
|
||||
private _lineAt(lineOrPosition: number | vscode.Position): vscode.TextLine {
|
||||
|
||||
let line: number;
|
||||
if (lineOrPosition instanceof Position) {
|
||||
@@ -154,13 +168,13 @@ export class ExtHostDocumentData extends MirrorModel2 {
|
||||
return result;
|
||||
}
|
||||
|
||||
offsetAt(position: vscode.Position): number {
|
||||
position = this.validatePosition(position);
|
||||
private _offsetAt(position: vscode.Position): number {
|
||||
position = this._validatePosition(position);
|
||||
this._ensureLineStarts();
|
||||
return this._lineStarts.getAccumulatedValue(position.line - 1) + position.character;
|
||||
}
|
||||
|
||||
positionAt(offset: number): vscode.Position {
|
||||
private _positionAt(offset: number): vscode.Position {
|
||||
offset = Math.floor(offset);
|
||||
offset = Math.max(0, offset);
|
||||
|
||||
@@ -175,13 +189,13 @@ export class ExtHostDocumentData extends MirrorModel2 {
|
||||
|
||||
// ---- range math
|
||||
|
||||
validateRange(range: vscode.Range): vscode.Range {
|
||||
private _validateRange(range: vscode.Range): vscode.Range {
|
||||
if (!(range instanceof Range)) {
|
||||
throw new Error('Invalid argument');
|
||||
}
|
||||
|
||||
let start = this.validatePosition(range.start);
|
||||
let end = this.validatePosition(range.end);
|
||||
let start = this._validatePosition(range.start);
|
||||
let end = this._validatePosition(range.end);
|
||||
|
||||
if (start === range.start && end === range.end) {
|
||||
return range;
|
||||
@@ -189,7 +203,7 @@ export class ExtHostDocumentData extends MirrorModel2 {
|
||||
return new Range(start.line, start.character, end.line, end.character);
|
||||
}
|
||||
|
||||
validatePosition(position: vscode.Position): vscode.Position {
|
||||
private _validatePosition(position: vscode.Position): vscode.Position {
|
||||
if (!(position instanceof Position)) {
|
||||
throw new Error('Invalid argument');
|
||||
}
|
||||
@@ -225,8 +239,8 @@ export class ExtHostDocumentData extends MirrorModel2 {
|
||||
return new Position(line, character);
|
||||
}
|
||||
|
||||
getWordRangeAtPosition(_position: vscode.Position, regexp?: RegExp): vscode.Range {
|
||||
let position = this.validatePosition(_position);
|
||||
private _getWordRangeAtPosition(_position: vscode.Position, regexp?: RegExp): vscode.Range {
|
||||
let position = this._validatePosition(_position);
|
||||
if (!regexp || regExpLeadsToEndlessLoop(regexp)) {
|
||||
regexp = getWordDefinitionFor(this._languageId);
|
||||
}
|
||||
|
||||
@@ -17,7 +17,7 @@ import { ExtHostHeapService } from 'vs/workbench/api/node/extHostHeapService';
|
||||
import { ExtHostDocuments } from 'vs/workbench/api/node/extHostDocuments';
|
||||
import { ExtHostCommands, CommandsConverter } from 'vs/workbench/api/node/extHostCommands';
|
||||
import { ExtHostDiagnostics } from 'vs/workbench/api/node/extHostDiagnostics';
|
||||
import { IWorkspaceSymbolProvider, IWorkspaceSymbol } from 'vs/workbench/parts/search/common/search';
|
||||
import { IWorkspaceSymbolProvider } from 'vs/workbench/parts/search/common/search';
|
||||
import { asWinJsPromise } from 'vs/base/common/async';
|
||||
import { MainContext, MainThreadLanguageFeaturesShape, ExtHostLanguageFeaturesShape, ObjectIdentifier } from './extHost.protocol';
|
||||
import { regExpLeadsToEndlessLoop } from 'vs/base/common/strings';
|
||||
@@ -38,7 +38,7 @@ class OutlineAdapter {
|
||||
let doc = this._documents.getDocumentData(resource).document;
|
||||
return asWinJsPromise(token => this._provider.provideDocumentSymbols(doc, token)).then(value => {
|
||||
if (Array.isArray(value)) {
|
||||
return value.map(TypeConverters.SymbolInformation.toOutlineEntry);
|
||||
return value.map(TypeConverters.fromSymbolInformation);
|
||||
}
|
||||
return undefined;
|
||||
});
|
||||
@@ -311,7 +311,7 @@ class DocumentFormattingAdapter {
|
||||
|
||||
provideDocumentFormattingEdits(resource: URI, options: modes.FormattingOptions): TPromise<ISingleEditOperation[]> {
|
||||
|
||||
const {document} = this._documents.getDocumentData(resource);
|
||||
const { document } = this._documents.getDocumentData(resource);
|
||||
|
||||
return asWinJsPromise(token => this._provider.provideDocumentFormattingEdits(document, <any>options, token)).then(value => {
|
||||
if (Array.isArray(value)) {
|
||||
@@ -334,7 +334,7 @@ class RangeFormattingAdapter {
|
||||
|
||||
provideDocumentRangeFormattingEdits(resource: URI, range: IRange, options: modes.FormattingOptions): TPromise<ISingleEditOperation[]> {
|
||||
|
||||
const {document} = this._documents.getDocumentData(resource);
|
||||
const { document } = this._documents.getDocumentData(resource);
|
||||
const ran = TypeConverters.toRange(range);
|
||||
|
||||
return asWinJsPromise(token => this._provider.provideDocumentRangeFormattingEdits(document, ran, <any>options, token)).then(value => {
|
||||
@@ -360,7 +360,7 @@ class OnTypeFormattingAdapter {
|
||||
|
||||
provideOnTypeFormattingEdits(resource: URI, position: IPosition, ch: string, options: modes.FormattingOptions): TPromise<ISingleEditOperation[]> {
|
||||
|
||||
const {document} = this._documents.getDocumentData(resource);
|
||||
const { document } = this._documents.getDocumentData(resource);
|
||||
const pos = TypeConverters.toPosition(position);
|
||||
|
||||
return asWinJsPromise(token => this._provider.provideOnTypeFormattingEdits(document, pos, ch, <any>options, token)).then(value => {
|
||||
@@ -383,7 +383,7 @@ class NavigateTypeAdapter implements IWorkspaceSymbolProvider {
|
||||
this._heapService = heapService;
|
||||
}
|
||||
|
||||
provideWorkspaceSymbols(search: string): TPromise<IWorkspaceSymbol[]> {
|
||||
provideWorkspaceSymbols(search: string): TPromise<modes.SymbolInformation[]> {
|
||||
|
||||
return asWinJsPromise(token => this._provider.provideWorkspaceSymbols(search, token)).then(value => {
|
||||
if (Array.isArray(value)) {
|
||||
@@ -397,7 +397,7 @@ class NavigateTypeAdapter implements IWorkspaceSymbolProvider {
|
||||
});
|
||||
}
|
||||
|
||||
resolveWorkspaceSymbol(item: IWorkspaceSymbol): TPromise<IWorkspaceSymbol> {
|
||||
resolveWorkspaceSymbol(item: modes.SymbolInformation): TPromise<modes.SymbolInformation> {
|
||||
|
||||
if (typeof this._provider.resolveWorkspaceSymbol !== 'function') {
|
||||
return TPromise.as(item);
|
||||
@@ -889,11 +889,11 @@ export class ExtHostLanguageFeatures extends ExtHostLanguageFeaturesShape {
|
||||
return this._createDisposable(handle);
|
||||
}
|
||||
|
||||
$provideWorkspaceSymbols(handle: number, search: string): TPromise<IWorkspaceSymbol[]> {
|
||||
$provideWorkspaceSymbols(handle: number, search: string): TPromise<modes.SymbolInformation[]> {
|
||||
return this._withAdapter(handle, NavigateTypeAdapter, adapter => adapter.provideWorkspaceSymbols(search));
|
||||
}
|
||||
|
||||
$resolveWorkspaceSymbol(handle: number, symbol: IWorkspaceSymbol): TPromise<IWorkspaceSymbol> {
|
||||
$resolveWorkspaceSymbol(handle: number, symbol: modes.SymbolInformation): TPromise<modes.SymbolInformation> {
|
||||
return this._withAdapter(handle, NavigateTypeAdapter, adapter => adapter.resolveWorkspaceSymbol(symbol));
|
||||
}
|
||||
|
||||
@@ -960,7 +960,7 @@ export class ExtHostLanguageFeatures extends ExtHostLanguageFeaturesShape {
|
||||
// --- configuration
|
||||
|
||||
setLanguageConfiguration(languageId: string, configuration: vscode.LanguageConfiguration): vscode.Disposable {
|
||||
let {wordPattern} = configuration;
|
||||
let { wordPattern } = configuration;
|
||||
|
||||
// check for a valid word pattern
|
||||
if (wordPattern && regExpLeadsToEndlessLoop(wordPattern)) {
|
||||
|
||||
479
src/vs/workbench/api/node/extHostTask.ts
Normal file
479
src/vs/workbench/api/node/extHostTask.ts
Normal file
@@ -0,0 +1,479 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
'use strict';
|
||||
|
||||
import { TPromise } from 'vs/base/common/winjs.base';
|
||||
import * as UUID from 'vs/base/common/uuid';
|
||||
import { asWinJsPromise } from 'vs/base/common/async';
|
||||
|
||||
import * as Problems from 'vs/platform/markers/common/problemMatcher';
|
||||
import { IExtensionDescription } from 'vs/platform/extensions/common/extensions';
|
||||
import * as TaskSystem from 'vs/workbench/parts/tasks/common/tasks';
|
||||
|
||||
import { IThreadService } from 'vs/workbench/services/thread/common/threadService';
|
||||
import { MainContext, MainThreadTaskShape, ExtHostTaskShape } from 'vs/workbench/api/node/extHost.protocol';
|
||||
import { fromDiagnosticSeverity } from 'vs/workbench/api/node/extHostTypeConverters';
|
||||
|
||||
import * as types from 'vs/workbench/api/node/extHostTypes';
|
||||
import * as vscode from 'vscode';
|
||||
|
||||
interface StringMap<V> {
|
||||
[key: string]: V;
|
||||
}
|
||||
|
||||
namespace ProblemPattern {
|
||||
export function from(value: vscode.ProblemPattern | vscode.MultiLineProblemPattern): Problems.ProblemPattern | Problems.MultiLineProblemPattern {
|
||||
if (value === void 0 || value === null) {
|
||||
return undefined;
|
||||
}
|
||||
if (Array.isArray(value)) {
|
||||
let result: Problems.ProblemPattern[] = [];
|
||||
for (let pattern of value) {
|
||||
let converted = fromSingle(pattern);
|
||||
if (!converted) {
|
||||
return undefined;
|
||||
}
|
||||
result.push(converted);
|
||||
}
|
||||
return result;
|
||||
} else {
|
||||
return fromSingle(value);
|
||||
}
|
||||
}
|
||||
|
||||
function copyProperty(target: Problems.ProblemPattern, source: vscode.ProblemPattern, tk: keyof Problems.ProblemPattern) {
|
||||
let sk: keyof vscode.ProblemPattern = tk;
|
||||
let value = source[sk];
|
||||
if (typeof value === 'number') {
|
||||
target[tk] = value;
|
||||
}
|
||||
}
|
||||
|
||||
function getValue(value: number, defaultValue: number): number {
|
||||
if (value !== void 0 && value === null) {
|
||||
return value;
|
||||
}
|
||||
return defaultValue;
|
||||
}
|
||||
|
||||
function fromSingle(problemPattern: vscode.ProblemPattern): Problems.ProblemPattern {
|
||||
if (problemPattern === void 0 || problemPattern === null || !(problemPattern.regexp instanceof RegExp)) {
|
||||
return undefined;
|
||||
}
|
||||
let result: Problems.ProblemPattern = {
|
||||
regexp: problemPattern.regexp
|
||||
};
|
||||
copyProperty(result, problemPattern, 'file');
|
||||
copyProperty(result, problemPattern, 'location');
|
||||
copyProperty(result, problemPattern, 'line');
|
||||
copyProperty(result, problemPattern, 'character');
|
||||
copyProperty(result, problemPattern, 'endLine');
|
||||
copyProperty(result, problemPattern, 'endCharacter');
|
||||
copyProperty(result, problemPattern, 'severity');
|
||||
copyProperty(result, problemPattern, 'code');
|
||||
copyProperty(result, problemPattern, 'message');
|
||||
if (problemPattern.loop === true || problemPattern.loop === false) {
|
||||
result.loop = problemPattern.loop;
|
||||
}
|
||||
if (result.location) {
|
||||
result.file = getValue(result.file, 1);
|
||||
result.message = getValue(result.message, 0);
|
||||
} else {
|
||||
result.file = getValue(result.file, 1);
|
||||
result.line = getValue(result.line, 2);
|
||||
result.character = getValue(result.character, 3);
|
||||
result.message = getValue(result.message, 0);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
namespace ApplyTo {
|
||||
export function from(value: vscode.ApplyToKind): Problems.ApplyToKind {
|
||||
if (value === void 0 || value === null) {
|
||||
return Problems.ApplyToKind.allDocuments;
|
||||
}
|
||||
switch (value) {
|
||||
case types.ApplyToKind.OpenDocuments:
|
||||
return Problems.ApplyToKind.openDocuments;
|
||||
case types.ApplyToKind.ClosedDocuments:
|
||||
return Problems.ApplyToKind.closedDocuments;
|
||||
}
|
||||
return Problems.ApplyToKind.allDocuments;
|
||||
}
|
||||
}
|
||||
|
||||
namespace FileLocation {
|
||||
export function from(value: vscode.FileLocationKind | string): { kind: Problems.FileLocationKind; prefix?: string } {
|
||||
if (value === void 0 || value === null) {
|
||||
return { kind: Problems.FileLocationKind.Auto };
|
||||
}
|
||||
if (typeof value === 'string') {
|
||||
return { kind: Problems.FileLocationKind.Relative, prefix: value };
|
||||
}
|
||||
switch (value) {
|
||||
case types.FileLocationKind.Absolute:
|
||||
return { kind: Problems.FileLocationKind.Absolute };
|
||||
case types.FileLocationKind.Relative:
|
||||
return { kind: Problems.FileLocationKind.Relative, prefix: '${workspaceRoot}' };
|
||||
}
|
||||
return { kind: Problems.FileLocationKind.Auto };
|
||||
}
|
||||
}
|
||||
|
||||
namespace WatchingPattern {
|
||||
export function from(value: RegExp | vscode.BackgroundPattern): Problems.WatchingPattern {
|
||||
if (value === void 0 || value === null) {
|
||||
return undefined;
|
||||
}
|
||||
if (value instanceof RegExp) {
|
||||
return { regexp: value };
|
||||
}
|
||||
if (!(value.regexp instanceof RegExp)) {
|
||||
return undefined;
|
||||
}
|
||||
let result: Problems.WatchingPattern = {
|
||||
regexp: value.regexp
|
||||
};
|
||||
if (typeof value.file === 'number') {
|
||||
result.file = value.file;
|
||||
}
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
namespace WathingMatcher {
|
||||
export function from(value: vscode.BackgroundMonitor): Problems.WatchingMatcher {
|
||||
if (value === void 0 || value === null) {
|
||||
return undefined;
|
||||
}
|
||||
let result: Problems.WatchingMatcher = {
|
||||
activeOnStart: !!value.activeOnStart,
|
||||
beginsPattern: WatchingPattern.from(value.beginsPattern),
|
||||
endsPattern: WatchingPattern.from(value.endsPattern)
|
||||
};
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
namespace ProblemMatcher {
|
||||
export function from(values: vscode.ProblemMatcher[]): Problems.ProblemMatcher[] {
|
||||
if (values === void 0 || values === null) {
|
||||
return undefined;
|
||||
}
|
||||
let result: Problems.ProblemMatcher[];
|
||||
for (let value of values) {
|
||||
let converted = fromSingle(value);
|
||||
if (converted) {
|
||||
result.push(converted);
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
function fromSingle(problemMatcher: vscode.ProblemMatcher): Problems.ProblemMatcher {
|
||||
if (problemMatcher === void 0 || problemMatcher === null) {
|
||||
return undefined;
|
||||
}
|
||||
|
||||
let location = FileLocation.from(problemMatcher.fileLocation);
|
||||
let result: Problems.ProblemMatcher = {
|
||||
owner: typeof problemMatcher.owner === 'string' ? problemMatcher.owner : UUID.generateUuid(),
|
||||
applyTo: ApplyTo.from(problemMatcher.applyTo),
|
||||
fileLocation: location.kind,
|
||||
filePrefix: location.prefix,
|
||||
pattern: ProblemPattern.from(problemMatcher.pattern),
|
||||
severity: fromDiagnosticSeverity(problemMatcher.severity),
|
||||
|
||||
};
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
namespace RevealKind {
|
||||
export function from(value: vscode.RevealKind): TaskSystem.ShowOutput {
|
||||
if (value === void 0 || value === null) {
|
||||
return TaskSystem.ShowOutput.Always;
|
||||
}
|
||||
switch (value) {
|
||||
case types.RevealKind.Silent:
|
||||
return TaskSystem.ShowOutput.Silent;
|
||||
case types.RevealKind.Never:
|
||||
return TaskSystem.ShowOutput.Never;
|
||||
}
|
||||
return TaskSystem.ShowOutput.Always;
|
||||
}
|
||||
}
|
||||
|
||||
namespace TerminalBehaviour {
|
||||
export function from(value: vscode.TerminalBehaviour): { showOutput: TaskSystem.ShowOutput, echo: boolean } {
|
||||
if (value === void 0 || value === null) {
|
||||
return { showOutput: TaskSystem.ShowOutput.Always, echo: false };
|
||||
}
|
||||
return { showOutput: RevealKind.from(value.reveal), echo: !!value.echo };
|
||||
}
|
||||
}
|
||||
|
||||
namespace Strings {
|
||||
export function from(value: string[]): string[] {
|
||||
if (value === void 0 || value === null) {
|
||||
return undefined;
|
||||
}
|
||||
for (let element of value) {
|
||||
if (typeof element !== 'string') {
|
||||
return [];
|
||||
}
|
||||
}
|
||||
return value;
|
||||
}
|
||||
}
|
||||
|
||||
namespace CommandOptions {
|
||||
export function from(value: { cwd?: string; env?: { [key: string]: string; } }): TaskSystem.CommandOptions {
|
||||
if (value === void 0 || value === null) {
|
||||
return undefined;
|
||||
}
|
||||
let result: TaskSystem.CommandOptions = {
|
||||
};
|
||||
if (typeof value.cwd === 'string') {
|
||||
result.cwd = value.cwd;
|
||||
}
|
||||
if (value.env) {
|
||||
result.env = Object.create(null);
|
||||
Object.keys(value.env).forEach(key => {
|
||||
let envValue = value.env[key];
|
||||
if (typeof envValue === 'string') {
|
||||
result.env[key] = envValue;
|
||||
}
|
||||
});
|
||||
}
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
namespace ShellConfiguration {
|
||||
export function from(value: { executable?: string, args?: string[] }): boolean | TaskSystem.ShellConfiguration {
|
||||
if (value === void 0 || value === null || typeof value.executable !== 'string') {
|
||||
return true;
|
||||
}
|
||||
|
||||
let result: TaskSystem.ShellConfiguration = {
|
||||
executable: value.executable,
|
||||
args: Strings.from(value.args)
|
||||
};
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
namespace Tasks {
|
||||
|
||||
export function from(tasks: vscode.Task[], uuidMap: UUIDMap): TaskSystem.Task[] {
|
||||
if (tasks === void 0 || tasks === null) {
|
||||
return [];
|
||||
}
|
||||
let result: TaskSystem.Task[] = [];
|
||||
try {
|
||||
uuidMap.start();
|
||||
for (let task of tasks) {
|
||||
let converted = fromSingle(task, uuidMap);
|
||||
if (converted) {
|
||||
result.push(converted);
|
||||
}
|
||||
}
|
||||
} finally {
|
||||
uuidMap.finish();
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
function fromSingle(task: vscode.Task, uuidMap: UUIDMap): TaskSystem.Task {
|
||||
if (typeof task.name !== 'string' || typeof task.identifier !== 'string') {
|
||||
return undefined;
|
||||
}
|
||||
let command: TaskSystem.CommandConfiguration;
|
||||
if (task instanceof types.ProcessTask) {
|
||||
command = getProcessCommand(task);
|
||||
} else if (task instanceof types.ShellTask) {
|
||||
command = getShellCommand(task);
|
||||
} else {
|
||||
return undefined;
|
||||
}
|
||||
if (command === void 0) {
|
||||
return undefined;
|
||||
}
|
||||
let behaviour = TerminalBehaviour.from(task.terminal);
|
||||
command.echo = behaviour.echo;
|
||||
let result: TaskSystem.Task = {
|
||||
_id: uuidMap.getUUID(task.identifier),
|
||||
name: task.name,
|
||||
identifier: task.identifier,
|
||||
command: command,
|
||||
showOutput: behaviour.showOutput,
|
||||
isBackground: !!task.isBackground,
|
||||
suppressTaskName: true,
|
||||
problemMatchers: ProblemMatcher.from(task.problemMatchers)
|
||||
};
|
||||
return result;
|
||||
}
|
||||
|
||||
function getProcessCommand(value: vscode.ProcessTask): TaskSystem.CommandConfiguration {
|
||||
if (typeof value.process !== 'string') {
|
||||
return undefined;
|
||||
}
|
||||
let result: TaskSystem.CommandConfiguration = {
|
||||
name: value.process,
|
||||
args: Strings.from(value.args),
|
||||
isShellCommand: false,
|
||||
echo: false,
|
||||
};
|
||||
if (value.options) {
|
||||
result.options = CommandOptions.from(value.options);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
function getShellCommand(value: vscode.ShellTask): TaskSystem.CommandConfiguration {
|
||||
if (typeof value.commandLine !== 'string') {
|
||||
return undefined;
|
||||
}
|
||||
let result: TaskSystem.CommandConfiguration = {
|
||||
name: value.commandLine,
|
||||
isShellCommand: ShellConfiguration.from(value.options),
|
||||
echo: false
|
||||
};
|
||||
if (value.options) {
|
||||
result.options = CommandOptions.from(value.options);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
class UUIDMap {
|
||||
|
||||
private _map: StringMap<string>;
|
||||
private _unused: StringMap<boolean>;
|
||||
|
||||
constructor() {
|
||||
this._map = Object.create(null);
|
||||
}
|
||||
|
||||
public start(): void {
|
||||
this._unused = Object.create(null);
|
||||
Object.keys(this._map).forEach(key => this._unused[key] = true);
|
||||
}
|
||||
|
||||
public getUUID(identifier: string): string {
|
||||
delete this._unused[identifier];
|
||||
let result = this._map[identifier];
|
||||
if (result) {
|
||||
return result;
|
||||
}
|
||||
result = UUID.generateUuid();
|
||||
this._map[identifier] = result;
|
||||
return result;
|
||||
}
|
||||
|
||||
public finish(): void {
|
||||
Object.keys(this._unused).forEach(key => delete this._map[key]);
|
||||
this._unused = null;
|
||||
}
|
||||
}
|
||||
|
||||
namespace TaskSet {
|
||||
|
||||
const idMaps: Map<string, UUIDMap> = new Map<string, UUIDMap>();
|
||||
|
||||
function getUUIDMap(extensionId: string): UUIDMap {
|
||||
let result = idMaps.get(extensionId);
|
||||
if (result) {
|
||||
return result;
|
||||
}
|
||||
result = new UUIDMap();
|
||||
idMaps.set(extensionId, result);
|
||||
return result;
|
||||
}
|
||||
|
||||
export function from(extension: IExtensionDescription, value: vscode.TaskSet): TaskSystem.TaskSet {
|
||||
if (value === void 0 || value === null || !Array.isArray(value.tasks)) {
|
||||
return { tasks: Object.create(null) };
|
||||
}
|
||||
|
||||
let tasks = Tasks.from(value.tasks, getUUIDMap(extension.id));
|
||||
let buildTasks: string[];
|
||||
let testTasks: string[];
|
||||
if (value.buildTasks || value.testTasks) {
|
||||
let map: Map<string, TaskSystem.Task> = new Map<string, TaskSystem.Task>();
|
||||
tasks.forEach(task => map.set(task.identifier, task));
|
||||
if (Array.isArray(value.buildTasks)) {
|
||||
buildTasks = [];
|
||||
for (let elem of value.buildTasks) {
|
||||
if (typeof elem === 'string' && map.has(elem)) {
|
||||
buildTasks.push(map.get(elem)._id);
|
||||
}
|
||||
}
|
||||
}
|
||||
if (Array.isArray(value.testTasks)) {
|
||||
testTasks = [];
|
||||
for (let elem of value.testTasks) {
|
||||
if (typeof elem === 'string' && map.has(elem)) {
|
||||
testTasks.push(map.get(elem)._id);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return {
|
||||
tasks,
|
||||
buildTasks,
|
||||
testTasks
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
interface HandlerData {
|
||||
provider: vscode.TaskProvider;
|
||||
extension: IExtensionDescription;
|
||||
}
|
||||
|
||||
export class ExtHostTask extends ExtHostTaskShape {
|
||||
|
||||
private _proxy: MainThreadTaskShape;
|
||||
private _handleCounter: number;
|
||||
private _handlers: Map<number, HandlerData>;
|
||||
|
||||
constructor(threadService: IThreadService) {
|
||||
super();
|
||||
this._proxy = threadService.get(MainContext.MainThreadTask);
|
||||
this._handleCounter = 0;
|
||||
this._handlers = new Map<number, HandlerData>();
|
||||
};
|
||||
|
||||
public registerTaskProvider(extension: IExtensionDescription, provider: vscode.TaskProvider): vscode.Disposable {
|
||||
if (!provider) {
|
||||
return new types.Disposable(() => { });
|
||||
}
|
||||
let handle = this.nextHandle();
|
||||
this._handlers.set(handle, { provider, extension });
|
||||
this._proxy.$registerTaskProvider(handle);
|
||||
return new types.Disposable(() => {
|
||||
this._handlers.delete(handle);
|
||||
this._proxy.$unregisterTaskProvider(handle);
|
||||
});
|
||||
}
|
||||
|
||||
public $provideTasks(handle: number): TPromise<TaskSystem.TaskSet> {
|
||||
let handler = this._handlers.get(handle);
|
||||
if (!handler) {
|
||||
return TPromise.wrapError<TaskSystem.TaskSet>(new Error('no handler found'));
|
||||
}
|
||||
return asWinJsPromise(token => handler.provider.provideTasks(token)).then(value => {
|
||||
return TaskSet.from(handler.extension, value);
|
||||
});
|
||||
}
|
||||
|
||||
private nextHandle(): number {
|
||||
return this._handleCounter++;
|
||||
}
|
||||
}
|
||||
@@ -5,6 +5,7 @@
|
||||
'use strict';
|
||||
|
||||
|
||||
import { ok } from 'vs/base/common/assert';
|
||||
import { readonly, illegalArgument } from 'vs/base/common/errors';
|
||||
import { IdGenerator } from 'vs/base/common/idGenerator';
|
||||
import { TPromise } from 'vs/base/common/winjs.base';
|
||||
@@ -308,19 +309,18 @@ export class ExtHostTextEditorOptions implements vscode.TextEditorOptions {
|
||||
warnOnError(this._proxy.$trySetOptions(this._id, bulkConfigurationUpdate));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
export class ExtHostTextEditor implements vscode.TextEditor {
|
||||
|
||||
private _proxy: MainThreadEditorsShape;
|
||||
private _id: string;
|
||||
private readonly _proxy: MainThreadEditorsShape;
|
||||
private readonly _id: string;
|
||||
private readonly _documentData: ExtHostDocumentData;
|
||||
|
||||
private _documentData: ExtHostDocumentData;
|
||||
private _selections: Selection[];
|
||||
private _options: ExtHostTextEditorOptions;
|
||||
private _viewColumn: vscode.ViewColumn;
|
||||
private _disposed: boolean = false;
|
||||
|
||||
constructor(proxy: MainThreadEditorsShape, id: string, document: ExtHostDocumentData, selections: Selection[], options: IResolvedTextEditorConfiguration, viewColumn: vscode.ViewColumn) {
|
||||
this._proxy = proxy;
|
||||
@@ -332,7 +332,8 @@ export class ExtHostTextEditor implements vscode.TextEditor {
|
||||
}
|
||||
|
||||
dispose() {
|
||||
this._documentData = null;
|
||||
ok(!this._disposed);
|
||||
this._disposed = true;
|
||||
}
|
||||
|
||||
@deprecated('TextEditor.show') show(column: vscode.ViewColumn) {
|
||||
@@ -346,9 +347,7 @@ export class ExtHostTextEditor implements vscode.TextEditor {
|
||||
// ---- the document
|
||||
|
||||
get document(): vscode.TextDocument {
|
||||
return this._documentData
|
||||
? this._documentData.document
|
||||
: undefined;
|
||||
return this._documentData.document;
|
||||
}
|
||||
|
||||
set document(value) {
|
||||
@@ -362,10 +361,13 @@ export class ExtHostTextEditor implements vscode.TextEditor {
|
||||
}
|
||||
|
||||
set options(value: vscode.TextEditorOptions) {
|
||||
this._options.assign(value);
|
||||
if (!this._disposed) {
|
||||
this._options.assign(value);
|
||||
}
|
||||
}
|
||||
|
||||
_acceptOptions(options: IResolvedTextEditorConfiguration): void {
|
||||
ok(!this._disposed);
|
||||
this._options._accept(options);
|
||||
}
|
||||
|
||||
@@ -380,6 +382,7 @@ export class ExtHostTextEditor implements vscode.TextEditor {
|
||||
}
|
||||
|
||||
_acceptViewColumn(value: vscode.ViewColumn) {
|
||||
ok(!this._disposed);
|
||||
this._viewColumn = value;
|
||||
}
|
||||
|
||||
@@ -437,18 +440,22 @@ export class ExtHostTextEditor implements vscode.TextEditor {
|
||||
}
|
||||
|
||||
_acceptSelections(selections: Selection[]): void {
|
||||
ok(!this._disposed);
|
||||
this._selections = selections;
|
||||
}
|
||||
|
||||
// ---- editing
|
||||
|
||||
edit(callback: (edit: TextEditorEdit) => void, options: { undoStopBefore: boolean; undoStopAfter: boolean; } = { undoStopBefore: true, undoStopAfter: true }): Thenable<boolean> {
|
||||
if (this._disposed) {
|
||||
return TPromise.wrapError<boolean>('TextEditor#edit not possible on closed editors');
|
||||
}
|
||||
let edit = new TextEditorEdit(this._documentData.document, options);
|
||||
callback(edit);
|
||||
return this._applyEdit(edit);
|
||||
}
|
||||
|
||||
_applyEdit(editBuilder: TextEditorEdit): TPromise<boolean> {
|
||||
private _applyEdit(editBuilder: TextEditorEdit): TPromise<boolean> {
|
||||
let editData = editBuilder.finalize();
|
||||
|
||||
// prepare data for serialization
|
||||
@@ -468,7 +475,9 @@ export class ExtHostTextEditor implements vscode.TextEditor {
|
||||
}
|
||||
|
||||
insertSnippet(snippet: SnippetString, where?: Position | Position[] | Range | Range[], options: { undoStopBefore: boolean; undoStopAfter: boolean; } = { undoStopBefore: true, undoStopAfter: true }): Thenable<boolean> {
|
||||
|
||||
if (this._disposed) {
|
||||
return TPromise.wrapError<boolean>('TextEditor#insertSnippet not possible on closed editors');
|
||||
}
|
||||
let ranges: IRange[];
|
||||
|
||||
if (!where || (Array.isArray(where) && where.length === 0)) {
|
||||
@@ -498,6 +507,14 @@ export class ExtHostTextEditor implements vscode.TextEditor {
|
||||
// ---- util
|
||||
|
||||
private _runOnProxy(callback: () => TPromise<any>, silent: boolean): TPromise<ExtHostTextEditor> {
|
||||
if (this._disposed) {
|
||||
if (!silent) {
|
||||
return TPromise.wrapError(silent);
|
||||
} else {
|
||||
console.warn('TextEditor is closed/disposed');
|
||||
return TPromise.as(undefined);
|
||||
}
|
||||
}
|
||||
return callback().then(() => this, err => {
|
||||
if (!silent) {
|
||||
return TPromise.wrapError(silent);
|
||||
|
||||
@@ -9,7 +9,7 @@ import * as modes from 'vs/editor/common/modes';
|
||||
import * as types from './extHostTypes';
|
||||
import { Position as EditorPosition } from 'vs/platform/editor/common/editor';
|
||||
import { IPosition, ISelection, IRange, IDecorationOptions, ISingleEditOperation, EndOfLineSequence } from 'vs/editor/common/editorCommon';
|
||||
import { IWorkspaceSymbol } from 'vs/workbench/parts/search/common/search';
|
||||
import { IPosition, ISelection, IRange, IDecorationOptions, ISingleEditOperation } from 'vs/editor/common/editorCommon';
|
||||
import * as vscode from 'vscode';
|
||||
import URI from 'vs/base/common/uri';
|
||||
import { SaveReason } from 'vs/workbench/services/textfile/common/textfiles';
|
||||
@@ -165,46 +165,63 @@ export const TextEdit = {
|
||||
}
|
||||
};
|
||||
|
||||
export namespace SymbolInformation {
|
||||
|
||||
export function fromOutlineEntry(entry: modes.SymbolInformation): types.SymbolInformation {
|
||||
return new types.SymbolInformation(
|
||||
entry.name,
|
||||
entry.kind,
|
||||
toRange(entry.location.range),
|
||||
entry.location.uri,
|
||||
entry.containerName
|
||||
);
|
||||
export namespace SymbolKind {
|
||||
|
||||
const _fromMapping: { [kind: number]: modes.SymbolKind } = Object.create(null);
|
||||
_fromMapping[types.SymbolKind.File] = 'file';
|
||||
_fromMapping[types.SymbolKind.Module] = 'module';
|
||||
_fromMapping[types.SymbolKind.Namespace] = 'namespace';
|
||||
_fromMapping[types.SymbolKind.Package] = 'package';
|
||||
_fromMapping[types.SymbolKind.Class] = 'class';
|
||||
_fromMapping[types.SymbolKind.Method] = 'method';
|
||||
_fromMapping[types.SymbolKind.Property] = 'property';
|
||||
_fromMapping[types.SymbolKind.Field] = 'field';
|
||||
_fromMapping[types.SymbolKind.Constructor] = 'constructor';
|
||||
_fromMapping[types.SymbolKind.Enum] = 'enum';
|
||||
_fromMapping[types.SymbolKind.Interface] = 'interface';
|
||||
_fromMapping[types.SymbolKind.Function] = 'function';
|
||||
_fromMapping[types.SymbolKind.Variable] = 'variable';
|
||||
_fromMapping[types.SymbolKind.Constant] = 'constant';
|
||||
_fromMapping[types.SymbolKind.String] = 'string';
|
||||
_fromMapping[types.SymbolKind.Number] = 'number';
|
||||
_fromMapping[types.SymbolKind.Boolean] = 'boolean';
|
||||
_fromMapping[types.SymbolKind.Array] = 'array';
|
||||
_fromMapping[types.SymbolKind.Object] = 'object';
|
||||
_fromMapping[types.SymbolKind.Key] = 'key';
|
||||
_fromMapping[types.SymbolKind.Null] = 'null';
|
||||
_fromMapping[types.SymbolKind.EnumMember] = 'enum-member';
|
||||
_fromMapping[types.SymbolKind.Struct] = 'struct';
|
||||
|
||||
export function from(kind: vscode.SymbolKind): modes.SymbolKind {
|
||||
return _fromMapping[kind] || 'property';
|
||||
}
|
||||
|
||||
export function toOutlineEntry(symbol: vscode.SymbolInformation): modes.SymbolInformation {
|
||||
return <modes.SymbolInformation>{
|
||||
name: symbol.name,
|
||||
kind: symbol.kind,
|
||||
containerName: symbol.containerName,
|
||||
location: {
|
||||
uri: <URI>symbol.location.uri,
|
||||
range: fromRange(symbol.location.range)
|
||||
export function to(kind: modes.SymbolKind): vscode.SymbolKind {
|
||||
for (let k in _fromMapping) {
|
||||
if (_fromMapping[k] === kind) {
|
||||
return Number(k);
|
||||
}
|
||||
};
|
||||
}
|
||||
return types.SymbolKind.Property;
|
||||
}
|
||||
}
|
||||
|
||||
export function fromSymbolInformation(info: vscode.SymbolInformation): IWorkspaceSymbol {
|
||||
return <IWorkspaceSymbol>{
|
||||
export function fromSymbolInformation(info: vscode.SymbolInformation): modes.SymbolInformation {
|
||||
return <modes.SymbolInformation>{
|
||||
name: info.name,
|
||||
type: types.SymbolKind[info.kind || types.SymbolKind.Property].toLowerCase(),
|
||||
kind: SymbolKind.from(info.kind),
|
||||
containerName: info.containerName,
|
||||
range: info.location && fromRange(info.location.range),
|
||||
resource: info.location && info.location.uri,
|
||||
location: location.from(info.location)
|
||||
};
|
||||
}
|
||||
|
||||
export function toSymbolInformation(bearing: IWorkspaceSymbol): types.SymbolInformation {
|
||||
return new types.SymbolInformation(bearing.name,
|
||||
types.SymbolKind[bearing.type.charAt(0).toUpperCase() + bearing.type.substr(1)],
|
||||
export function toSymbolInformation(bearing: modes.SymbolInformation): types.SymbolInformation {
|
||||
return new types.SymbolInformation(
|
||||
bearing.name,
|
||||
SymbolKind.to(bearing.kind),
|
||||
bearing.containerName,
|
||||
new types.Location(bearing.resource, toRange(bearing.range))
|
||||
location.to(bearing.location)
|
||||
);
|
||||
}
|
||||
|
||||
@@ -247,11 +264,14 @@ export const CompletionItemKind = {
|
||||
case types.CompletionItemKind.Variable: return 'variable';
|
||||
case types.CompletionItemKind.Class: return 'class';
|
||||
case types.CompletionItemKind.Interface: return 'interface';
|
||||
case types.CompletionItemKind.Struct: return 'struct';
|
||||
case types.CompletionItemKind.Module: return 'module';
|
||||
case types.CompletionItemKind.Property: return 'property';
|
||||
case types.CompletionItemKind.Unit: return 'unit';
|
||||
case types.CompletionItemKind.Value: return 'value';
|
||||
case types.CompletionItemKind.Constant: return 'constant';
|
||||
case types.CompletionItemKind.Enum: return 'enum';
|
||||
case types.CompletionItemKind.EnumMember: return 'enum-member';
|
||||
case types.CompletionItemKind.Keyword: return 'keyword';
|
||||
case types.CompletionItemKind.Snippet: return 'snippet';
|
||||
case types.CompletionItemKind.Text: return 'text';
|
||||
|
||||
@@ -718,27 +718,29 @@ export class DocumentHighlight {
|
||||
}
|
||||
|
||||
export enum SymbolKind {
|
||||
File,
|
||||
Module,
|
||||
Namespace,
|
||||
Package,
|
||||
Class,
|
||||
Method,
|
||||
Property,
|
||||
Field,
|
||||
Constructor,
|
||||
Enum,
|
||||
Interface,
|
||||
Function,
|
||||
Variable,
|
||||
Constant,
|
||||
String,
|
||||
Number,
|
||||
Boolean,
|
||||
Array,
|
||||
Object,
|
||||
Key,
|
||||
Null
|
||||
File = 0,
|
||||
Module = 1,
|
||||
Namespace = 2,
|
||||
Package = 3,
|
||||
Class = 4,
|
||||
Method = 5,
|
||||
Property = 6,
|
||||
Field = 7,
|
||||
Constructor = 8,
|
||||
Enum = 9,
|
||||
Interface = 10,
|
||||
Function = 11,
|
||||
Variable = 12,
|
||||
Constant = 13,
|
||||
String = 14,
|
||||
Number = 15,
|
||||
Boolean = 16,
|
||||
Array = 17,
|
||||
Object = 18,
|
||||
Key = 19,
|
||||
Null = 20,
|
||||
EnumMember = 21,
|
||||
Struct = 22
|
||||
}
|
||||
|
||||
export class SymbolInformation {
|
||||
@@ -846,7 +848,10 @@ export enum CompletionItemKind {
|
||||
Color = 15,
|
||||
File = 16,
|
||||
Reference = 17,
|
||||
Folder = 18
|
||||
Folder = 18,
|
||||
EnumMember = 19,
|
||||
Constant = 20,
|
||||
Struct = 21
|
||||
}
|
||||
|
||||
export class CompletionItem {
|
||||
@@ -958,3 +963,227 @@ export class DocumentLink {
|
||||
this.target = target;
|
||||
}
|
||||
}
|
||||
|
||||
export enum FileLocationKind {
|
||||
Auto = 1,
|
||||
|
||||
Relative = 2,
|
||||
|
||||
Absolute = 3
|
||||
}
|
||||
|
||||
export enum ApplyToKind {
|
||||
AllDocuments = 1,
|
||||
|
||||
OpenDocuments = 2,
|
||||
|
||||
ClosedDocuments = 3
|
||||
}
|
||||
|
||||
export enum RevealKind {
|
||||
Always = 1,
|
||||
|
||||
Silent = 2,
|
||||
|
||||
Never = 3
|
||||
}
|
||||
|
||||
export class BaseTask {
|
||||
|
||||
private _name: string;
|
||||
private _problemMatchers: vscode.ProblemMatcher[];
|
||||
private _identifier: string;
|
||||
private _isBackground: boolean;
|
||||
private _terminal: vscode.TerminalBehaviour;
|
||||
|
||||
constructor(name: string, problemMatchers: vscode.ProblemMatcher[]) {
|
||||
if (typeof name !== 'string') {
|
||||
throw illegalArgument('name');
|
||||
}
|
||||
this._name = name;
|
||||
this._identifier = name;
|
||||
this._problemMatchers = problemMatchers || [];
|
||||
this._isBackground = false;
|
||||
this._terminal = Object.create(null);
|
||||
}
|
||||
|
||||
get identifier(): string {
|
||||
return this._identifier;
|
||||
}
|
||||
|
||||
set identifier(value: string) {
|
||||
if (typeof name !== 'string') {
|
||||
throw illegalArgument('identifier');
|
||||
}
|
||||
this._identifier = value;
|
||||
}
|
||||
|
||||
get name(): string {
|
||||
return this._name;
|
||||
}
|
||||
|
||||
get isBackground(): boolean {
|
||||
return this._isBackground;
|
||||
}
|
||||
|
||||
set isBackground(value: boolean) {
|
||||
if (value !== true && value !== false) {
|
||||
value = false;
|
||||
}
|
||||
this._isBackground = value;
|
||||
}
|
||||
|
||||
get terminal(): vscode.TerminalBehaviour {
|
||||
return this._terminal;
|
||||
}
|
||||
|
||||
set terminal(value: vscode.TerminalBehaviour) {
|
||||
if (value === void 0 || value === null) {
|
||||
value = Object.create(null);
|
||||
}
|
||||
this._terminal = value;
|
||||
}
|
||||
|
||||
get problemMatchers(): vscode.ProblemMatcher[] {
|
||||
return this._problemMatchers;
|
||||
}
|
||||
|
||||
set problemMatchers(value: vscode.ProblemMatcher[]) {
|
||||
if (!Array.isArray(value)) {
|
||||
value = [];
|
||||
}
|
||||
this._problemMatchers = value;
|
||||
}
|
||||
}
|
||||
|
||||
namespace ProblemMatcher {
|
||||
export function is(value: any): value is vscode.ProblemMatcher {
|
||||
let candidate: vscode.ProblemMatcher = value;
|
||||
return candidate && !!candidate.pattern;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
export class ProcessTask extends BaseTask {
|
||||
|
||||
private _process: string;
|
||||
private _args: string[];
|
||||
private _options: vscode.ProcessOptions;
|
||||
|
||||
private static parseArguments(restArgs: any[]): { args: string[]; options: vscode.ProcessOptions; problemMatchers: vscode.ProblemMatcher[] } {
|
||||
let args: string[] = [];
|
||||
let options: vscode.ProcessOptions = undefined;
|
||||
let problemMatchers: vscode.ProblemMatcher[] = [];
|
||||
if (!restArgs || restArgs.length === 0) {
|
||||
return { args, options, problemMatchers };
|
||||
}
|
||||
let current: any = restArgs[0];
|
||||
if (Array.isArray(current)) {
|
||||
args = current;
|
||||
restArgs.shift();
|
||||
current = restArgs[0];
|
||||
}
|
||||
if (ProblemMatcher.is(current)) {
|
||||
problemMatchers = restArgs;
|
||||
} else if (current) {
|
||||
options = current;
|
||||
restArgs.shift();
|
||||
if (restArgs.length > 0) {
|
||||
problemMatchers = restArgs;
|
||||
}
|
||||
}
|
||||
return { args, options, problemMatchers };
|
||||
}
|
||||
|
||||
constructor(name: string, process: string, ...problemMatchers: vscode.ProblemMatcher[]);
|
||||
constructor(name: string, process: string, args: string[], ...problemMatchers: vscode.ProblemMatcher[]);
|
||||
constructor(name: string, process: string, args: string[], options: vscode.ProcessOptions, ...problemMatchers: vscode.ProblemMatcher[]);
|
||||
constructor(name: string, process: string, ...rest: any[]) {
|
||||
if (typeof process !== 'string') {
|
||||
throw illegalArgument('process');
|
||||
}
|
||||
let { args, options, problemMatchers } = ProcessTask.parseArguments(rest);
|
||||
super(name, problemMatchers);
|
||||
this._process = process;
|
||||
this._args = args;
|
||||
this._options = options || Object.create(null);
|
||||
}
|
||||
|
||||
get process(): string {
|
||||
return this._process;
|
||||
}
|
||||
|
||||
get args(): string[] {
|
||||
return this._args;
|
||||
}
|
||||
|
||||
set args(value: string[]) {
|
||||
if (!Array.isArray(value)) {
|
||||
value = [];
|
||||
}
|
||||
this._args = value;
|
||||
}
|
||||
|
||||
get options(): vscode.ProcessOptions {
|
||||
return this._options;
|
||||
}
|
||||
|
||||
set options(value: vscode.ProcessOptions) {
|
||||
if (value === void 0 || value === null) {
|
||||
value = Object.create(null);
|
||||
}
|
||||
this._options = value;
|
||||
}
|
||||
}
|
||||
|
||||
export class ShellTask extends BaseTask {
|
||||
|
||||
private _commandLine: string;
|
||||
private _options: vscode.ShellOptions;
|
||||
|
||||
private static parseArguments(restArgs: any[]): { options: vscode.ShellOptions; problemMatchers: vscode.ProblemMatcher[] } {
|
||||
let options: vscode.ShellOptions = undefined;
|
||||
let problemMatchers: vscode.ProblemMatcher[] = [];
|
||||
if (!restArgs || restArgs.length === 0) {
|
||||
return { options, problemMatchers };
|
||||
}
|
||||
let current: any = restArgs[0];
|
||||
if (current && !ProblemMatcher.is(current)) {
|
||||
options = current;
|
||||
restArgs.shift();
|
||||
current = restArgs[0];
|
||||
}
|
||||
if (ProblemMatcher.is(current)) {
|
||||
problemMatchers = restArgs;
|
||||
}
|
||||
return { options, problemMatchers };
|
||||
}
|
||||
|
||||
constructor(name: string, commandLine: string, ...problemMatchers: vscode.ProblemMatcher[]);
|
||||
constructor(name: string, commandLine: string, options: vscode.ShellOptions, ...problemMatchers: vscode.ProblemMatcher[]);
|
||||
constructor(name: string, commandLine: string, ...rest: any[]) {
|
||||
if (typeof commandLine !== 'string') {
|
||||
throw illegalArgument('commandLine');
|
||||
}
|
||||
let { options, problemMatchers } = ShellTask.parseArguments(rest);
|
||||
|
||||
super(name, problemMatchers);
|
||||
this._commandLine = commandLine;
|
||||
this._options = options || Object.create(null);
|
||||
}
|
||||
|
||||
get commandLine(): string {
|
||||
return this._commandLine;
|
||||
}
|
||||
|
||||
get options(): vscode.ShellOptions {
|
||||
return this._options;
|
||||
}
|
||||
|
||||
set options(value: vscode.ShellOptions) {
|
||||
if (value === void 0 || value === null) {
|
||||
value = Object.create(null);
|
||||
}
|
||||
this._options = value;
|
||||
}
|
||||
}
|
||||
@@ -7,7 +7,6 @@
|
||||
import URI from 'vs/base/common/uri';
|
||||
import { toErrorMessage } from 'vs/base/common/errorMessage';
|
||||
import { EmitterEvent } from 'vs/base/common/eventEmitter';
|
||||
import { setDisposableTimeout } from 'vs/base/common/async';
|
||||
import { IModelService } from 'vs/editor/common/services/modelService';
|
||||
import { IThreadService } from 'vs/workbench/services/thread/common/threadService';
|
||||
import { IDisposable, dispose, IReference } from 'vs/base/common/lifecycle';
|
||||
@@ -25,48 +24,47 @@ import { MainThreadDocumentsAndEditors } from './mainThreadDocumentsAndEditors';
|
||||
import * as editorCommon from 'vs/editor/common/editorCommon';
|
||||
import { ITextEditorModel } from 'vs/workbench/common/editor';
|
||||
|
||||
class TimeoutReference {
|
||||
export class BoundModelReferenceCollection {
|
||||
|
||||
private static _delay = 1000 * 60 * 3;
|
||||
|
||||
private _timer: IDisposable;
|
||||
private _disposed = false;
|
||||
private _data = new Array<{ length: number, dispose(): void }>();
|
||||
private _length = 0;
|
||||
|
||||
constructor(
|
||||
readonly codeEditorService: ICodeEditorService,
|
||||
readonly editorGroupService: IEditorGroupService,
|
||||
readonly reference: IReference<ITextEditorModel>
|
||||
private _maxAge: number = 1000 * 60 * 3,
|
||||
private _maxLength: number = 1024 * 1024 * 80
|
||||
) {
|
||||
|
||||
const check = () => {
|
||||
if (!this.isUsed()) {
|
||||
this.dispose();
|
||||
} else {
|
||||
this._timer = setDisposableTimeout(check, TimeoutReference._delay);
|
||||
}
|
||||
};
|
||||
this._timer = setDisposableTimeout(check, TimeoutReference._delay);
|
||||
//
|
||||
}
|
||||
|
||||
dispose(): void {
|
||||
if (!this._disposed) {
|
||||
this._disposed = true;
|
||||
dispose(this.reference, this._timer);
|
||||
}
|
||||
this._data = dispose(this._data);
|
||||
}
|
||||
|
||||
private isUsed(): boolean {
|
||||
for (const editor of this.codeEditorService.listCodeEditors()) {
|
||||
if (editor.getModel() === this.reference.object.textEditorModel) {
|
||||
return true;
|
||||
add(ref: IReference<ITextEditorModel>): void {
|
||||
let length = ref.object.textEditorModel.getValueLength();
|
||||
let handle: number;
|
||||
let entry: { length: number, dispose(): void };
|
||||
const dispose = () => {
|
||||
let idx = this._data.indexOf(entry);
|
||||
if (idx >= 0) {
|
||||
this._length -= length;
|
||||
ref.dispose();
|
||||
clearTimeout(handle);
|
||||
this._data.splice(idx, 1);
|
||||
}
|
||||
};
|
||||
handle = setTimeout(dispose, this._maxAge);
|
||||
entry = { length, dispose };
|
||||
|
||||
this._data.push(entry);
|
||||
this._length += length;
|
||||
this._cleanup();
|
||||
}
|
||||
|
||||
private _cleanup(): void {
|
||||
while (this._length > this._maxLength) {
|
||||
this._data[0].dispose();
|
||||
}
|
||||
for (const group of this.editorGroupService.getStacksModel().groups) {
|
||||
if (group.contains(this.reference.object.textEditorModel.uri)) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -86,6 +84,7 @@ export class MainThreadDocuments extends MainThreadDocumentsShape {
|
||||
private _proxy: ExtHostDocumentsShape;
|
||||
private _modelIsSynced: { [modelId: string]: boolean; };
|
||||
private _resourceContentProvider: { [handle: number]: IDisposable };
|
||||
private _modelReferenceCollection = new BoundModelReferenceCollection();
|
||||
|
||||
constructor(
|
||||
documentsAndEditors: MainThreadDocumentsAndEditors,
|
||||
@@ -113,6 +112,7 @@ export class MainThreadDocuments extends MainThreadDocumentsShape {
|
||||
this._modelIsSynced = {};
|
||||
|
||||
this._toDispose = [];
|
||||
this._toDispose.push(this._modelReferenceCollection);
|
||||
this._toDispose.push(documentsAndEditors.onDocumentAdd(models => models.forEach(this._onModelAdded, this)));
|
||||
this._toDispose.push(documentsAndEditors.onDocumentRemove(urls => urls.forEach(this._onModelRemoved, this)));
|
||||
modelService.onModelModeChanged(this._onModelModeChanged, this, this._toDispose);
|
||||
@@ -234,11 +234,7 @@ export class MainThreadDocuments extends MainThreadDocumentsShape {
|
||||
|
||||
private _handleAsResourceInput(uri: URI): TPromise<boolean> {
|
||||
return this._textModelResolverService.createModelReference(uri).then(ref => {
|
||||
// TimeoutReference will check every 3 min if the
|
||||
// reference is still in use. This is quite harsh to
|
||||
// extensions but we don't want them to make us hold
|
||||
// on to model indefinitely
|
||||
this._toDispose.push(new TimeoutReference(this._codeEditorService, this._editorGroupService, ref));
|
||||
this._modelReferenceCollection.add(ref);
|
||||
const result = !!ref.object;
|
||||
return result;
|
||||
});
|
||||
|
||||
@@ -11,7 +11,7 @@ import { IThreadService } from 'vs/workbench/services/thread/common/threadServic
|
||||
import * as vscode from 'vscode';
|
||||
import { IReadOnlyModel, ISingleEditOperation } from 'vs/editor/common/editorCommon';
|
||||
import * as modes from 'vs/editor/common/modes';
|
||||
import { WorkspaceSymbolProviderRegistry, IWorkspaceSymbolProvider, IWorkspaceSymbol } from 'vs/workbench/parts/search/common/search';
|
||||
import { WorkspaceSymbolProviderRegistry, IWorkspaceSymbolProvider } from 'vs/workbench/parts/search/common/search';
|
||||
import { wireCancellationToken } from 'vs/base/common/async';
|
||||
import { CancellationToken } from 'vs/base/common/cancellation';
|
||||
import { Position as EditorPosition } from 'vs/editor/common/core/position';
|
||||
@@ -200,10 +200,10 @@ export class MainThreadLanguageFeatures extends MainThreadLanguageFeaturesShape
|
||||
|
||||
$registerNavigateTypeSupport(handle: number): TPromise<any> {
|
||||
this._registrations[handle] = WorkspaceSymbolProviderRegistry.register(<IWorkspaceSymbolProvider>{
|
||||
provideWorkspaceSymbols: (search: string): TPromise<IWorkspaceSymbol[]> => {
|
||||
provideWorkspaceSymbols: (search: string): TPromise<modes.SymbolInformation[]> => {
|
||||
return this._heapService.trackRecursive(this._proxy.$provideWorkspaceSymbols(handle, search));
|
||||
},
|
||||
resolveWorkspaceSymbol: (item: IWorkspaceSymbol): TPromise<IWorkspaceSymbol> => {
|
||||
resolveWorkspaceSymbol: (item: modes.SymbolInformation): TPromise<modes.SymbolInformation> => {
|
||||
return this._proxy.$resolveWorkspaceSymbol(handle, item);
|
||||
}
|
||||
});
|
||||
|
||||
@@ -43,7 +43,7 @@ export class MainThreadOutputService extends MainThreadOutputServiceShape {
|
||||
}
|
||||
|
||||
private _getChannel(channelId: string, label: string): IOutputChannel {
|
||||
if (Registry.as<IOutputChannelRegistry>(Extensions.OutputChannels).getChannels().every(channel => channel.id !== channelId)) {
|
||||
if (!Registry.as<IOutputChannelRegistry>(Extensions.OutputChannels).getChannel(channelId)) {
|
||||
Registry.as<IOutputChannelRegistry>(Extensions.OutputChannels).registerChannel(channelId, label);
|
||||
}
|
||||
|
||||
|
||||
36
src/vs/workbench/api/node/mainThreadTask.ts
Normal file
36
src/vs/workbench/api/node/mainThreadTask.ts
Normal file
@@ -0,0 +1,36 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
'use strict';
|
||||
|
||||
import { TPromise } from 'vs/base/common/winjs.base';
|
||||
|
||||
import { ITaskService } from 'vs/workbench/parts/tasks/common/taskService';
|
||||
import { IThreadService } from 'vs/workbench/services/thread/common/threadService';
|
||||
|
||||
import { ExtHostContext, MainThreadTaskShape, ExtHostTaskShape } from './extHost.protocol';
|
||||
|
||||
export class MainThreadTask extends MainThreadTaskShape {
|
||||
|
||||
private _proxy: ExtHostTaskShape;
|
||||
|
||||
constructor( @IThreadService threadService: IThreadService, @ITaskService private _taskService: ITaskService) {
|
||||
super();
|
||||
this._proxy = threadService.get(ExtHostContext.ExtHostTask);
|
||||
}
|
||||
|
||||
public $registerTaskProvider(handle: number): TPromise<void> {
|
||||
this._taskService.registerTaskProvider(handle, {
|
||||
provideTasks: () => {
|
||||
return this._proxy.$provideTasks(handle);
|
||||
}
|
||||
});
|
||||
return TPromise.as<void>(undefined);
|
||||
}
|
||||
|
||||
public $unregisterTaskProvider(handle: number): TPromise<any> {
|
||||
this._taskService.unregisterTaskProvider(handle);
|
||||
return TPromise.as<void>(undefined);
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user