fix(language-service): do not return external template that does not exist (#39898)

There is a bug in tsserver that causes it to crash when it tries to create
script info for an external template that does not exist.

I've submitted an upstream PR
https://github.com/microsoft/TypeScript/pull/41737 to fix this, but before
the commit lands in the stable release, we'll have to workaround the issue
in language service.

Close https://github.com/angular/vscode-ng-language-service/issues/1001

PR Close #39898
This commit is contained in:
Keen Yee Liau 2020-11-30 16:49:06 -08:00 committed by Misko Hevery
parent 8d613c1d42
commit 2b84882ab0
2 changed files with 17 additions and 2 deletions

View File

@ -29,8 +29,16 @@ export function getExternalFiles(project: tss.server.Project): string[] {
return []; return [];
} }
const ngLsHost = PROJECT_MAP.get(project); const ngLsHost = PROJECT_MAP.get(project);
ngLsHost?.getAnalyzedModules(); if (ngLsHost === undefined) {
return ngLsHost?.getExternalTemplates() || []; return [];
}
ngLsHost.getAnalyzedModules();
return ngLsHost.getExternalTemplates().filter(fileName => {
// TODO(kyliau): Remove this when the following PR lands on the version of
// TypeScript used in this repo.
// https://github.com/microsoft/TypeScript/pull/41737
return project.fileExists(fileName);
});
} }
export function create(info: tss.server.PluginCreateInfo): tss.LanguageService { export function create(info: tss.server.PluginCreateInfo): tss.LanguageService {

View File

@ -21,6 +21,7 @@ const mockProject = {
}, },
}, },
hasRoots: () => true, hasRoots: () => true,
fileExists: () => true,
} as any; } as any;
describe('plugin', () => { describe('plugin', () => {
@ -136,6 +137,12 @@ describe('plugin', () => {
'/app/test.ng', '/app/test.ng',
]); ]);
}); });
it('should not return external template that does not exist', () => {
spyOn(mockProject, 'fileExists').and.returnValue(false);
const externalTemplates = getExternalFiles(mockProject);
expect(externalTemplates.length).toBe(0);
});
}); });
describe(`with config 'angularOnly = true`, () => { describe(`with config 'angularOnly = true`, () => {