From ff9470b0a0196a3638f19028bba15e002cb0ff27 Mon Sep 17 00:00:00 2001 From: JoostK Date: Sat, 27 Mar 2021 00:45:42 +0100 Subject: [PATCH] fix(compiler): include used components during JIT compilation of partial component declaration (#41353) In #41104 the list of used directives was split into two arrays of used directives and components, but the JIT side was not updated. This commit fixes the JIT integration by including the list of used components. Fixes #41318 PR Close #41353 --- .../compiler/src/compiler_facade_interface.ts | 16 +++++--- packages/compiler/src/jit_compiler_facade.ts | 9 +++-- .../test/compiler_facade_interface_spec.ts | 5 +++ .../src/compiler/compiler_facade_interface.ts | 16 +++++--- .../render3/jit/declare_component_spec.ts | 40 ++++++++++++++++++- 5 files changed, 69 insertions(+), 17 deletions(-) diff --git a/packages/compiler/src/compiler_facade_interface.ts b/packages/compiler/src/compiler_facade_interface.ts index 1f6d803eef..5343e4583c 100644 --- a/packages/compiler/src/compiler_facade_interface.ts +++ b/packages/compiler/src/compiler_facade_interface.ts @@ -200,12 +200,8 @@ export interface R3DeclareComponentFacade extends R3DeclareDirectiveFacade { template: string; isInline?: boolean; styles?: string[]; - directives?: { - selector: string; type: OpaqueValue | (() => OpaqueValue); - inputs?: string[]; - outputs?: string[]; - exportAs?: string[]; - }[]; + components?: R3DeclareUsedDirectiveFacade[]; + directives?: R3DeclareUsedDirectiveFacade[]; pipes?: {[pipeName: string]: OpaqueValue|(() => OpaqueValue)}; viewProviders?: OpaqueValue; animations?: OpaqueValue; @@ -215,6 +211,14 @@ export interface R3DeclareComponentFacade extends R3DeclareDirectiveFacade { preserveWhitespaces?: boolean; } +export interface R3DeclareUsedDirectiveFacade { + selector: string; + type: OpaqueValue|(() => OpaqueValue); + inputs?: string[]; + outputs?: string[]; + exportAs?: string[]; +} + export interface R3UsedDirectiveMetadata { selector: string; inputs: string[]; diff --git a/packages/compiler/src/jit_compiler_facade.ts b/packages/compiler/src/jit_compiler_facade.ts index 8c8b2b9036..32496f8789 100644 --- a/packages/compiler/src/jit_compiler_facade.ts +++ b/packages/compiler/src/jit_compiler_facade.ts @@ -7,7 +7,7 @@ */ -import {CompilerFacade, CoreEnvironment, ExportedCompilerFacade, OpaqueValue, R3ComponentMetadataFacade, R3DeclareComponentFacade, R3DeclareDependencyMetadataFacade, R3DeclareDirectiveFacade, R3DeclareFactoryFacade, R3DeclareInjectorFacade, R3DeclareNgModuleFacade, R3DeclarePipeFacade, R3DeclareQueryMetadataFacade, R3DependencyMetadataFacade, R3DirectiveMetadataFacade, R3FactoryDefMetadataFacade, R3InjectableMetadataFacade, R3InjectorMetadataFacade, R3NgModuleMetadataFacade, R3PipeMetadataFacade, R3QueryMetadataFacade, StringMap, StringMapWithRename} from './compiler_facade_interface'; +import {CompilerFacade, CoreEnvironment, ExportedCompilerFacade, OpaqueValue, R3ComponentMetadataFacade, R3DeclareComponentFacade, R3DeclareDependencyMetadataFacade, R3DeclareDirectiveFacade, R3DeclareFactoryFacade, R3DeclareInjectorFacade, R3DeclareNgModuleFacade, R3DeclarePipeFacade, R3DeclareQueryMetadataFacade, R3DeclareUsedDirectiveFacade, R3DependencyMetadataFacade, R3DirectiveMetadataFacade, R3FactoryDefMetadataFacade, R3InjectableMetadataFacade, R3InjectorMetadataFacade, R3NgModuleMetadataFacade, R3PipeMetadataFacade, R3QueryMetadataFacade, StringMap, StringMapWithRename} from './compiler_facade_interface'; import {ConstantPool} from './constant_pool'; import {ChangeDetectionStrategy, HostBinding, HostListener, Input, Output, Type, ViewEncapsulation} from './core'; import {compileInjectable} from './injectable_compiler_2'; @@ -384,7 +384,9 @@ function convertDeclareComponentFacadeToMetadata( ...convertDeclareDirectiveFacadeToMetadata(declaration, typeSourceSpan), template, styles: declaration.styles ?? [], - directives: (declaration.directives ?? []).map(convertUsedDirectiveDeclarationToMetadata), + directives: (declaration.components ?? []) + .concat(declaration.directives ?? []) + .map(convertUsedDirectiveDeclarationToMetadata), pipes: convertUsedPipesToMetadata(declaration.pipes), viewProviders: declaration.viewProviders !== undefined ? new WrappedNodeExpr(declaration.viewProviders) : @@ -400,8 +402,7 @@ function convertDeclareComponentFacadeToMetadata( }; } -function convertUsedDirectiveDeclarationToMetadata( - declaration: NonNullable[number]): +function convertUsedDirectiveDeclarationToMetadata(declaration: R3DeclareUsedDirectiveFacade): R3UsedDirectiveMetadata { return { selector: declaration.selector, diff --git a/packages/compiler/test/compiler_facade_interface_spec.ts b/packages/compiler/test/compiler_facade_interface_spec.ts index 7f2f56faa2..e0481e504a 100644 --- a/packages/compiler/test/compiler_facade_interface_spec.ts +++ b/packages/compiler/test/compiler_facade_interface_spec.ts @@ -116,6 +116,11 @@ const coreR3DeclareComponentFacade: core.R3DeclareComponentFacade = const compilerR3DeclareComponentFacade: compiler.R3DeclareComponentFacade = null! as core.R3DeclareComponentFacade; +const coreR3DeclareUsedDirectiveFacade: core.R3DeclareUsedDirectiveFacade = + null! as compiler.R3DeclareUsedDirectiveFacade; +const compilerR3DeclareUsedDirectiveFacade: compiler.R3DeclareUsedDirectiveFacade = + null! as core.R3DeclareUsedDirectiveFacade; + const coreR3UsedDirectiveMetadata: core.R3UsedDirectiveMetadata = null! as compiler.R3UsedDirectiveMetadata; const compilerR3UsedDirectiveMetadata: compiler.R3UsedDirectiveMetadata = diff --git a/packages/core/src/compiler/compiler_facade_interface.ts b/packages/core/src/compiler/compiler_facade_interface.ts index 1f6d803eef..5343e4583c 100644 --- a/packages/core/src/compiler/compiler_facade_interface.ts +++ b/packages/core/src/compiler/compiler_facade_interface.ts @@ -200,12 +200,8 @@ export interface R3DeclareComponentFacade extends R3DeclareDirectiveFacade { template: string; isInline?: boolean; styles?: string[]; - directives?: { - selector: string; type: OpaqueValue | (() => OpaqueValue); - inputs?: string[]; - outputs?: string[]; - exportAs?: string[]; - }[]; + components?: R3DeclareUsedDirectiveFacade[]; + directives?: R3DeclareUsedDirectiveFacade[]; pipes?: {[pipeName: string]: OpaqueValue|(() => OpaqueValue)}; viewProviders?: OpaqueValue; animations?: OpaqueValue; @@ -215,6 +211,14 @@ export interface R3DeclareComponentFacade extends R3DeclareDirectiveFacade { preserveWhitespaces?: boolean; } +export interface R3DeclareUsedDirectiveFacade { + selector: string; + type: OpaqueValue|(() => OpaqueValue); + inputs?: string[]; + outputs?: string[]; + exportAs?: string[]; +} + export interface R3UsedDirectiveMetadata { selector: string; inputs: string[]; diff --git a/packages/core/test/render3/jit/declare_component_spec.ts b/packages/core/test/render3/jit/declare_component_spec.ts index 85cc90b219..28dd53ef44 100644 --- a/packages/core/test/render3/jit/declare_component_spec.ts +++ b/packages/core/test/render3/jit/declare_component_spec.ts @@ -6,7 +6,7 @@ * found in the LICENSE file at https://angular.io/license */ -import {ChangeDetectionStrategy, Directive, ElementRef, forwardRef, Pipe, Type, ViewEncapsulation, ɵɵngDeclareComponent} from '@angular/core'; +import {ChangeDetectionStrategy, Component, Directive, ElementRef, forwardRef, Pipe, Type, ViewEncapsulation, ɵɵngDeclareComponent} from '@angular/core'; import {AttributeMarker, ComponentDef} from '../../../src/render3'; import {functionContaining} from './matcher'; @@ -338,6 +338,21 @@ describe('component declaration jit compilation', () => { }); }); + it('should compile used components', () => { + const def = ɵɵngDeclareComponent({ + type: TestClass, + template: '', + components: [{ + type: TestCmp, + selector: 'cmp', + }], + }) as ComponentDef; + + expectComponentDef(def, { + directives: [TestCmp], + }); + }); + it('should compile used directives', () => { const def = ɵɵngDeclareComponent({ type: TestClass, @@ -353,6 +368,25 @@ describe('component declaration jit compilation', () => { }); }); + it('should compile used directives together with used components', () => { + const def = ɵɵngDeclareComponent({ + type: TestClass, + template: '', + components: [{ + type: TestCmp, + selector: 'cmp', + }], + directives: [{ + type: TestDir, + selector: '[dir]', + }], + }) as ComponentDef; + + expectComponentDef(def, { + directives: [TestCmp, TestDir], + }); + }); + it('should compile forward declared directives', () => { const def = ɵɵngDeclareComponent({ type: TestClass, @@ -534,6 +568,10 @@ class TestClass {} class TestDir { } +@Component({selector: 'cmp', template: ''}) +class TestCmp { +} + @Pipe({name: 'test'}) class TestPipe { }