diff --git a/packages/compiler-cli/src/metadata/collector.ts b/packages/compiler-cli/src/metadata/collector.ts index e2748ce9df..77611644f1 100644 --- a/packages/compiler-cli/src/metadata/collector.ts +++ b/packages/compiler-cli/src/metadata/collector.ts @@ -289,7 +289,7 @@ export class MetadataCollector { ts.TypeAliasDeclaration | ts.EnumDeclaration) => exportedIdentifierName(node.name); - // Predeclare classes and functions + // Pre-declare classes and functions ts.forEachChild(sourceFile, node => { switch (node.kind) { case ts.SyntaxKind.ClassDeclaration: @@ -454,7 +454,7 @@ export class MetadataCollector { }; } else { nextDefaultValue = - recordEntry(errorSym('Unsuppported enum member name', member.name), node); + recordEntry(errorSym('Unsupported enum member name', member.name), node); } } if (writtenMembers) { diff --git a/packages/compiler-cli/src/metadata/evaluator.ts b/packages/compiler-cli/src/metadata/evaluator.ts index 273db143c2..cf5c2ea269 100644 --- a/packages/compiler-cli/src/metadata/evaluator.ts +++ b/packages/compiler-cli/src/metadata/evaluator.ts @@ -356,9 +356,6 @@ export class Evaluator { } } const args = arrayOrEmpty(callExpression.arguments).map(arg => this.evaluateNode(arg)); - if (!this.options.verboseInvalidExpression && args.some(isMetadataError)) { - return args.find(isMetadataError); - } if (this.isFoldable(callExpression)) { if (isMethodCallOf(callExpression, 'concat')) { const arrayValue = this.evaluateNode( diff --git a/packages/compiler-cli/test/metadata/collector_spec.ts b/packages/compiler-cli/test/metadata/collector_spec.ts index 34ca4a4979..9d4bbf7e0e 100644 --- a/packages/compiler-cli/test/metadata/collector_spec.ts +++ b/packages/compiler-cli/test/metadata/collector_spec.ts @@ -1054,10 +1054,20 @@ describe('Collector', () => { expect(metadata.metadata.MyComponent).toEqual({ __symbolic: 'class', decorators: [{ - __symbolic: 'error', - message: 'Expression form not supported', - line: 5, - character: 55 + __symbolic: 'call', + expression: { + __symbolic: 'reference', + module: '@angular/core', + name: 'Component', + line: 4, + character: 9 + }, + arguments: [{ + __symbolic: 'error', + message: 'Expression form not supported', + line: 5, + character: 55 + }] }] }); }); diff --git a/packages/compiler-cli/test/ngc_spec.ts b/packages/compiler-cli/test/ngc_spec.ts index 65bc967120..dafa6fe3dd 100644 --- a/packages/compiler-cli/test/ngc_spec.ts +++ b/packages/compiler-cli/test/ngc_spec.ts @@ -1698,6 +1698,40 @@ describe('ngc transformer command-line', () => { expect(messages[0]).toContain(`is imported recursively by the module 'MyFaultyImport`); }); + // Regression test for #21273 + it('should not report errors for unknown property annotations', () => { + write('src/tsconfig.json', `{ + "extends": "../tsconfig-base.json", + "files": ["test-module.ts"] + }`); + + write('src/test-decorator.ts', ` + export function Convert(p: any): any { + // Make sur this doesn't look like a macro function + var r = p; + return r; + } + `); + write('src/test-module.ts', ` + import {Component, Input, NgModule} from '@angular/core'; + import {Convert} from './test-decorator'; + + @Component({template: '{{name}}'}) + export class TestComponent { + @Input() @Convert(convert) name: string; + } + + function convert(n: any) { return n; } + + @NgModule({declarations: [TestComponent]}) + export class TestModule {} + `); + const messages: string[] = []; + expect( + main(['-p', path.join(basePath, 'src/tsconfig.json')], message => messages.push(message))) + .toBe(0, `Compile failed:\n ${messages.join('\n ')}`); + }); + it('should allow using 2 classes with the same name in declarations with noEmitOnError=true', () => { write('src/tsconfig.json', `{ diff --git a/packages/compiler/test/aot/static_reflector_spec.ts b/packages/compiler/test/aot/static_reflector_spec.ts index 0d13a2bd25..eb6f636400 100644 --- a/packages/compiler/test/aot/static_reflector_spec.ts +++ b/packages/compiler/test/aot/static_reflector_spec.ts @@ -364,7 +364,8 @@ describe('StaticReflector', () => { const classData: any = moduleMetadata['InvalidMetadata']; expect(classData).toBeDefined(); simplify( - reflector.getStaticSymbol('/tmp/src/invalid-metadata.ts', ''), classData.decorators[0]); + reflector.getStaticSymbol('/tmp/src/invalid-metadata.ts', ''), + classData.decorators[0].arguments); } catch (e) { expect(e.position).toBeDefined(); threw = true;