4213e8d5f0
Shim generation was built on a lie. Shims are files added to the program which aren't original files authored by the user, but files authored effectively by the compiler. These fall into two categories: files which will be generated (like the .ngfactory shims we generate for View Engine compatibility) as well as files used internally in compilation (like the __ng_typecheck__.ts file). Previously, shim generation was driven by the `rootFiles` passed to the compiler as input. These are effectively the `files` listed in the `tsconfig.json`. Each shim generator (e.g. the `FactoryGenerator`) would examine the `rootFiles` and produce a list of shim file names which it would be responsible for generating. These names would then be added to the `rootFiles` when the program was created. The fatal flaw here is that `rootFiles` does not always account for all of the files in the program. In fact, it's quite rare that it does. Users don't typically specify every file directly in `files`. Instead, they rely on TypeScript, during program creation, starting with a few root files and transitively discovering all of the files in the program. This happens, however, during `ts.createProgram`, which is too late to add new files to the `rootFiles` list. As a result, shim generation was only including shims for files actually listed in the `tsconfig.json` file, and not for the transitive set of files in the user's program as it should. This commit completely rewrites shim generation to use a different technique for adding files to the program, inspired by View Engine's shim generator. In this new technique, as the program is being created and `ts.SourceFile`s are being requested from the `NgCompilerHost`, shims for those files are generated and a reference to them is patched onto the original file's `ts.SourceFile.referencedFiles`. This causes TS to think that the original file references the shim, and causes the shim to be included in the program. The original `referencedFiles` array is saved and restored after program creation, hiding this little hack from the rest of the system. The new shim generation engine differentiates between two kinds of shims: top-level shims (such as the flat module entrypoint file and __ng_typecheck__.ts) and per-file shims such as ngfactory or ngsummary files. The former are included via `rootFiles` as before, the latter are included via the `referencedFiles` of their corresponding original files. As a result of this change, shims are now correctly generated for all files in the program, not just the ones named in `tsconfig.json`. A few mitigating factors prevented this bug from being realized until now: * in g3, `files` does include the transitive closure of files in the program * in CLI apps, shims are not really used This change also makes use of a novel technique for associating information with source files: the use of an `NgExtension` `Symbol` to patch the information directly onto the AST object. This is used in several circumstances: * For shims, metadata about a `ts.SourceFile`'s status as a shim and its origins are held in the extension data. * For original files, the original `referencedFiles` are stashed in the extension data for later restoration. The main benefit of this technique is a lot less bookkeeping around `Map`s of `ts.SourceFile`s to various kinds of data, which need to be tracked/ invalidated as part of incremental builds. This technique is based on designs used internally in the TypeScript compiler and is serving as a prototype of this design in ngtsc. If it works well, it could have benefits across the rest of the compiler. PR Close #36211 |
||
---|---|---|
.circleci | ||
.devcontainer | ||
.github | ||
.vscode | ||
.yarn | ||
aio | ||
dev-infra | ||
docs | ||
goldens | ||
integration | ||
modules | ||
packages | ||
scripts | ||
third_party | ||
tools | ||
.bazelignore | ||
.bazelrc | ||
.bazelversion | ||
.clang-format | ||
.dev-infra.json | ||
.editorconfig | ||
.gitattributes | ||
.gitignore | ||
.mailmap | ||
.nvmrc | ||
.pullapprove.yml | ||
.yarnrc | ||
BUILD.bazel | ||
CHANGELOG.md | ||
CODE_OF_CONDUCT.md | ||
CONTRIBUTING.md | ||
LICENSE | ||
README.md | ||
WORKSPACE | ||
browser-providers.conf.js | ||
gulpfile.js | ||
karma-js.conf.js | ||
package.json | ||
protractor-perf.conf.js | ||
shims_for_IE.js | ||
test-events.js | ||
test-main.js | ||
tslint.json | ||
yarn.lock | ||
yarn.lock.readme.md |
README.md
Angular
Angular is a development platform for building mobile and desktop web applications using TypeScript/JavaScript and other languages.
Quickstart
Changelog
Learn about the latest improvements.
Want to help?
Want to file a bug, contribute some code, or improve documentation? Excellent! Read up on our guidelines for contributing and then check out one of our issues in the hotlist: community-help.