40 Commits

Author SHA1 Message Date
Paul Gschwendtner
25f763cff8 feat(core): support TypeScript 4.3 (#42022)
Switches the repository to TypeScript 4.3 and the latest
version of tslib. This involves updating the peer dependency
ranges on `typescript` for the compiler CLI and for the Bazel
package. Tests for new TypeScript features have been added to
ensure compatibility with Angular's ngtsc compiler.

PR Close #42022
2021-06-04 11:17:09 -07:00
Andrew Scott
a86ca4fe04 feat(language-service): Enable renaming of pipes (#40523)
This commit updates the logic in the LS renaming to handle renaming of
pipes, both from the name expression in the pipe metadata as well as
from the template.

The approach here is to introduce a new concept for renaming: an
"indirect" rename. In this type of rename, we find rename locations
in with the native TS Language Service using a different node than the
one we are renaming. Using pipes as an example, if we want to rename the
pipe name from the string literal expression, we use the transform
method to find rename locations rather than the string literal itself
(which will not return any results because it's just a string).

So the general approach is:
* Determine the details about the requested rename location, i.e. the
  targeted template node and symbol for a template rename, or the TS
  node for a rename outside a template.
* Using the details of the location, determine if the node is attempting
  to rename something that is an indirect rename (pipes, selectors,
  bindings). Other renames are considered "direct" and we use whatever
  results the native TSLS returns for the rename locations.
* In the case of indirect renames, we throw out results that do not
  appear in the templates (in this case, the shim files). These results will be
  for the "indirect" rename that we don't want to touch, but are only
  using to find template results.
* Create an additional rename result for the string literal expression
  that is used for the input/output alias, the pipe name, or the
  selector.

 Note that renaming is moving towards being much more accurate in its
 results than "find references". When the approach for renaming
 stabilizes, we may want to then port the changes back to being shared
 with the approach for retrieving references.

PR Close #40523
2021-05-06 17:54:13 -04:00
Zach Arend
fe5bf7f53f fix(compiler-cli): autocomplete literal types in templates. (#41456) (#41645)
This adds string literals, number literals, `true`, `false`, `null` and
`undefined` to autocomplete results in templates.

For example, when completing an input of union type.

Component: `@Input('input') input!: 'a'|'b'|null;`
Template: `[input]="|"`

Provide `'a'`, `'b'`, and `null` as autocompletion entries.

Previously we did not include literal types because we only included
results from the component context (`ctx.`) and the template scope.

This is the second attempt at this. The first attempt is in
1d12c50f63f90c91636185b2287e31e9c0291121 and it was reverted in 75f881e078150b0d095f2c54a916fc67a10444f6.

PR Close #41645
2021-04-16 08:54:27 -07:00
Joey Perrott
0bc539af29 Revert "fix(compiler-cli): autocomplete literal types in templates. (#41456)" (#41623)
This reverts commit 1d12c50f63f90c91636185b2287e31e9c0291121.

PR Close #41623
2021-04-14 09:16:34 -07:00
Zach Arend
1d12c50f63 fix(compiler-cli): autocomplete literal types in templates. (#41456)
This adds string literals, number literals, `true`, `false`, `null` and
`undefined` to autocomplete results in templates.

For example, when completing an input of union type.

Component: `@Input('input') input!: 'a'|'b'|null;`
Template: `[input]="|"`

Provide `'a'`, `'b'`, and `null` as autocompletion entries.

Previously we did not include literal types because we only included
results from the component context (`ctx.`) and the template scope.

PR Close #41456
2021-04-13 13:51:47 -07:00
Alex Rickabaugh
deacc741e0 fix(compiler-cli): ensure the compiler tracks ts.Programs correctly (#41291)
`NgCompiler` previously had a notion of the "next" `ts.Program`, which
served two purposes:

* it allowed a client using the `ts.createProgram` API to query for the
  latest program produced by the previous `NgCompiler`, as a starting
  point for building the _next_ program that incorporated any new user
  changes.

* it allowed the old `NgCompiler` to be queried for the `ts.Program` on
  which all prior state is based, which is needed to compute the delta
  from the new program to ultimately determine how much of the prior
  state can be reused.

This system contained a flaw: it relied on the `NgCompiler` knowing when
the `ts.Program` would be changed. This works fine for changes that
originate in `NgCompiler` APIs, but a client of the `TemplateTypeChecker`
may use that API in ways that create new `ts.Program`s without the
`NgCompiler`'s knowledge. This caused the `NgCompiler`'s concept of the
"next" program to get out of sync, causing incorrectness in future
incremental analysis.

This refactoring cleans up the compiler's `ts.Program` management in
several ways:

* `TypeCheckingProgramStrategy`, the API which controls `ts.Program`
  updating, is renamed to the `ProgramDriver` and extracted to a separate
  ngtsc package.

* It loses its responsibility of determining component shim filenames. That
  functionality now lives exclusively in the template type-checking package.

* The "next" `ts.Program` concept is renamed to the "current" program, as
  the "next" name was misleading in several ways.

* `NgCompiler` now wraps the `ProgramDriver` used in the
  `TemplateTypeChecker` to know when a new `ts.Program` is created,
  regardless of which API drove the creation, which actually fixes the bug.

PR Close #41291
2021-04-08 10:20:38 -07:00
Alex Rickabaugh
1eba57eb00 fix(language-service): show suggestion when type inference is suboptimal (#41072)
The Ivy Language Service uses the compiler's template type-checking engine,
which honors the configuration in the user's tsconfig.json. We recommend
that users upgrade to `strictTemplates` mode in their projects to take
advantage of the best possible type inference, and thus to have the best
experience in Language Service.

If a project is not using `strictTemplates`, then the compiler will not
leverage certain type inference options it has. One case where this is very
noticeable is the inference of let- variables for structural directives that
provide a template context guard (such as NgFor). Without `strictTemplates`,
these guards will not be applied and such variables will be inferred as
'any', degrading the user experience within Language Service.

This is working as designed, since the Language Service _should_ reflect
types exactly as the compiler sees them. However, the View Engine Language
Service used its own type system that _would_ infer these types even when
the compiler did not. As a result, it's confusing to some users why the
Ivy Language Service has "worse" type inference.

To address this confusion, this commit implements a suggestion diagnostic
which is shown in the Language Service for variables which could have been
narrowed via a context guard, but the type checking configuration didn't
allow it. This should make the reason why variables receive the 'any' type
as well as the action needed to improve the typings much more obvious,
improving the Language Service experience.

Fixes angular/vscode-ng-language-service#1155
Closes #41042

PR Close #41072
2021-03-23 09:39:19 -07:00
Zach Arend
09aefd2904 fix(compiler-cli): add useInlining option to type check config (#41043)
This commit fixes the behavior when creating a type constructor for a directive when the following
conditions are met.
1. The directive has bound generic parameters.
2. Inlining is not available. (This happens for language service compiles).

Previously, we would throw an error saying 'Inlining is not supported in this environment.' The
compiler would stop type checking, and the developer could lose out on getting errors after the
compiler gives up.

This commit adds a useInlineTypeConstructors to the type check config. When set to false, we use
`any` type for bound generic parameters to avoid crashing. When set to true, we inline the type
constructor when inlining is required.

Addresses #40963

PR Close #41043
2021-03-18 09:52:47 -07:00
Alex Rickabaugh
a3b0864428 refactor(compiler-cli): remove the overrideComponentTemplate API (#40585)
The `TemplateTypeChecker.overrideComponentTemplate` operation was originally
conceived as a "fast path" for the Language Service to react to a template
change without needing to go through a full incremental compilation step. It
served this purpose until the previous commit, which switches the LS to use
the new resource-only incremental change operation provided by `NgCompiler`.

`overrideComponentTemplate` is now no longer utilized, and is known to have
several hard-to-overcome issues that prevent it from being useful in any
other situations. As such, this commit removes it entirely.

PR Close #40585
2021-02-02 16:24:57 -08:00
Alex Rickabaugh
be979c907b perf(compiler-cli): introduce fast path for resource-only updates (#40561)
This commit adds a new `IncrementalResourceCompilationTicket` which reuses
an existing `NgCompiler` instance and updates it to optimally process
template-only and style-only changes. Performing this update involves both
instructing `DecoratorHandler`s to react to the resource changes, as well as
invalidating `TemplateTypeChecker` state for the component(s) in question.
That way, querying the `TemplateTypeChecker` will trigger new TCB generation
for the changed template(s).

PR Close #40561
2021-01-27 10:45:57 -08:00
Zach Arend
db97453ca0 refactor(compiler-cli): move template parse errors to TemplateData (#40026)
Durring analysis we find template parse errors. This commit changes
where the type checking context stores the parse errors. Previously, we
stored them on the AnalysisOutput this commit changes the errors to be
stored on the TemplateData (which is a property on the shim). That way,
the template parse errors can be grouped by template.

Previously, if a template had a parse error, we poisoned the module and
would not procede to find typecheck errors. This change does not poison
modules whose template have typecheck errors, so that ngtsc can emit
typecheck errors for templates with parse errors.

Additionally, all template diagnostics are produced in the same place.
This allows requesting just the template template diagnostics or just
other types of errors.

PR Close #40026
2020-12-15 13:30:52 -08:00
Alex Rickabaugh
c55bf4a4a3 refactor(compiler-cli): identify structural directives (#40032)
This commit introduces an `isStructural` flag on directive metadata, which
is `true` if the directive injects `TemplateRef` (and thus is at least
theoretically usable as a structural directive). The flag is not used for
anything currently, but will be utilized by the Language Service to offer
better autocompletion results for structural directives.

PR Close #40032
2020-12-14 12:08:41 -08:00
Alex Rickabaugh
c0ab43f3c8 refactor(compiler-cli): introduce APIs to support directive autocompletion (#40032)
This commit adds two new APIs to the `TemplateTypeChecker`:
`getPotentialDomBindings` and `getDirectiveMetadata`. Together, these will
support the Language Service in performing autocompletion of directive
inputs/outputs.

PR Close #40032
2020-12-14 12:08:41 -08:00
Alex Rickabaugh
e42250f139 feat(language-service): autocompletion of element tags (#40032)
This commit expands the autocompletion capabilities of the language service
to include element tag names. It presents both DOM elements from the Angular
DOM schema as well as any components (or directives with element selectors)
that are in scope within the template as options for completion.

PR Close #40032
2020-12-14 12:08:40 -08:00
Andrew Scott
2b74a05a65 refactor(compiler-cli): Enable pipe information when checkTypeOfPipes=false (#39555)
When `checkTypeOfPipes` is set to `false`, the configuration is meant to
ignore the signature of the pipe's `transform` method for diagnostics.
However, we still should produce some information about the pipe for the
`TemplateTypeChecker`. This change refactors the returned symbol for
pipes so that it also includes information about the pipe's class
instance as it appears in the TCB.

PR Close #39555
2020-12-11 16:19:15 -08:00
Alex Rickabaugh
93a83266f9 feat(language-service): autocompletion within expression contexts (#39727)
This commit adds support to the Language Service for autocompletion within
expression contexts. Specifically, this is auto completion of property reads
and method calls, both in normal and safe-navigational forms.

PR Close #39727
2020-12-10 11:09:53 -08:00
Alex Rickabaugh
28a0bcb424 feat(language-service): implement autocompletion for global properties (Ivy) (#39250)
This commit adds support in the Ivy Language Service for autocompletion in a
global context - e.g. a {{foo|}} completion.

Support is added both for the primary function `getCompletionsAtPosition` as
well as the detail functions `getCompletionEntryDetails` and
`getCompletionEntrySymbol`. These latter operations are not used yet as an
upstream change to the extension is required to advertise and support this
capability.

PR Close #39250
2020-12-04 10:19:45 -08:00
Andrew Scott
75fc89384d refactor(compiler-cli): expose TTC method to determine if file is tracked shim (#39768)
The Language Service "find references" currently uses the
`ngtypecheck.ts` suffix to determine if a file is a shim file. Instead,
a better API would be to expose a method in the template type checker
that does this verification so that the LS does not have to "know" about
the typecheck suffix. This also fixes an issue (albeit unlikely) whereby a file
in the user's program that _actually_ is named with the `ngtypecheck.ts`
suffix would have been interpreted as a shim file.

PR Close #39768
2020-12-02 12:54:22 -08:00
Andrew Scott
06a782a2e3 feat(language-service): Add "find references" capability to Ivy integrated LS (#39768)
This commit adds "find references" functionality to the Ivy integrated
language service. The basic approach is as follows:

1. Generate shims for all files to ensure we find references in shims
throughout the entire program
2. Determine if the position for the reference request is within a
template.
  * Yes, it is in a template: Find which node in the template AST the
  position refers to. Then find the position in the shim file for that
  template node. Pass the shim file and position in the shim file along
  to step 3.
  * No, the request for references was made outside a template: Forward
  the file and position to step 3.
3. (`getReferencesAtTypescriptPosition`): Call the native TypeScript LS
`getReferencesAtPosition`. For each reference that is in a shim file, map those
back to a template location, otherwise return it as-is.

PR Close #39768
2020-12-02 12:54:21 -08:00
Andrew Scott
1eb4066c2e refactor(compiler-cli): Expose API for mappping from TCB to template location (#39715)
Consumers of the `TemplateTypeChecker` API could be interested in
mapping from a shim location back to the original source location in the
template. One concrete example of this use-case is for the "find
references" action in the Language Service. This will return locations
in the TypeScript shim file, and we will then need to be able to map the
result back to the template.

PR Close #39715
2020-11-19 12:15:22 -08:00
Andrew Scott
fae2769f44 refactor(compiler-cli): Add additional shim locations to reference and variable symbols (#39715)
Both `ReferenceSymbol` and `VariableSymbol` have two locations of
interest to an external consumer.
1. The location for the initializers of the local TCB variables allow consumers
to query the TypeScript Language Service for information about the initialized type of the variable.
2. The location of the local variable itself (i.e. `_t1`) allows
consumers to query the TypeScript LS for references to that variable
from within the template.

PR Close #39715
2020-11-19 12:15:21 -08:00
Alex Rickabaugh
0ecdef9cfa refactor(compiler-cli): API to get directives/pipes in scope (#39278)
This commit introduces two new methods to the TemplateTypeChecker, which
retrieve the directives and pipes that are "in scope" for a given component
template. The metadata returned by this API is minimal, but enough to power
autocompletion of selectors and attributes in templates.

PR Close #39278
2020-10-27 13:17:14 -07:00
Alex Rickabaugh
c4f99b6e52 refactor(compiler-cli): move global completion into new CompletionEngine (#39278)
This commit refactors the previously introduced `getGlobalCompletions()` API
for the template type-checker in a couple ways:

 * The return type is adjusted to use a `Map` instead of an array, and
   separate out the component context completion position. This allows for a
   cleaner integration in the language service.
 * A new `CompletionEngine` class is introduced which powers autocompletion
   for a single component, and can cache completion results.
 * The `CompletionEngine` for each component is itself cached on the
   `TemplateTypeCheckerImpl` and is invalidated when the component template
   is overridden or reset.

This refactoring simplifies the `TemplateTypeCheckerImpl` class by
extracting the autocompletion logic, enables caching for better performance,
and prepares for the introduction of other autocompletion APIs.

PR Close #39278
2020-10-27 13:17:14 -07:00
Alex Rickabaugh
f2fca6d58e refactor(compiler-cli): add a global autocompletion API (#39048)
This commit introduces a new API for the `TemplateTypeChecker` which allows
for autocompletion in a global expression context (for example, in a new
interpolation expression such as `{{|}}`). This API returns instances of the
type `GlobalCompletion`, which can represent either a completion result from
the template's component context or a declaration such as a local reference
or template variable. The Language Service will use this API to implement
autocompletion within templates.

PR Close #39048
2020-10-06 13:55:00 -07:00
Andrew Scott
e10b3e22ac refactor(compiler): Add ngModule to directive symbol (#39099)
This is needed so that the Language Service can provide the module name
in the quick info for a directive/component.
To accomplish this, the compiler's `LocalModuleScope` is provided to the
`TemplateTypeCheckerImpl`.  This will also allow the `TemplateTypeChecker` to
provide more completions in the future, giving it a way to determine all the
directives/pipes/etc. available to a template.

PR Close #39099
2020-10-05 14:48:58 -07:00
Andrew Scott
ddc9e8e47a refactor(compiler): refactor template symbol builder (#39047)
* Add `templateNode` to `ElementSymbol` and `TemplateSymbol` so callers
can use the information about the attributes on the
`TmplAstElement`/`TmplAstTemplate` for directive matching
* Remove helper function `getSymbolOfVariableDeclaration` and favor
more specific handling for scenarios. The generic function did not
easily handle different scenarios for all types of variable declarations
in the TCB

PR Close #39047
2020-09-30 09:34:24 -04:00
Andrew Scott
c74917a7d5 refactor(compiler-cli): update type checker symbols to include more information (#38844)
This commit updates the symbols in the TemplateTypeCheck API and methods
for retrieving them:

* Include `isComponent` and `selector` for directives so callers can determine which
attributes on an element map to the matched directives.
* Add a new `TextAttributeSymbol` and return this when requesting a symbol for a `TextAttribute`.
* When requesting a symbol for `PropertyWrite` and `MethodCall`, use the
`nameSpan` to retrieve symbols.
* Add fix to retrieve generic directives attached to elements/templates.

PR Close #38844
2020-09-28 16:19:44 -04:00
Alex Rickabaugh
40975e06c6 fix(compiler-cli): perform DOM schema checks even in basic mode in g3 (#38943)
In Ivy, template type-checking has 3 modes: basic, full, and strict. The
primary difference between basic and full modes is that basic mode only
checks the top-level template, whereas full mode descends into nested
templates (embedded views like ngIfs and ngFors). Ivy applies this approach
to all of its template type-checking, including the DOM schema checks which
validate whether an element is a valid component/directive or not.

View Engine has both the basic and the full mode, with the same distinction.
However in View Engine, DOM schema checks happen for the full template even
in the basic mode.

Ivy's behavior here is technically a "fix" as it does not make sense for
some checks to apply to the full template and others only to the top-level
view. However, since g3 relies exclusively on the basic mode of checking and
developers there are used to DOM checks applying throughout their template,
this commit re-enables the nested schema checks even in basic mode only in
g3. This is done by enabling the checks only when Closure Compiler
annotations are requested.

Outside of g3, it's recommended that applications use at least the full mode
of checking (controlled by the `fullTemplateTypeCheck` flag), and ideally
the strict mode (`strictTemplates`).

PR Close #38943
2020-09-23 15:46:32 -04:00
Andrew Scott
c4556db9f5 feat(compiler-cli): TemplateTypeChecker operation to get Symbol from a template node (#38618)
Specifically, this commit adds support for retrieving a `Symbol` from a
`TmplAstBoundEvent` or `TmplAstBoundAttribute`. Other template nodes
will be supported in following commits.

PR Close #38618
2020-09-10 12:40:41 -07:00
Andrew Scott
a46e0e48a3 refactor(compiler-cli): Adjust output of TCB to support TemplateTypeChecker Symbol retrieval (#38618)
The statements generated in the TCB are optimized for performance and producing diagnostics.
These optimizations can result in generating a TCB that does not have all the information
needed by the `TemplateTypeChecker` for retrieving `Symbol`s. For example, as an optimization,
the TCB will not generate variable declaration statements for directives that have no
references, inputs, or outputs. However, the `TemplateTypeChecker` always needs these
statements to be present in order to provide `ts.Symbol`s and `ts.Type`s for the directives.

This commit adds logic to the TCB generation to ensure the required
information is available in a form that the `TemplateTypeChecker` can
consume. It also adds an option to the `NgCompiler` that makes this
generation configurable.

PR Close #38618
2020-09-10 12:40:38 -07:00
Andrew Scott
9e77bd3087 feat(compiler-cli): define interfaces to be used for TemplateTypeChecker (#38618)
This commit defines the interfaces which outline the information the
`TemplateTypeChecker` can return when requesting a Symbol for an item in the
`TemplateAst`.
Rather than providing the `ts.Symbol`, `ts.Type`, etc.
information in several separate functions, the `TemplateTypeChecker` can
instead provide all the useful information it knows about a particular
node in the `TemplateAst` and allow the callers to determine what to do
with it.

PR Close #38618
2020-09-10 12:40:35 -07:00
Alex Rickabaugh
4007422cc6 fix(compiler): correct confusion between field and property names (#38685)
The `R3TargetBinder` accepts an interface for directive metadata which
declares types for `input` and `output` objects. These types convey the
mapping between the property names for an input or output and the
corresponding property name on the component class. Due to
`R3TargetBinder`'s requirements, this mapping was specified with property
names as keys and field names as values.

However, because of duck typing, this interface was accidentally satisifed
by the opposite mapping, of field names to property names, that was produced
in other parts of the compiler. This form more naturally represents the data
model for inputs.

Rather than accept the field -> property mapping and invert it, this commit
introduces a new abstraction for such mappings which is bidirectional,
eliminating the ambiguous plain object type. This mapping uses new,
unambiguous terminology ("class property name" and "binding property name")
and can be used to satisfy both the needs of the binder as well as those of
the template type-checker (field -> property).

A new test ensures that the input/output metadata produced by the compiler
during analysis is directly compatible with the binder via this unambiguous
new interface.

PR Close #38685
2020-09-08 11:43:02 -07:00
Alex Rickabaugh
0b54c0c6b4 refactor(compiler-cli): add getTemplateOfComponent to TemplateTypeChecker (#38355)
This commit adds a `getTemplateOfComponent` method to the
`TemplateTypeChecker` API, which retrieves the actual nodes parsed and used
by the compiler for template type-checking. This is advantageous for the
language service, which may need to query other APIs in
`TemplateTypeChecker` that require the same nodes used to bind the template
while generating the TCB.

Fixes #38352

PR Close #38355
2020-08-19 14:07:03 -07:00
Andrew Scott
71138f6004 feat(compiler-cli): Add compiler option to report errors when assigning to restricted input fields (#38249)
The compiler does not currently report errors when there's an `@Input()`
for a `private`, `protected`, or `readonly` directive/component class member.
This change adds an option to enable reporting errors when a template
attempts to bind to one of these restricted input fields.

PR Close #38249
2020-08-11 09:55:48 -07:00
JoostK
fa0104017a refactor(compiler-cli): only use type constructors for directives with generic types (#38249)
Prior to this change, the template type checker would always use a
type-constructor to instantiate a directive. This type-constructor call
serves two purposes:

1. Infer any generic types for the directive instance from the inputs
   that are passed in.
2. Type check the inputs that are passed into the directive's inputs.

The first purpose is only relevant when the directive actually has any
generic types and using a type-constructor for these cases inhibits
a type-check performance penalty, as a type-constructor's signature is
quite complex and needs to be generated for each directive.

This commit refactors the generated type-check blocks to only generate
a type-constructor call for directives that have generic types. Type
checking of inputs is achieved by generating individual statements for
all inputs, using assignments into the directive's fields.

Even if a type-constructor is used for type-inference of generic types
will the input checking also be achieved using the individual assignment
statements. This is done to support the rework of the language service,
which will start to extract symbol information from the type-check
blocks.

As a future optimization, it may be possible to reduce the number of
inputs passed into a type-constructor to only those inputs that
contribute the the type-inference of the generics. As this is not a
necessity at the moment this is left as follow-up work.

Closes #38185

PR Close #38249
2020-08-11 09:55:48 -07:00
Alex Rickabaugh
d8c07b83c3 refactor(compiler-cli): support type-checking a single component (#38105)
This commit adds a method `getDiagnosticsForComponent` to the
`TemplateTypeChecker`, which does the minimum amount of work to retrieve
diagnostics for a single component.

With the normal `ReusedProgramStrategy` this offers virtually no improvement
over the standard `getDiagnosticsForFile` operation, but if the
`TypeCheckingProgramStrategy` supports separate shims for each component,
this operation can yield a faster turnaround for components that are
declared in files with many other components.

PR Close #38105
2020-07-29 10:31:21 -07:00
Alex Rickabaugh
3c0424e7e0 refactor(compiler-cli): allow overriding templates in the type checker (#38105)
This commit adds an `overrideComponentTemplate` operation to the template
type-checker. This operation changes the template used during template
type-checking operations.

Overriding a template causes any previous work for it to be discarded, and
the template type-checking engine will regenerate the TCB for that template
on the next request.

This operation can be used by a consumer such as the language service to
get rapid feedback or diagnostics as the user is editing a template file,
without the need for a full incremental build iteration.

Closes #38058

PR Close #38105
2020-07-29 10:31:20 -07:00
Alex Rickabaugh
de14b2c670 refactor(compiler-cli): efficient single-file type checking diagnostics (#38105)
Previously, the `TemplateTypeChecker` abstraction allowed fetching
diagnostics for a single file, but under the hood would generate type
checking code for the entire program to satisfy the request.

With this commit, an `OptimizeFor` hint is passed to `getDiagnosticsForFile`
which indicates whether the user intends to request diagnostics for the
whole program or is truly interested in just the single file. If the latter,
the `TemplateTypeChecker` can perform only the work needed to produce
diagnostics for just that file, thus returning answers more efficiently.

PR Close #38105
2020-07-29 10:31:20 -07:00
Alex Rickabaugh
c573d91285 refactor(compiler-cli): allow program strategies to opt out of inlining (#38105)
The template type-checking engine relies on the abstraction interface
`TypeCheckingProgramStrategy` to create updated `ts.Program`s for
template type-checking. The basic API is that the type-checking engine
requests changes to certain files in the program, and the strategy provides
an updated `ts.Program`.

Typically, such changes are made to 'ngtypecheck' shim files, but certain
conditions can cause template type-checking to require "inline" operations,
which change user .ts files instead. The strategy used by 'ngc' (the
`ReusedProgramStrategy`) supports these kinds of updates, but other clients
such as the language service might not always support modifying user files.

To accommodate this, the `TypeCheckingProgramStrategy` interface was
modified to include a `supportsInlineOperations` flag. If an implementation
specifies `false` for inline support, the template type-checking system will
return diagnostics on components which would otherwise require inline
operations.

Closes #38059

PR Close #38105
2020-07-29 10:31:20 -07:00
Alex Rickabaugh
16c7441c2f refactor(compiler-cli): introduce the TemplateTypeChecker abstraction (#38105)
This commit significantly refactors the 'typecheck' package to introduce a
new abstraction, the `TemplateTypeChecker`. To achieve this:

* a 'typecheck:api' package is introduced, containing common interfaces that
  consumers of the template type-checking infrastructure can depend on
  without incurring a dependency on the template type-checking machinery as
  a whole.
* interfaces for `TemplateTypeChecker` and `TypeCheckContext` are introduced
  which contain the abstract operations supported by the implementation
  classes `TemplateTypeCheckerImpl` and `TypeCheckContextImpl` respectively.
* the `TemplateTypeChecker` interface supports diagnostics on a whole
  program basis to start with, but the implementation is purposefully
  designed to support incremental diagnostics at a per-file or per-component
  level.
* `TemplateTypeChecker` supports direct access to the type check block of a
  component.
* the testing utility is refactored to be a lot more useful, and new tests
  are added for the new abstraction.

PR Close #38105
2020-07-29 10:31:20 -07:00