提交 69c9edeb 编写于 作者: J Johannes Rieken

prefix stack with extension id, #32766

上级 d30567bd
......@@ -168,6 +168,24 @@ export function transformErrorForSerialization(error: any): any {
return error;
}
// see https://github.com/v8/v8/wiki/Stack%20Trace%20API#basic-stack-traces
export interface V8CallSite {
getThis(): any;
getTypeName(): string;
getFunction(): string;
getFunctionName(): string;
getMethodName(): string;
getFileName(): string;
getLineNumber(): number;
getColumnNumber(): number;
getEvalOrigin(): string;
isToplevel(): boolean;
isEval(): boolean;
isNative(): boolean;
isConstructor(): boolean;
toString(): string;
}
const canceledName = 'Canceled';
/**
......
......@@ -47,7 +47,6 @@ import { ITelemetryService } from 'vs/platform/telemetry/common/telemetry';
import { CancellationTokenSource } from 'vs/base/common/cancellation';
import * as vscode from 'vscode';
import * as paths from 'vs/base/common/paths';
import { realpath } from 'fs';
import { MainContext, ExtHostContext, IInitData } from './extHost.protocol';
import * as languageConfiguration from 'vs/editor/common/modes/languageConfiguration';
import { TextEditorCursorStyle } from 'vs/editor/common/config/editorOptions';
......@@ -621,30 +620,7 @@ class Extension<T> implements vscode.Extension<T> {
}
export function initializeExtensionApi(extensionService: ExtHostExtensionService, apiFactory: IExtensionApiFactory): TPromise<void> {
return createExtensionPathIndex(extensionService).then(trie => defineAPI(apiFactory, trie));
}
function createExtensionPathIndex(extensionService: ExtHostExtensionService): TPromise<TrieMap<IExtensionDescription>> {
// create trie to enable fast 'filename -> extension id' look up
const trie = new TrieMap<IExtensionDescription>();
const extensions = extensionService.getAllExtensionDescriptions().map(ext => {
if (!ext.main) {
return undefined;
}
return new TPromise((resolve, reject) => {
realpath(ext.extensionFolderPath, (err, path) => {
if (err) {
reject(err);
} else {
trie.insert(path, ext);
resolve(void 0);
}
});
});
});
return TPromise.join(extensions).then(() => trie);
return extensionService.getExtensionPathIndex().then(trie => defineAPI(apiFactory, trie));
}
function defineAPI(factory: IExtensionApiFactory, extensionPaths: TrieMap<IExtensionDescription>): void {
......
......@@ -18,6 +18,8 @@ import { MainContext, MainThreadExtensionServiceShape, IWorkspaceData, IEnvironm
import { IExtensionMemento, ExtensionsActivator, ActivatedExtension, IExtensionAPI, IExtensionContext, EmptyExtension, IExtensionModule } from "vs/workbench/api/node/extHostExtensionActivator";
import { Barrier } from "vs/workbench/services/extensions/node/barrier";
import { ExtHostThreadService } from "vs/workbench/services/thread/node/extHostThreadService";
import { realpath } from 'fs';
import { TrieMap } from "vs/base/common/map";
class ExtensionMemento implements IExtensionMemento {
......@@ -115,7 +117,7 @@ export class ExtHostExtensionService implements ExtHostExtensionServiceShape {
private readonly _storagePath: ExtensionStoragePath;
private readonly _proxy: MainThreadExtensionServiceShape;
private _activator: ExtensionsActivator;
private _extensionPathIndex: TPromise<TrieMap<IExtensionDescription>>;
/**
* This class is constructed manually because it is a service, so it doesn't use any ctor injection
*/
......@@ -202,6 +204,31 @@ export class ExtHostExtensionService implements ExtHostExtensionServiceShape {
}
}
// create trie to enable fast 'filename -> extension id' look up
public getExtensionPathIndex(): TPromise<TrieMap<IExtensionDescription>> {
if (!this._extensionPathIndex) {
const trie = new TrieMap<IExtensionDescription>();
const extensions = this.getAllExtensionDescriptions().map(ext => {
if (!ext.main) {
return undefined;
}
return new TPromise((resolve, reject) => {
realpath(ext.extensionFolderPath, (err, path) => {
if (err) {
reject(err);
} else {
trie.insert(path, ext);
resolve(void 0);
}
});
});
});
this._extensionPathIndex = TPromise.join(extensions).then(() => trie);
}
return this._extensionPathIndex;
}
public deactivate(extensionId: string): TPromise<void> {
let result: TPromise<void> = TPromise.as(void 0);
......
......@@ -12,6 +12,7 @@ import { join } from 'path';
import { RPCProtocol } from 'vs/workbench/services/extensions/node/rpcProtocol';
import { ExtHostExtensionService } from 'vs/workbench/api/node/extHostExtensionService';
import { ExtHostThreadService } from 'vs/workbench/services/thread/node/extHostThreadService';
import { IExtensionDescription } from "vs/platform/extensions/common/extensions";
import { QueryType, ISearchQuery } from 'vs/platform/search/common/search';
import { DiskSearch } from 'vs/workbench/services/search/node/searchService';
import { RemoteTelemetryService } from 'vs/workbench/api/node/extHostTelemetry';
......@@ -49,9 +50,27 @@ export class ExtensionHostMain {
const telemetryService = new RemoteTelemetryService('pluginHostTelemetry', threadService);
this._extensionService = new ExtHostExtensionService(initData, threadService, telemetryService);
// Error forwarding
// error forwarding and stack trace scanning
this._extensionService.getExtensionPathIndex().then(map => {
(<any>Error).prepareStackTrace = (error: Error, stackTrace: errors.V8CallSite[]) => {
let stackTraceMessage = '';
let extension: IExtensionDescription;
for (const call of stackTrace) {
stackTraceMessage += `\n\tat ${call.toString()}`;
extension = extension || map.findSubstr(stackTrace[0].getFileName());
}
let name = error.name || 'Error';
if (extension) {
name = `[${extension.id}] ${name}`;
}
return `${name}: ${error.message}${stackTraceMessage}`;
};
});
const mainThreadErrors = threadService.get(MainContext.MainThreadErrors);
errors.setUnexpectedErrorHandler(err => mainThreadErrors.$onUnexpectedExtHostError(errors.transformErrorForSerialization(err)));
errors.setUnexpectedErrorHandler(err => {
const data = errors.transformErrorForSerialization(err);
mainThreadErrors.$onUnexpectedExtHostError(data);
});
// Configure the watchdog to kill our process if the JS event loop is unresponsive for more than 10s
if (!initData.environment.isExtensionDevelopmentDebug) {
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册