perf(ngcc): shortcircuit tokenizing in ESM dependency host (#37639)
This dependency host tokenizes files to identify all the imported paths. This commit calculates the last place in the source code where there can be an import path; it then exits the tokenization when we get to this point in the file. Testing with a reasonably large project showed that the tokenizer spends about 2/3 as much time scanning files. For example in a "noop" hot run of ngcc using the program-based entry-point finder the percentage of time spent in the `scan()` function of the TS tokenizer goes down from 9.9% to 6.6%. PR Close #37639
This commit is contained in:
parent
d0437b3be0
commit
bd7f440357
@ -47,10 +47,14 @@ export class EsmDependencyHost extends DependencyHostBase {
|
|||||||
const templateStack: ts.SyntaxKind[] = [];
|
const templateStack: ts.SyntaxKind[] = [];
|
||||||
let lastToken: ts.SyntaxKind = ts.SyntaxKind.Unknown;
|
let lastToken: ts.SyntaxKind = ts.SyntaxKind.Unknown;
|
||||||
let currentToken: ts.SyntaxKind = ts.SyntaxKind.Unknown;
|
let currentToken: ts.SyntaxKind = ts.SyntaxKind.Unknown;
|
||||||
|
const stopAtIndex = findLastPossibleImportOrReexport(fileContents);
|
||||||
|
|
||||||
this.scanner.setText(fileContents);
|
this.scanner.setText(fileContents);
|
||||||
|
|
||||||
while ((currentToken = this.scanner.scan()) !== ts.SyntaxKind.EndOfFileToken) {
|
while ((currentToken = this.scanner.scan()) !== ts.SyntaxKind.EndOfFileToken) {
|
||||||
|
if (this.scanner.getTokenPos() > stopAtIndex) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
switch (currentToken) {
|
switch (currentToken) {
|
||||||
case ts.SyntaxKind.TemplateHead:
|
case ts.SyntaxKind.TemplateHead:
|
||||||
// TemplateHead indicates the beginning of a backticked string
|
// TemplateHead indicates the beginning of a backticked string
|
||||||
@ -266,6 +270,9 @@ export function hasImportOrReexportStatements(source: string): boolean {
|
|||||||
return /(?:import|export)[\s\S]+?(["'])(?:\\\1|.)+?\1/.test(source);
|
return /(?:import|export)[\s\S]+?(["'])(?:\\\1|.)+?\1/.test(source);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function findLastPossibleImportOrReexport(source: string): number {
|
||||||
|
return Math.max(source.lastIndexOf('import'), source.lastIndexOf(' from '));
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Check whether the given statement is an import with a string literal module specifier.
|
* Check whether the given statement is an import with a string literal module specifier.
|
||||||
|
Loading…
x
Reference in New Issue
Block a user