Skip to content

Commit 4889571

Browse files
committed
perf: lazy calculation TS plugin proxy, TS program proxy
#507
1 parent 35f27bf commit 4889571

File tree

1 file changed

+74
-53
lines changed

1 file changed

+74
-53
lines changed

packages/vscode-vue-languageservice/src/languageService.ts

+74-53
Original file line numberDiff line numberDiff line change
@@ -222,57 +222,8 @@ export function createLanguageService(
222222
const findDefinition = definitions.register(context);
223223
const renames = rename.register(context);
224224

225-
// ts plugin proxy
226-
const _tsPluginApis = tsPluginApis.register(context);
227-
const tsPlugin: Partial<ts.LanguageService> = {
228-
getSemanticDiagnostics: apiHook(scriptTsLsRaw.getSemanticDiagnostics, false),
229-
getEncodedSemanticClassifications: apiHook(scriptTsLsRaw.getEncodedSemanticClassifications, false),
230-
getCompletionsAtPosition: apiHook(_tsPluginApis.getCompletionsAtPosition, false),
231-
getCompletionEntryDetails: apiHook(scriptTsLsRaw.getCompletionEntryDetails, false), // not sure
232-
getCompletionEntrySymbol: apiHook(scriptTsLsRaw.getCompletionEntrySymbol, false), // not sure
233-
getQuickInfoAtPosition: apiHook(scriptTsLsRaw.getQuickInfoAtPosition, false),
234-
getSignatureHelpItems: apiHook(scriptTsLsRaw.getSignatureHelpItems, false),
235-
getRenameInfo: apiHook(scriptTsLsRaw.getRenameInfo, false),
236-
237-
findRenameLocations: apiHook(_tsPluginApis.findRenameLocations, true),
238-
getDefinitionAtPosition: apiHook(_tsPluginApis.getDefinitionAtPosition, false),
239-
getDefinitionAndBoundSpan: apiHook(_tsPluginApis.getDefinitionAndBoundSpan, false),
240-
getTypeDefinitionAtPosition: apiHook(_tsPluginApis.getTypeDefinitionAtPosition, false),
241-
getImplementationAtPosition: apiHook(_tsPluginApis.getImplementationAtPosition, false),
242-
getReferencesAtPosition: apiHook(_tsPluginApis.getReferencesAtPosition, true),
243-
findReferences: apiHook(_tsPluginApis.findReferences, true),
244-
245-
// TODO: now is handle by vue server
246-
// prepareCallHierarchy: apiHook(tsLanguageService.rawLs.prepareCallHierarchy, false),
247-
// provideCallHierarchyIncomingCalls: apiHook(tsLanguageService.rawLs.provideCallHierarchyIncomingCalls, false),
248-
// provideCallHierarchyOutgoingCalls: apiHook(tsLanguageService.rawLs.provideCallHierarchyOutgoingCalls, false),
249-
// getEditsForFileRename: apiHook(tsLanguageService.rawLs.getEditsForFileRename, false),
250-
251-
// TODO
252-
// getCodeFixesAtPosition: apiHook(tsLanguageService.rawLs.getCodeFixesAtPosition, false),
253-
// getCombinedCodeFix: apiHook(tsLanguageService.rawLs.getCombinedCodeFix, false),
254-
// applyCodeActionCommand: apiHook(tsLanguageService.rawLs.applyCodeActionCommand, false),
255-
// getApplicableRefactors: apiHook(tsLanguageService.rawLs.getApplicableRefactors, false),
256-
// getEditsForRefactor: apiHook(tsLanguageService.rawLs.getEditsForRefactor, false),
257-
};
258-
259-
// ts program proxy
260-
const tsProgram = scriptTsLsRaw.getProgram(); // TODO: handle template ls?
261-
if (!tsProgram) throw '!tsProgram';
262-
263-
const tsProgramApis_2 = tsProgramApis.register(context);
264-
const tsProgramApis_3: Partial<typeof tsProgram> = {
265-
emit: apiHook(tsProgramApis_2.emit),
266-
getRootFileNames: apiHook(tsProgramApis_2.getRootFileNames),
267-
getSemanticDiagnostics: apiHook(tsProgramApis_2.getSemanticDiagnostics),
268-
getSyntacticDiagnostics: apiHook(tsProgramApis_2.getSyntacticDiagnostics),
269-
getGlobalDiagnostics: apiHook(tsProgramApis_2.getGlobalDiagnostics),
270-
};
271-
const tsProgramProxy = new Proxy(tsProgram, {
272-
get: (target: any, property: keyof typeof tsProgram) => {
273-
return tsProgramApis_3[property] || target[property];
274-
},
275-
});
225+
let tsPluginProxy: ReturnType<typeof createTsPluginProxy> | undefined;
226+
let tsProgramProxy: ReturnType<typeof createTsProgramProxy> | undefined;;
276227

277228
return {
278229
doValidation: publicApiHook(diagnostics.register(context, () => update(true)), false, false),
@@ -307,8 +258,18 @@ export function createLanguageService(
307258

308259
__internal__: {
309260
rootPath: vueHost.getCurrentDirectory(),
310-
tsPlugin,
311-
tsProgramProxy,
261+
get tsPlugin() {
262+
if (!tsPluginProxy) {
263+
tsPluginProxy = createTsPluginProxy();
264+
}
265+
return tsPluginProxy;
266+
},
267+
get tsProgramProxy() {
268+
if (!tsProgramProxy) {
269+
tsProgramProxy = createTsProgramProxy();
270+
}
271+
return tsProgramProxy;
272+
},
312273
context,
313274
onInitProgress(cb: (p: number) => void) {
314275
initProgressCallback.push(cb);
@@ -326,6 +287,66 @@ export function createLanguageService(
326287
},
327288
};
328289

290+
function createTsPluginProxy() {
291+
292+
// ts plugin proxy
293+
const _tsPluginApis = tsPluginApis.register(context);
294+
const tsPlugin: Partial<ts.LanguageService> = {
295+
getSemanticDiagnostics: apiHook(scriptTsLsRaw.getSemanticDiagnostics, false),
296+
getEncodedSemanticClassifications: apiHook(scriptTsLsRaw.getEncodedSemanticClassifications, false),
297+
getCompletionsAtPosition: apiHook(_tsPluginApis.getCompletionsAtPosition, false),
298+
getCompletionEntryDetails: apiHook(scriptTsLsRaw.getCompletionEntryDetails, false), // not sure
299+
getCompletionEntrySymbol: apiHook(scriptTsLsRaw.getCompletionEntrySymbol, false), // not sure
300+
getQuickInfoAtPosition: apiHook(scriptTsLsRaw.getQuickInfoAtPosition, false),
301+
getSignatureHelpItems: apiHook(scriptTsLsRaw.getSignatureHelpItems, false),
302+
getRenameInfo: apiHook(scriptTsLsRaw.getRenameInfo, false),
303+
304+
findRenameLocations: apiHook(_tsPluginApis.findRenameLocations, true),
305+
getDefinitionAtPosition: apiHook(_tsPluginApis.getDefinitionAtPosition, false),
306+
getDefinitionAndBoundSpan: apiHook(_tsPluginApis.getDefinitionAndBoundSpan, false),
307+
getTypeDefinitionAtPosition: apiHook(_tsPluginApis.getTypeDefinitionAtPosition, false),
308+
getImplementationAtPosition: apiHook(_tsPluginApis.getImplementationAtPosition, false),
309+
getReferencesAtPosition: apiHook(_tsPluginApis.getReferencesAtPosition, true),
310+
findReferences: apiHook(_tsPluginApis.findReferences, true),
311+
312+
// TODO: now is handle by vue server
313+
// prepareCallHierarchy: apiHook(tsLanguageService.rawLs.prepareCallHierarchy, false),
314+
// provideCallHierarchyIncomingCalls: apiHook(tsLanguageService.rawLs.provideCallHierarchyIncomingCalls, false),
315+
// provideCallHierarchyOutgoingCalls: apiHook(tsLanguageService.rawLs.provideCallHierarchyOutgoingCalls, false),
316+
// getEditsForFileRename: apiHook(tsLanguageService.rawLs.getEditsForFileRename, false),
317+
318+
// TODO
319+
// getCodeFixesAtPosition: apiHook(tsLanguageService.rawLs.getCodeFixesAtPosition, false),
320+
// getCombinedCodeFix: apiHook(tsLanguageService.rawLs.getCombinedCodeFix, false),
321+
// applyCodeActionCommand: apiHook(tsLanguageService.rawLs.applyCodeActionCommand, false),
322+
// getApplicableRefactors: apiHook(tsLanguageService.rawLs.getApplicableRefactors, false),
323+
// getEditsForRefactor: apiHook(tsLanguageService.rawLs.getEditsForRefactor, false),
324+
};
325+
326+
return tsPlugin;
327+
}
328+
function createTsProgramProxy() {
329+
330+
// ts program proxy
331+
const tsProgram = scriptTsLsRaw.getProgram(); // TODO: handle template ls?
332+
if (!tsProgram) throw '!tsProgram';
333+
334+
const tsProgramApis_2 = tsProgramApis.register(context);
335+
const tsProgramApis_3: Partial<typeof tsProgram> = {
336+
emit: apiHook(tsProgramApis_2.emit),
337+
getRootFileNames: apiHook(tsProgramApis_2.getRootFileNames),
338+
getSemanticDiagnostics: apiHook(tsProgramApis_2.getSemanticDiagnostics),
339+
getSyntacticDiagnostics: apiHook(tsProgramApis_2.getSyntacticDiagnostics),
340+
getGlobalDiagnostics: apiHook(tsProgramApis_2.getGlobalDiagnostics),
341+
};
342+
const tsProgramProxy = new Proxy<ts.Program>(tsProgram, {
343+
get: (target: any, property: keyof typeof tsProgram) => {
344+
return tsProgramApis_3[property] || target[property];
345+
},
346+
});
347+
348+
return tsProgramProxy;
349+
}
329350
function isTemplateScriptPosition(uri: string, pos: vscode.Position) {
330351

331352
const sourceFile = sourceFiles.get(uri);

0 commit comments

Comments
 (0)