提交 5eb65764 编写于 作者: S Sandeep Somavarapu

Merge branch 'master' into pr/83797

......@@ -1139,11 +1139,6 @@
"when": "scmProvider == git && scmResourceGroup == workingTree",
"group": "2_view"
},
{
"command": "git.openChange",
"when": "scmProvider == git && scmResourceGroup == workingTree",
"group": "navigation"
},
{
"command": "git.openChange",
"when": "scmProvider == git && scmResourceGroup == untracked",
......
......@@ -14,7 +14,6 @@
},
"include": [
"typings/require.d.ts",
"typings/require-monaco.d.ts",
"typings/thenable.d.ts",
"typings/es6-promise.d.ts",
"typings/lib.es2018.promise.d.ts",
......
......@@ -48,3 +48,5 @@ interface NodeRequire {
__$__nodeRequire<T>(moduleName: string): T;
getStats(): ReadonlyArray<LoaderEvent>;
}
declare var require: NodeRequire;
/*---------------------------------------------------------------------------------------------
* Copyright (c) Microsoft Corporation. All rights reserved.
* Licensed under the MIT License. See License.txt in the project root for license information.
*--------------------------------------------------------------------------------------------*/
declare module 'yauzl' {
import { EventEmitter } from 'events';
import { Readable } from 'stream';
export class Entry {
fileName: string;
extraFields: { id: number; data: Buffer; }[];
comment: string;
versionMadeBy: number;
versionNeededToExtract: number;
generalPurposeBitFlag: number;
compressionMethod: number;
lastModFileTime: number;
lastModFileDate: number;
crc32: number;
compressedSize: number;
uncompressedSize: number;
fileNameLength: number;
extraFieldLength: number;
fileCommentLength: number;
internalFileAttributes: number;
externalFileAttributes: number;
relativeOffsetOfLocalHeader: number;
getLastModDate(): Date;
}
export class ZipFile extends EventEmitter {
readEntry(): void;
openReadStream(entry: Entry, callback: (err?: Error, stream?: Readable) => void): void;
close(): void;
isOpen: boolean;
entryCount: number;
comment: string;
}
export interface IOptions {
autoClose?: boolean;
lazyEntries?: boolean;
}
export function open(path: string, callback: (err?: Error, zipfile?: ZipFile) => void): void;
export function open(path: string, options: IOptions | undefined, callback: (err?: Error, zipfile?: ZipFile) => void): void;
}
\ No newline at end of file
/*---------------------------------------------------------------------------------------------
* Copyright (c) Microsoft Corporation. All rights reserved.
* Licensed under the MIT License. See License.txt in the project root for license information.
*--------------------------------------------------------------------------------------------*/
declare module 'yazl' {
import * as stream from 'stream';
class ZipFile {
outputStream: stream.Stream;
addBuffer(buffer: Buffer, path: string): void;
addFile(localPath: string, path: string): void;
end(): void;
}
}
\ No newline at end of file
......@@ -14,7 +14,7 @@
height: 100%;
position: absolute;
top: 0;
left: 18px;
left: 16px;
pointer-events: none;
}
......
......@@ -163,7 +163,7 @@ function extractZip(zipfile: ZipFile, targetPath: string, options: IOptions, tok
function openZip(zipFile: string, lazy: boolean = false): Promise<ZipFile> {
return new Promise((resolve, reject) => {
_openZip(zipFile, lazy ? { lazyEntries: true } : undefined, (error?: Error, zipfile?: ZipFile) => {
_openZip(zipFile, lazy ? { lazyEntries: true } : undefined!, (error?: Error, zipfile?: ZipFile) => {
if (error) {
reject(toExtractError(error));
} else {
......
......@@ -498,39 +498,35 @@ export class MainThreadLanguageFeatures implements MainThreadLanguageFeaturesSha
this._registrations.set(handle, callh.CallHierarchyProviderRegistry.register(selector, {
prepareCallHierarchy: async (document, position, token) => {
const result = await this._proxy.$prepareCallHierarchy(handle, document.uri, position, token);
if (!result) {
const item = await this._proxy.$prepareCallHierarchy(handle, document.uri, position, token);
if (!item) {
return undefined;
}
return {
dispose: () => this._proxy.$releaseCallHierarchy(handle, result.sessionId),
root: MainThreadLanguageFeatures._reviveCallHierarchyItemDto(result.root)
dispose: () => this._proxy.$releaseCallHierarchy(handle, item._sessionId),
root: MainThreadLanguageFeatures._reviveCallHierarchyItemDto(item)
};
},
provideOutgoingCalls: async (item, token) => {
const outgoing = await this._proxy.$provideCallHierarchyOutgoingCalls(handle, item.id, token);
const outgoing = await this._proxy.$provideCallHierarchyOutgoingCalls(handle, item._sessionId, item._itemId, token);
if (!outgoing) {
return outgoing;
}
return outgoing.map(([item, fromRanges]): callh.OutgoingCall => {
return {
to: MainThreadLanguageFeatures._reviveCallHierarchyItemDto(item),
fromRanges
};
outgoing.forEach(value => {
value.to = MainThreadLanguageFeatures._reviveCallHierarchyItemDto(value.to);
});
return <any>outgoing;
},
provideIncomingCalls: async (item, token) => {
const incoming = await this._proxy.$provideCallHierarchyIncomingCalls(handle, item.id, token);
const incoming = await this._proxy.$provideCallHierarchyIncomingCalls(handle, item._sessionId, item._itemId, token);
if (!incoming) {
return incoming;
}
return incoming.map(([item, fromRanges]): callh.IncomingCall => {
return {
from: MainThreadLanguageFeatures._reviveCallHierarchyItemDto(item),
fromRanges
};
incoming.forEach(value => {
value.from = MainThreadLanguageFeatures._reviveCallHierarchyItemDto(value.from);
});
return <any>incoming;
}
}));
}
......
......@@ -71,7 +71,7 @@ export interface IStaticWorkspaceData {
}
export interface IWorkspaceData extends IStaticWorkspaceData {
folders: { uri: UriComponents, name: string, index: number }[];
folders: { uri: UriComponents, name: string, index: number; }[];
}
export interface IInitData {
......@@ -97,7 +97,7 @@ export interface IConfigurationInitData extends IConfigurationData {
export interface IWorkspaceConfigurationChangeEventData {
changedConfiguration: IConfigurationModel;
changedConfigurationByResource: { [folder: string]: IConfigurationModel };
changedConfigurationByResource: { [folder: string]: IConfigurationModel; };
}
export interface IExtHostContext extends IRPCProtocol {
......@@ -136,7 +136,7 @@ export type CommentThreadChanges = Partial<{
label: string,
contextValue: string,
comments: modes.Comment[],
collapseState: modes.CommentThreadCollapsibleState
collapseState: modes.CommentThreadCollapsibleState;
}>;
export interface MainThreadCommentsShape extends IDisposable {
......@@ -165,13 +165,13 @@ export interface MainThreadDialogOpenOptions {
canSelectFiles?: boolean;
canSelectFolders?: boolean;
canSelectMany?: boolean;
filters?: { [name: string]: string[] };
filters?: { [name: string]: string[]; };
}
export interface MainThreadDialogSaveOptions {
defaultUri?: UriComponents;
saveLabel?: string;
filters?: { [name: string]: string[] };
filters?: { [name: string]: string[]; };
}
export interface MainThreadDiaglogsShape extends IDisposable {
......@@ -254,8 +254,8 @@ export interface MainThreadTextEditorsShape extends IDisposable {
}
export interface MainThreadTreeViewsShape extends IDisposable {
$registerTreeViewDataProvider(treeViewId: string, options: { showCollapseAll: boolean, canSelectMany: boolean }): void;
$refresh(treeViewId: string, itemsToRefresh?: { [treeItemHandle: string]: ITreeItem }): Promise<void>;
$registerTreeViewDataProvider(treeViewId: string, options: { showCollapseAll: boolean, canSelectMany: boolean; }): void;
$refresh(treeViewId: string, itemsToRefresh?: { [treeItemHandle: string]: ITreeItem; }): Promise<void>;
$reveal(treeViewId: string, treeItem: ITreeItem, parentChain: ITreeItem[], options: IRevealOptions): Promise<void>;
$setMessage(treeViewId: string, message: string): void;
$setTitle(treeViewId: string, title: string): void;
......@@ -278,7 +278,7 @@ export interface MainThreadKeytarShape extends IDisposable {
$setPassword(service: string, account: string, password: string): Promise<void>;
$deletePassword(service: string, account: string): Promise<boolean>;
$findPassword(service: string): Promise<string | null>;
$findCredentials(service: string): Promise<Array<{ account: string, password: string }>>;
$findCredentials(service: string): Promise<Array<{ account: string, password: string; }>>;
}
export interface IRegExpDto {
......@@ -321,7 +321,7 @@ export interface ILanguageConfigurationDto {
};
}
export type GlobPattern = string | { base: string; pattern: string };
export type GlobPattern = string | { base: string; pattern: string; };
export interface IDocumentFilterDto {
$serialized: true;
......@@ -400,7 +400,7 @@ export interface TerminalLaunchConfig {
shellPath?: string;
shellArgs?: string[] | string;
cwd?: string | UriComponents;
env?: { [key: string]: string | null };
env?: { [key: string]: string | null; };
waitOnExit?: boolean;
strictEnv?: boolean;
hideFromUser?: boolean;
......@@ -408,7 +408,7 @@ export interface TerminalLaunchConfig {
}
export interface MainThreadTerminalServiceShape extends IDisposable {
$createTerminal(config: TerminalLaunchConfig): Promise<{ id: number, name: string }>;
$createTerminal(config: TerminalLaunchConfig): Promise<{ id: number, name: string; }>;
$dispose(terminalId: number): void;
$hide(terminalId: number): void;
$sendText(terminalId: number, text: string, addNewLine: boolean): void;
......@@ -558,7 +558,7 @@ export interface MainThreadWebviewsShape extends IDisposable {
$disposeWebview(handle: WebviewPanelHandle): void;
$reveal(handle: WebviewPanelHandle, showOptions: WebviewPanelShowOptions): void;
$setTitle(handle: WebviewPanelHandle, value: string): void;
$setIconPath(handle: WebviewPanelHandle, value: { light: UriComponents, dark: UriComponents } | undefined): void;
$setIconPath(handle: WebviewPanelHandle, value: { light: UriComponents, dark: UriComponents; } | undefined): void;
$setHtml(handle: WebviewPanelHandle, value: string): void;
$setOptions(handle: WebviewPanelHandle, options: modes.IWebviewOptions): void;
......@@ -593,7 +593,7 @@ export interface MainThreadUrlsShape extends IDisposable {
$registerUriHandler(handle: number, extensionId: ExtensionIdentifier): Promise<void>;
$unregisterUriHandler(handle: number): Promise<void>;
$createAppUri(uri: UriComponents): Promise<UriComponents>;
$proposedCreateAppUri(extensionId: ExtensionIdentifier, options?: { payload?: Partial<UriComponents> }): Promise<UriComponents>;
$proposedCreateAppUri(extensionId: ExtensionIdentifier, options?: { payload?: Partial<UriComponents>; }): Promise<UriComponents>;
}
export interface ExtHostUrlsShape {
......@@ -609,7 +609,7 @@ export interface MainThreadWorkspaceShape extends IDisposable {
$startTextSearch(query: search.IPatternInfo, options: ITextQueryBuilderOptions, requestId: number, token: CancellationToken): Promise<ITextSearchComplete>;
$checkExists(folders: UriComponents[], includes: string[], token: CancellationToken): Promise<boolean>;
$saveAll(includeUntitled?: boolean): Promise<boolean>;
$updateWorkspaceFolders(extensionName: string, index: number, deleteCount: number, workspaceFoldersToAdd: { uri: UriComponents, name?: string }[]): Promise<void>;
$updateWorkspaceFolders(extensionName: string, index: number, deleteCount: number, workspaceFoldersToAdd: { uri: UriComponents, name?: string; }[]): Promise<void>;
$resolveProxy(url: string): Promise<string | undefined>;
}
......@@ -764,7 +764,7 @@ export interface MainThreadWindowShape extends IDisposable {
export interface ExtHostCommandsShape {
$executeContributedCommand<T>(id: string, ...args: any[]): Promise<T>;
$getContributedCommandHandlerDescriptions(): Promise<{ [id: string]: string | ICommandHandlerDescription }>;
$getContributedCommandHandlerDescriptions(): Promise<{ [id: string]: string | ICommandHandlerDescription; }>;
}
export interface ExtHostConfigurationShape {
......@@ -898,7 +898,7 @@ export interface ExtHostExtensionServiceShape {
$startExtensionHost(enabledExtensionIds: ExtensionIdentifier[]): Promise<void>;
$activateByEvent(activationEvent: string): Promise<void>;
$activate(extensionId: ExtensionIdentifier, reason: ExtensionActivationReason): Promise<boolean>;
$setRemoteEnvironment(env: { [key: string]: string | null }): Promise<void>;
$setRemoteEnvironment(env: { [key: string]: string | null; }): Promise<void>;
$deltaExtensions(toAdd: IExtensionDescription[], toRemove: ExtensionIdentifier[]): Promise<void>;
......@@ -978,7 +978,7 @@ export interface ISuggestDataDto {
[ISuggestDataDtoField.preselect]?: boolean;
[ISuggestDataDtoField.insertText]?: string;
[ISuggestDataDtoField.insertTextRules]?: modes.CompletionItemInsertTextRule;
[ISuggestDataDtoField.range]?: IRange | { insert: IRange, replace: IRange };
[ISuggestDataDtoField.range]?: IRange | { insert: IRange, replace: IRange; };
[ISuggestDataDtoField.commitCharacters]?: string[];
[ISuggestDataDtoField.additionalTextEdits]?: ISingleEditOperation[];
[ISuggestDataDtoField.command]?: modes.Command;
......@@ -989,7 +989,7 @@ export interface ISuggestDataDto {
export interface ISuggestResultDto {
x?: number;
a: { insert: IRange, replace: IRange };
a: { insert: IRange, replace: IRange; };
b: ISuggestDataDto[];
c?: boolean;
}
......@@ -1112,7 +1112,8 @@ export interface ICodeLensDto {
}
export interface ICallHierarchyItemDto {
id: string;
_sessionId: string;
_itemId: string;
kind: modes.SymbolKind;
name: string;
detail?: string;
......@@ -1121,6 +1122,16 @@ export interface ICallHierarchyItemDto {
selectionRange: IRange;
}
export interface IIncomingCallDto {
from: ICallHierarchyItemDto;
fromRanges: IRange[];
}
export interface IOutgoingCallDto {
fromRanges: IRange[];
to: ICallHierarchyItemDto;
}
export interface ExtHostLanguageFeaturesShape {
$provideDocumentSymbols(handle: number, resource: UriComponents, token: CancellationToken): Promise<modes.DocumentSymbol[] | undefined>;
$provideCodeLenses(handle: number, resource: UriComponents, token: CancellationToken): Promise<ICodeLensListDto | undefined>;
......@@ -1155,9 +1166,9 @@ export interface ExtHostLanguageFeaturesShape {
$provideColorPresentations(handle: number, resource: UriComponents, colorInfo: IRawColorInfo, token: CancellationToken): Promise<modes.IColorPresentation[] | undefined>;
$provideFoldingRanges(handle: number, resource: UriComponents, context: modes.FoldingContext, token: CancellationToken): Promise<modes.FoldingRange[] | undefined>;
$provideSelectionRanges(handle: number, resource: UriComponents, positions: IPosition[], token: CancellationToken): Promise<modes.SelectionRange[][]>;
$prepareCallHierarchy(handle: number, resource: UriComponents, position: IPosition, token: CancellationToken): Promise<{ sessionId: string, root: ICallHierarchyItemDto } | undefined>;
$provideCallHierarchyIncomingCalls(handle: number, itemId: string, token: CancellationToken): Promise<[ICallHierarchyItemDto, IRange[]][] | undefined>;
$provideCallHierarchyOutgoingCalls(handle: number, itemId: string, token: CancellationToken): Promise<[ICallHierarchyItemDto, IRange[]][] | undefined>;
$prepareCallHierarchy(handle: number, resource: UriComponents, position: IPosition, token: CancellationToken): Promise<ICallHierarchyItemDto | undefined>;
$provideCallHierarchyIncomingCalls(handle: number, sessionId: string, itemId: string, token: CancellationToken): Promise<IIncomingCallDto[] | undefined>;
$provideCallHierarchyOutgoingCalls(handle: number, sessionId: string, itemId: string, token: CancellationToken): Promise<IOutgoingCallDto[] | undefined>;
$releaseCallHierarchy(handle: number, sessionId: string): void;
}
......@@ -1177,7 +1188,7 @@ export interface IShellLaunchConfigDto {
executable?: string;
args?: string[] | string;
cwd?: string | UriComponents;
env?: { [key: string]: string | null };
env?: { [key: string]: string | null; };
}
export interface IShellDefinitionDto {
......@@ -1232,8 +1243,8 @@ export interface ExtHostTaskShape {
$onDidStartTaskProcess(value: tasks.TaskProcessStartedDTO): void;
$onDidEndTaskProcess(value: tasks.TaskProcessEndedDTO): void;
$OnDidEndTask(execution: tasks.TaskExecutionDTO): void;
$resolveVariables(workspaceFolder: UriComponents, toResolve: { process?: { name: string; cwd?: string }, variables: string[] }): Promise<{ process?: string; variables: { [key: string]: string } }>;
$getDefaultShellAndArgs(): Thenable<{ shell: string, args: string[] | string | undefined }>;
$resolveVariables(workspaceFolder: UriComponents, toResolve: { process?: { name: string; cwd?: string; }, variables: string[]; }): Promise<{ process?: string; variables: { [key: string]: string; }; }>;
$getDefaultShellAndArgs(): Thenable<{ shell: string, args: string[] | string | undefined; }>;
$jsonTasksSupported(): Thenable<boolean>;
}
......@@ -1321,7 +1332,7 @@ export interface DecorationRequest {
}
export type DecorationData = [number, boolean, string, string, ThemeColor];
export type DecorationReply = { [id: number]: DecorationData };
export type DecorationReply = { [id: number]: DecorationData; };
export interface ExtHostDecorationsShape {
$provideDecorations(requests: DecorationRequest[], token: CancellationToken): Promise<DecorationReply>;
......
......@@ -4,11 +4,11 @@
*--------------------------------------------------------------------------------------------*/
import { URI } from 'vs/base/common/uri';
import { DisposableStore } from 'vs/base/common/lifecycle';
import { DisposableStore, IDisposable } from 'vs/base/common/lifecycle';
import * as vscode from 'vscode';
import * as typeConverters from 'vs/workbench/api/common/extHostTypeConverters';
import * as types from 'vs/workbench/api/common/extHostTypes';
import { IRawColorInfo, IWorkspaceEditDto } from 'vs/workbench/api/common/extHost.protocol';
import { IRawColorInfo, IWorkspaceEditDto, ICallHierarchyItemDto, IIncomingCallDto, IOutgoingCallDto } from 'vs/workbench/api/common/extHost.protocol';
import { ISingleEditOperation } from 'vs/editor/common/model';
import * as modes from 'vs/editor/common/modes';
import * as search from 'vs/workbench/contrib/search/common/search';
......@@ -19,10 +19,97 @@ import { ICommandsExecutor, OpenFolderAPICommand, DiffAPICommand, OpenAPICommand
import { EditorGroupLayout } from 'vs/workbench/services/editor/common/editorGroupsService';
import { isFalsyOrEmpty } from 'vs/base/common/arrays';
import { IRange } from 'vs/editor/common/core/range';
import { IPosition } from 'vs/editor/common/core/position';
//#region --- NEW world
export class ApiCommandArgument<V, O = V> {
static readonly Uri = new ApiCommandArgument<URI>('uri', 'Uri of a text document', v => URI.isUri(v), v => v);
static readonly Position = new ApiCommandArgument<types.Position, IPosition>('position', 'A position in a text document', v => types.Position.isPosition(v), typeConverters.Position.from);
static readonly CallHierarchyItem = new ApiCommandArgument('item', 'A call hierarchy item', v => v instanceof types.CallHierarchyItem, typeConverters.CallHierarchyItem.to);
constructor(
readonly name: string,
readonly description: string,
readonly validate: (v: V) => boolean,
readonly convert: (v: V) => O
) { }
}
export class ApiCommandResult<V, O = V> {
constructor(
readonly description: string,
readonly convert: (v: V) => O
) { }
}
export class ApiCommand {
constructor(
readonly id: string,
readonly internalId: string,
readonly description: string,
readonly args: ApiCommandArgument<any, any>[],
readonly result: ApiCommandResult<any, any>
) { }
register(commands: ExtHostCommands): IDisposable {
return commands.registerCommand(false, this.id, async (...apiArgs) => {
const internalArgs = this.args.map((arg, i) => {
if (!arg.validate(apiArgs[i])) {
throw new Error(`Invalid argument '${arg.name}' when running '${this.id}', receieved: ${apiArgs[i]}`);
}
return arg.convert(apiArgs[i]);
});
const internalResult = await commands.executeCommand(this.internalId, ...internalArgs);
return this.result.convert(internalResult);
}, undefined, this._getCommandHandlerDesc());
}
private _getCommandHandlerDesc(): ICommandHandlerDescription {
return {
description: this.description,
args: this.args,
returns: this.result.description
};
}
}
const newCommands: ApiCommand[] = [
new ApiCommand(
'vscode.prepareCallHierarchy', '_executePrepareCallHierarchy', 'Prepare call hierarchy at a position inside a document',
[ApiCommandArgument.Uri, ApiCommandArgument.Position],
new ApiCommandResult<ICallHierarchyItemDto, types.CallHierarchyItem>('A CallHierarchyItem or undefined', v => typeConverters.CallHierarchyItem.to(v))
),
new ApiCommand(
'vscode.provideIncomingCalls', '_executeProvideIncomingCalls', 'Compute incoming calls for an item',
[ApiCommandArgument.CallHierarchyItem],
new ApiCommandResult<IIncomingCallDto[], types.CallHierarchyIncomingCall[]>('A CallHierarchyItem or undefined', v => v.map(typeConverters.CallHierarchyIncomingCall.to))
),
new ApiCommand(
'vscode.provideOutgoingCalls', '_executeProvideOutgoingCalls', 'Compute outgoing calls for an item',
[ApiCommandArgument.CallHierarchyItem],
new ApiCommandResult<IOutgoingCallDto[], types.CallHierarchyOutgoingCall[]>('A CallHierarchyItem or undefined', v => v.map(typeConverters.CallHierarchyOutgoingCall.to))
),
];
//#endregion
//#region OLD world
export class ExtHostApiCommands {
static register(commands: ExtHostCommands) {
newCommands.forEach(command => command.register(commands));
return new ExtHostApiCommands(commands).registerCommands();
}
......@@ -433,7 +520,7 @@ export class ExtHostApiCommands {
});
}
private _executeColorPresentationProvider(color: types.Color, context: { uri: URI, range: types.Range }): Promise<types.ColorPresentation[]> {
private _executeColorPresentationProvider(color: types.Color, context: { uri: URI, range: types.Range; }): Promise<types.ColorPresentation[]> {
const args = {
resource: context.uri,
color: typeConverters.Color.from(color),
......
......@@ -26,6 +26,7 @@ import { CancellationToken } from 'vs/base/common/cancellation';
import { ExtensionIdentifier, IExtensionDescription } from 'vs/platform/extensions/common/extensions';
import { IURITransformer } from 'vs/base/common/uriIpc';
import { DisposableStore, dispose } from 'vs/base/common/lifecycle';
import { IdGenerator } from 'vs/base/common/idGenerator';
// --- adapter
......@@ -751,7 +752,7 @@ class SuggestAdapter {
}
// 'overwrite[Before|After]'-logic
let range: vscode.Range | { inserting: vscode.Range, replacing: vscode.Range } | undefined;
let range: vscode.Range | { inserting: vscode.Range, replacing: vscode.Range; } | undefined;
if (item.textEdit) {
range = item.textEdit.range;
} else if (item.range) {
......@@ -1034,15 +1035,15 @@ class SelectionRangeAdapter {
class CallHierarchyAdapter {
private _idPool: number = 0;
private readonly _cache = new Map<string, vscode.CallHierarchyItem[]>();
private readonly _idPool = new IdGenerator('');
private readonly _cache = new Map<string, Map<string, vscode.CallHierarchyItem>>();
constructor(
private readonly _documents: ExtHostDocuments,
private readonly _provider: vscode.CallHierarchyProvider
) { }
async prepareSession(uri: URI, position: IPosition, token: CancellationToken): Promise<{ sessionId: string, root: extHostProtocol.ICallHierarchyItemDto } | undefined> {
async prepareSession(uri: URI, position: IPosition, token: CancellationToken): Promise<extHostProtocol.ICallHierarchyItemDto | undefined> {
const doc = this._documents.getDocument(uri);
const pos = typeConvert.Position.to(position);
......@@ -1050,13 +1051,14 @@ class CallHierarchyAdapter {
if (!item) {
return undefined;
}
const sessionId = String.fromCharCode(this._idPool++);
this._cache.set(sessionId, []);
return { sessionId, root: this._cacheAndConvertItem(sessionId, item) };
const sessionId = this._idPool.nextId();
this._cache.set(sessionId, new Map());
return this._cacheAndConvertItem(sessionId, item);
}
async provideCallsTo(itemId: string, token: CancellationToken): Promise<[extHostProtocol.ICallHierarchyItemDto, IRange[]][] | undefined> {
const item = this._itemFromCache(itemId);
async provideCallsTo(sessionId: string, itemId: string, token: CancellationToken): Promise<extHostProtocol.IIncomingCallDto[] | undefined> {
const item = this._itemFromCache(sessionId, itemId);
if (!item) {
throw new Error('missing call hierarchy item');
}
......@@ -1064,11 +1066,16 @@ class CallHierarchyAdapter {
if (!calls) {
return undefined;
}
return calls.map(call => (<[extHostProtocol.ICallHierarchyItemDto, IRange[]]>[this._cacheAndConvertItem(itemId, call.from), call.fromRanges.map(typeConvert.Range.from)]));
return calls.map(call => {
return {
from: this._cacheAndConvertItem(sessionId, call.from),
fromRanges: call.fromRanges.map(r => typeConvert.Range.from(r))
};
});
}
async provideCallsFrom(itemId: string, token: CancellationToken): Promise<[extHostProtocol.ICallHierarchyItemDto, IRange[]][] | undefined> {
const item = this._itemFromCache(itemId);
async provideCallsFrom(sessionId: string, itemId: string, token: CancellationToken): Promise<extHostProtocol.IOutgoingCallDto[] | undefined> {
const item = this._itemFromCache(sessionId, itemId);
if (!item) {
throw new Error('missing call hierarchy item');
}
......@@ -1076,7 +1083,12 @@ class CallHierarchyAdapter {
if (!calls) {
return undefined;
}
return calls.map(call => (<[extHostProtocol.ICallHierarchyItemDto, IRange[]]>[this._cacheAndConvertItem(itemId, call.to), call.fromRanges.map(typeConvert.Range.from)]));
return calls.map(call => {
return {
to: this._cacheAndConvertItem(sessionId, call.to),
fromRanges: call.fromRanges.map(r => typeConvert.Range.from(r))
};
});
}
releaseSession(sessionId: string): void {
......@@ -1085,9 +1097,10 @@ class CallHierarchyAdapter {
private _cacheAndConvertItem(itemOrSessionId: string, item: vscode.CallHierarchyItem): extHostProtocol.ICallHierarchyItemDto {
const sessionId = itemOrSessionId.charAt(0);
const array = this._cache.get(sessionId)!;
const map = this._cache.get(sessionId)!;
const dto: extHostProtocol.ICallHierarchyItemDto = {
id: sessionId + String.fromCharCode(array.length),
_sessionId: sessionId,
_itemId: map.size.toString(36),
name: item.name,
detail: item.detail,
kind: typeConvert.SymbolKind.from(item.kind),
......@@ -1095,17 +1108,13 @@ class CallHierarchyAdapter {
range: typeConvert.Range.from(item.range),
selectionRange: typeConvert.Range.from(item.selectionRange),
};
array.push(item);
map.set(dto._itemId, item);
return dto;
}
private _itemFromCache(itemId: string): vscode.CallHierarchyItem | undefined {
const sessionId = itemId.charAt(0);
const array = this._cache.get(sessionId);
if (!array) {
return undefined;
}
return array[itemId.charCodeAt(1)];
private _itemFromCache(sessionId: string, itemId: string): vscode.CallHierarchyItem | undefined {
const map = this._cache.get(sessionId);
return map && map.get(itemId);
}
}
......@@ -1193,7 +1202,7 @@ export class ExtHostLanguageFeatures implements extHostProtocol.ExtHostLanguageF
return ExtHostLanguageFeatures._handlePool++;
}
private _withAdapter<A, R>(handle: number, ctor: { new(...args: any[]): A }, callback: (adapter: A, extension: IExtensionDescription | undefined) => Promise<R>, fallbackValue: R): Promise<R> {
private _withAdapter<A, R>(handle: number, ctor: { new(...args: any[]): A; }, callback: (adapter: A, extension: IExtensionDescription | undefined) => Promise<R>, fallbackValue: R): Promise<R> {
const data = this._adapter.get(handle);
if (!data) {
return Promise.resolve(fallbackValue);
......@@ -1541,16 +1550,16 @@ export class ExtHostLanguageFeatures implements extHostProtocol.ExtHostLanguageF
return this._createDisposable(handle);
}
$prepareCallHierarchy(handle: number, resource: UriComponents, position: IPosition, token: CancellationToken): Promise<{ sessionId: string, root: extHostProtocol.ICallHierarchyItemDto } | undefined> {
$prepareCallHierarchy(handle: number, resource: UriComponents, position: IPosition, token: CancellationToken): Promise<extHostProtocol.ICallHierarchyItemDto | undefined> {
return this._withAdapter(handle, CallHierarchyAdapter, adapter => Promise.resolve(adapter.prepareSession(URI.revive(resource), position, token)), undefined);
}
$provideCallHierarchyIncomingCalls(handle: number, itemId: string, token: CancellationToken): Promise<[extHostProtocol.ICallHierarchyItemDto, IRange[]][] | undefined> {
return this._withAdapter(handle, CallHierarchyAdapter, adapter => adapter.provideCallsTo(itemId, token), undefined);
$provideCallHierarchyIncomingCalls(handle: number, sessionId: string, itemId: string, token: CancellationToken): Promise<extHostProtocol.IIncomingCallDto[] | undefined> {
return this._withAdapter(handle, CallHierarchyAdapter, adapter => adapter.provideCallsTo(sessionId, itemId, token), undefined);
}
$provideCallHierarchyOutgoingCalls(handle: number, itemId: string, token: CancellationToken): Promise<[extHostProtocol.ICallHierarchyItemDto, IRange[]][] | undefined> {
return this._withAdapter(handle, CallHierarchyAdapter, adapter => adapter.provideCallsFrom(itemId, token), undefined);
$provideCallHierarchyOutgoingCalls(handle: number, sessionId: string, itemId: string, token: CancellationToken): Promise<extHostProtocol.IOutgoingCallDto[] | undefined> {
return this._withAdapter(handle, CallHierarchyAdapter, adapter => adapter.provideCallsFrom(sessionId, itemId, token), undefined);
}
$releaseCallHierarchy(handle: number, sessionId: string): void {
......
......@@ -255,7 +255,7 @@ export namespace MarkdownString {
}
// extract uris into a separate object
const resUris: { [href: string]: UriComponents } = Object.create(null);
const resUris: { [href: string]: UriComponents; } = Object.create(null);
res.uris = resUris;
const collectUri = (href: string): string => {
......@@ -277,7 +277,7 @@ export namespace MarkdownString {
return res;
}
function _uriMassage(part: string, bucket: { [n: string]: UriComponents }): string {
function _uriMassage(part: string, bucket: { [n: string]: UriComponents; }): string {
if (!part) {
return part;
}
......@@ -513,7 +513,7 @@ export namespace WorkspaceEdit {
export namespace SymbolKind {
const _fromMapping: { [kind: number]: modes.SymbolKind } = Object.create(null);
const _fromMapping: { [kind: number]: modes.SymbolKind; } = Object.create(null);
_fromMapping[types.SymbolKind.File] = modes.SymbolKind.File;
_fromMapping[types.SymbolKind.Module] = modes.SymbolKind.Module;
_fromMapping[types.SymbolKind.Namespace] = modes.SymbolKind.Namespace;
......@@ -627,8 +627,8 @@ export namespace DocumentSymbol {
export namespace CallHierarchyItem {
export function to(item: extHostProtocol.ICallHierarchyItemDto): vscode.CallHierarchyItem {
return new types.CallHierarchyItem(
export function to(item: extHostProtocol.ICallHierarchyItemDto): types.CallHierarchyItem {
const result = new types.CallHierarchyItem(
SymbolKind.to(item.kind),
item.name,
item.detail || '',
......@@ -636,6 +636,31 @@ export namespace CallHierarchyItem {
Range.to(item.range),
Range.to(item.selectionRange)
);
result._sessionId = item._sessionId;
result._itemId = item._itemId;
return result;
}
}
export namespace CallHierarchyIncomingCall {
export function to(item: extHostProtocol.IIncomingCallDto): types.CallHierarchyIncomingCall {
return new types.CallHierarchyIncomingCall(
CallHierarchyItem.to(item.from),
item.fromRanges.map(r => Range.to(r))
);
}
}
export namespace CallHierarchyOutgoingCall {
export function to(item: extHostProtocol.IOutgoingCallDto): types.CallHierarchyOutgoingCall {
return new types.CallHierarchyOutgoingCall(
CallHierarchyItem.to(item.to),
item.fromRanges.map(r => Range.to(r))
);
}
}
......
......@@ -29,8 +29,8 @@ function es5ClassCompat(target: Function): any {
@es5ClassCompat
export class Disposable {
static from(...inDisposables: { dispose(): any }[]): Disposable {
let disposables: ReadonlyArray<{ dispose(): any }> | undefined = inDisposables;
static from(...inDisposables: { dispose(): any; }[]): Disposable {
let disposables: ReadonlyArray<{ dispose(): any; }> | undefined = inDisposables;
return new Disposable(function () {
if (disposables) {
for (const disposable of disposables) {
......@@ -333,9 +333,9 @@ export class Range {
return this._start.line === this._end.line;
}
with(change: { start?: Position, end?: Position }): Range;
with(change: { start?: Position, end?: Position; }): Range;
with(start?: Position, end?: Position): Range;
with(startOrChange: Position | undefined | { start?: Position, end?: Position }, end: Position = this.end): Range {
with(startOrChange: Position | undefined | { start?: Position, end?: Position; }, end: Position = this.end): Range {
if (startOrChange === null || end === null) {
throw illegalArgument();
......@@ -589,15 +589,15 @@ export class WorkspaceEdit implements vscode.WorkspaceEdit {
private _edits = new Array<IFileOperation | IFileTextEdit>();
renameFile(from: vscode.Uri, to: vscode.Uri, options?: { overwrite?: boolean, ignoreIfExists?: boolean }): void {
renameFile(from: vscode.Uri, to: vscode.Uri, options?: { overwrite?: boolean, ignoreIfExists?: boolean; }): void {
this._edits.push({ _type: 1, from, to, options });
}
createFile(uri: vscode.Uri, options?: { overwrite?: boolean, ignoreIfExists?: boolean }): void {
createFile(uri: vscode.Uri, options?: { overwrite?: boolean, ignoreIfExists?: boolean; }): void {
this._edits.push({ _type: 1, from: undefined, to: uri, options });
}
deleteFile(uri: vscode.Uri, options?: { recursive?: boolean, ignoreIfNotExists?: boolean }): void {
deleteFile(uri: vscode.Uri, options?: { recursive?: boolean, ignoreIfNotExists?: boolean; }): void {
this._edits.push({ _type: 1, from: uri, to: undefined, options });
}
......@@ -1142,6 +1142,10 @@ export class SelectionRange {
}
export class CallHierarchyItem {
_sessionId: string;
_itemId: string;
kind: SymbolKind;
name: string;
detail?: string;
......@@ -1496,7 +1500,7 @@ export class Color {
}
}
export type IColorFormat = string | { opaque: string, transparent: string };
export type IColorFormat = string | { opaque: string, transparent: string; };
@es5ClassCompat
export class ColorInformation {
......@@ -2051,13 +2055,13 @@ export class TreeItem {
label?: string | vscode.TreeItemLabel;
resourceUri?: URI;
iconPath?: string | URI | { light: string | URI; dark: string | URI };
iconPath?: string | URI | { light: string | URI; dark: string | URI; };
command?: vscode.Command;
contextValue?: string;
tooltip?: string;
constructor(label: string | vscode.TreeItemLabel, collapsibleState?: vscode.TreeItemCollapsibleState)
constructor(resourceUri: URI, collapsibleState?: vscode.TreeItemCollapsibleState)
constructor(label: string | vscode.TreeItemLabel, collapsibleState?: vscode.TreeItemCollapsibleState);
constructor(resourceUri: URI, collapsibleState?: vscode.TreeItemCollapsibleState);
constructor(arg1: string | vscode.TreeItemLabel | URI, public collapsibleState: vscode.TreeItemCollapsibleState = TreeItemCollapsibleState.None) {
if (URI.isUri(arg1)) {
this.resourceUri = arg1;
......
......@@ -9,10 +9,14 @@ import { ITextModel } from 'vs/editor/common/model';
import { CancellationToken } from 'vs/base/common/cancellation';
import { LanguageFeatureRegistry } from 'vs/editor/common/modes/languageFeatureRegistry';
import { URI } from 'vs/base/common/uri';
import { IPosition } from 'vs/editor/common/core/position';
import { IPosition, Position } from 'vs/editor/common/core/position';
import { isNonEmptyArray } from 'vs/base/common/arrays';
import { onUnexpectedExternalError } from 'vs/base/common/errors';
import { IDisposable } from 'vs/base/common/lifecycle';
import { IDisposable, dispose } from 'vs/base/common/lifecycle';
import { CommandsRegistry } from 'vs/platform/commands/common/commands';
import { assertType } from 'vs/base/common/types';
import { IModelService } from 'vs/editor/common/services/modelService';
import { ITextModelService } from 'vs/editor/common/services/resolverService';
export const enum CallHierarchyDirection {
CallsTo = 1,
......@@ -20,7 +24,8 @@ export const enum CallHierarchyDirection {
}
export interface CallHierarchyItem {
id: string;
_sessionId: string;
_itemId: string;
kind: SymbolKind;
name: string;
detail?: string;
......@@ -87,10 +92,11 @@ export class CallHierarchyModel {
if (!session) {
return undefined;
}
return new CallHierarchyModel(provider, session.root, new RefCountedDisposabled(session));
return new CallHierarchyModel(session.root._sessionId, provider, session.root, new RefCountedDisposabled(session));
}
private constructor(
readonly id: string,
readonly provider: CallHierarchyProvider,
readonly root: CallHierarchyItem,
readonly ref: RefCountedDisposabled,
......@@ -104,7 +110,7 @@ export class CallHierarchyModel {
const that = this;
return new class extends CallHierarchyModel {
constructor() {
super(that.provider, item, that.ref.acquire());
super(that.id, that.provider, item, that.ref.acquire());
}
};
}
......@@ -134,3 +140,71 @@ export class CallHierarchyModel {
}
}
// --- API command support
const _models = new Map<string, CallHierarchyModel>();
CommandsRegistry.registerCommand('_executePrepareCallHierarchy', async (accessor, ...args) => {
const [resource, position] = args;
assertType(URI.isUri(resource));
assertType(Position.isIPosition(position));
const modelService = accessor.get(IModelService);
let textModel = modelService.getModel(resource);
let textModelReference: IDisposable | undefined;
if (!textModel) {
const textModelService = accessor.get(ITextModelService);
const result = await textModelService.createModelReference(resource);
textModel = result.object.textEditorModel;
textModelReference = result;
}
try {
const model = await CallHierarchyModel.create(textModel, position, CancellationToken.None);
if (!model) {
return undefined;
}
//
_models.set(model.id, model);
_models.forEach((value, key, map) => {
if (map.size > 10) {
value.dispose();
_models.delete(key);
}
});
return model.root;
} finally {
dispose(textModelReference);
}
});
function isCallHierarchyItemDto(obj: any): obj is CallHierarchyItem {
return true;
}
CommandsRegistry.registerCommand('_executeProvideIncomingCalls', async (_accessor, ...args) => {
const [item] = args;
assertType(isCallHierarchyItemDto(item));
// find model
const model = _models.get(item._sessionId);
if (!model) {
return undefined;
}
return model.resolveIncomingCalls(item, CancellationToken.None);
});
CommandsRegistry.registerCommand('_executeProvideOutgoingCalls', async (_accessor, ...args) => {
const [item] = args;
assertType(isCallHierarchyItemDto(item));
// find model
const model = _models.get(item._sessionId);
if (!model) {
return undefined;
}
return model.resolveOutgoingCalls(item, CancellationToken.None);
});
......@@ -26,10 +26,10 @@ export class ExtensionDependencyChecker extends Disposable implements IWorkbench
@IHostService private readonly hostService: IHostService
) {
super();
CommandsRegistry.registerCommand('workbench.extensions.installMissingDepenencies', () => this.installMissingDependencies());
CommandsRegistry.registerCommand('workbench.extensions.installMissingDependencies', () => this.installMissingDependencies());
MenuRegistry.appendMenuItem(MenuId.CommandPalette, {
command: {
id: 'workbench.extensions.installMissingDepenencies',
id: 'workbench.extensions.installMissingDependencies',
category: localize('extensions', "Extensions"),
title: localize('auto install missing deps', "Install Missing Dependencies")
}
......
......@@ -119,20 +119,6 @@ export class MarkersFilterAction extends Action {
}
}
focus(): void {
this._onFocus.fire();
}
layout(width: number): void {
if (width > 600) {
this.class = 'markers-panel-action-filter grow';
} else if (width < 400) {
this.class = 'markers-panel-action-filter small';
} else {
this.class = 'markers-panel-action-filter';
}
}
private _showWarnings: boolean = true;
get showWarnings(): boolean {
return this._showWarnings;
......@@ -165,6 +151,20 @@ export class MarkersFilterAction extends Action {
this._onDidChange.fire(<IMarkersFilterActionChangeEvent>{ showInfos: true });
}
}
focus(): void {
this._onFocus.fire();
}
layout(width: number): void {
if (width > 600) {
this.class = 'markers-panel-action-filter grow';
} else if (width < 400) {
this.class = 'markers-panel-action-filter small';
} else {
this.class = 'markers-panel-action-filter';
}
}
}
export interface IMarkerFilterController {
......
......@@ -67,13 +67,13 @@ suite('ExtHostLanguageFeatureCommands', function () {
rpcProtocol = new TestRPCProtocol();
instantiationService.stub(ICommandService, {
_serviceBrand: undefined,
executeCommand(id: string, args: any): any {
executeCommand(id: string, ...args: any): any {
const command = CommandsRegistry.getCommands().get(id);
if (!command) {
return Promise.reject(new Error(id + ' NOT known'));
}
const { handler } = command;
return Promise.resolve(instantiationService.invokeFunction(handler, args));
return Promise.resolve(instantiationService.invokeFunction(handler, ...args));
}
});
instantiationService.stub(IMarkerService, new MarkerService());
......@@ -856,4 +856,46 @@ suite('ExtHostLanguageFeatureCommands', function () {
assert.equal(value.length, 1);
assert.ok(value[0].parent);
});
// --- call hierarcht
test('CallHierarchy, back and forth', async function () {
disposables.push(extHost.registerCallHierarchyProvider(nullExtensionDescription, defaultSelector, new class implements vscode.CallHierarchyProvider {
prepareCallHierarchy(document: vscode.TextDocument, position: vscode.Position, ): vscode.ProviderResult<vscode.CallHierarchyItem> {
return new types.CallHierarchyItem(types.SymbolKind.Constant, 'ROOT', 'ROOT', document.uri, new types.Range(0, 0, 0, 0), new types.Range(0, 0, 0, 0));
}
provideCallHierarchyIncomingCalls(item: vscode.CallHierarchyItem, token: vscode.CancellationToken): vscode.ProviderResult<vscode.CallHierarchyIncomingCall[]> {
return [new types.CallHierarchyIncomingCall(
new types.CallHierarchyItem(types.SymbolKind.Constant, 'INCOMING', 'INCOMING', item.uri, new types.Range(0, 0, 0, 0), new types.Range(0, 0, 0, 0)),
[new types.Range(0, 0, 0, 0)]
)];
}
provideCallHierarchyOutgoingCalls(item: vscode.CallHierarchyItem, token: vscode.CancellationToken): vscode.ProviderResult<vscode.CallHierarchyOutgoingCall[]> {
return [new types.CallHierarchyOutgoingCall(
new types.CallHierarchyItem(types.SymbolKind.Constant, 'OUTGOING', 'OUTGOING', item.uri, new types.Range(0, 0, 0, 0), new types.Range(0, 0, 0, 0)),
[new types.Range(0, 0, 0, 0)]
)];
}
}));
await rpcProtocol.sync();
const root = await commands.executeCommand<vscode.CallHierarchyItem>('vscode.prepareCallHierarchy', model.uri, new types.Position(0, 0));
assert.ok(root);
assert.equal(root.name, 'ROOT');
const incoming = await commands.executeCommand<vscode.CallHierarchyIncomingCall[]>('vscode.provideIncomingCalls', root);
assert.equal(incoming.length, 1);
assert.equal(incoming[0].from.name, 'INCOMING');
const outgoing = await commands.executeCommand<vscode.CallHierarchyOutgoingCall[]>('vscode.provideOutgoingCalls', root);
assert.equal(outgoing.length, 1);
assert.equal(outgoing[0].to.name, 'OUTGOING');
});
});
......@@ -195,6 +195,20 @@
resolved "https://registry.yarnpkg.com/@types/winreg/-/winreg-1.2.30.tgz#91d6710e536d345b9c9b017c574cf6a8da64c518"
integrity sha1-kdZxDlNtNFucmwF8V0z2qNpkxRg=
"@types/yauzl@^2.9.1":
version "2.9.1"
resolved "https://registry.yarnpkg.com/@types/yauzl/-/yauzl-2.9.1.tgz#d10f69f9f522eef3cf98e30afb684a1e1ec923af"
integrity sha512-A1b8SU4D10uoPjwb0lnHmmu8wZhR9d+9o2PKBQT2jU5YPTKsxac6M2qGAdY7VcL+dHHhARVUDmeg0rOrcd9EjA==
dependencies:
"@types/node" "*"
"@types/yazl@^2.4.2":
version "2.4.2"
resolved "https://registry.yarnpkg.com/@types/yazl/-/yazl-2.4.2.tgz#d5f8a4752261badbf1a36e8b49e042dc18ec84bc"
integrity sha512-T+9JH8O2guEjXNxqmybzQ92mJUh2oCwDDMSSimZSe1P+pceZiFROZLYmcbqkzV5EUwz6VwcKXCO2S2yUpra6XQ==
dependencies:
"@types/node" "*"
"@webassemblyjs/ast@1.5.13":
version "1.5.13"
resolved "https://registry.yarnpkg.com/@webassemblyjs/ast/-/ast-1.5.13.tgz#81155a570bd5803a30ec31436bc2c9c0ede38f25"
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册