From 79a7e02c6141adc421cc816f8a014cd71f53abcc Mon Sep 17 00:00:00 2001 From: Dylan Hunn Date: Sun, 10 Dec 2023 01:01:16 -0800 Subject: [PATCH] refactor(compiler): Support `$any` in host bindings (#53478) `$any` should be interpreted as a cast, not as a context read of a variable called `$any`. This already worked in template compilations, but the relevant phase was not enabled for host bindings. PR Close #53478 --- .../host_bindings/GOLDEN_PARTIAL.js | 29 +++++++++++++++++++ .../host_bindings/TEST_CASES.json | 14 +++++++++ .../host_bindings/host_dollar_any.js | 6 ++++ .../host_bindings/host_dollar_any.ts | 11 +++++++ .../src/template/pipeline/src/emit.ts | 2 +- 5 files changed, 61 insertions(+), 1 deletion(-) create mode 100644 packages/compiler-cli/test/compliance/test_cases/r3_view_compiler_bindings/host_bindings/host_dollar_any.js create mode 100644 packages/compiler-cli/test/compliance/test_cases/r3_view_compiler_bindings/host_bindings/host_dollar_any.ts diff --git a/packages/compiler-cli/test/compliance/test_cases/r3_view_compiler_bindings/host_bindings/GOLDEN_PARTIAL.js b/packages/compiler-cli/test/compliance/test_cases/r3_view_compiler_bindings/host_bindings/GOLDEN_PARTIAL.js index 6edee331ed7..85c85d4b470 100644 --- a/packages/compiler-cli/test/compliance/test_cases/r3_view_compiler_bindings/host_bindings/GOLDEN_PARTIAL.js +++ b/packages/compiler-cli/test/compliance/test_cases/r3_view_compiler_bindings/host_bindings/GOLDEN_PARTIAL.js @@ -663,6 +663,35 @@ export declare class MyComponent { static ɵcmp: i0.ɵɵComponentDeclaration; } +/**************************************************************************************************** + * PARTIAL FILE: host_dollar_any.js + ****************************************************************************************************/ +import { Component } from '@angular/core'; +import * as i0 from "@angular/core"; +export class HostBindingDir { +} +HostBindingDir.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "0.0.0-PLACEHOLDER", ngImport: i0, type: HostBindingDir, deps: [], target: i0.ɵɵFactoryTarget.Component }); +HostBindingDir.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "0.0.0-PLACEHOLDER", type: HostBindingDir, selector: "[hostBindingDir]", host: { properties: { "style.color": "$any(\"red\")" } }, ngImport: i0, template: ``, isInline: true }); +i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "0.0.0-PLACEHOLDER", ngImport: i0, type: HostBindingDir, decorators: [{ + type: Component, + args: [{ + selector: '[hostBindingDir]', + host: { + '[style.color]': '$any("red")', + }, + template: `` + }] + }] }); + +/**************************************************************************************************** + * PARTIAL FILE: host_dollar_any.d.ts + ****************************************************************************************************/ +import * as i0 from "@angular/core"; +export declare class HostBindingDir { + static ɵfac: i0.ɵɵFactoryDeclaration; + static ɵcmp: i0.ɵɵComponentDeclaration; +} + /**************************************************************************************************** * PARTIAL FILE: host_bindings_primitive_names.js ****************************************************************************************************/ diff --git a/packages/compiler-cli/test/compliance/test_cases/r3_view_compiler_bindings/host_bindings/TEST_CASES.json b/packages/compiler-cli/test/compliance/test_cases/r3_view_compiler_bindings/host_bindings/TEST_CASES.json index 6a2717a0e40..3c2abce876f 100644 --- a/packages/compiler-cli/test/compliance/test_cases/r3_view_compiler_bindings/host_bindings/TEST_CASES.json +++ b/packages/compiler-cli/test/compliance/test_cases/r3_view_compiler_bindings/host_bindings/TEST_CASES.json @@ -253,6 +253,20 @@ } ] }, + { + "description": "should allow $any in host binding expressions", + "inputFiles": [ + "host_dollar_any.ts" + ], + "expectations": [ + { + "failureMessage": "Invalid host binding code", + "files": [ + "host_dollar_any.js" + ] + } + ] + }, { "description": "should handle host bindings with the same name as a primitive value", "inputFiles": [ diff --git a/packages/compiler-cli/test/compliance/test_cases/r3_view_compiler_bindings/host_bindings/host_dollar_any.js b/packages/compiler-cli/test/compliance/test_cases/r3_view_compiler_bindings/host_bindings/host_dollar_any.js new file mode 100644 index 00000000000..999bdc4a728 --- /dev/null +++ b/packages/compiler-cli/test/compliance/test_cases/r3_view_compiler_bindings/host_bindings/host_dollar_any.js @@ -0,0 +1,6 @@ +function HostBindingDir_HostBindings(rf, ctx) { + if (rf & 2) { + i0.ɵɵstyleProp("color", "red"); + } +} + \ No newline at end of file diff --git a/packages/compiler-cli/test/compliance/test_cases/r3_view_compiler_bindings/host_bindings/host_dollar_any.ts b/packages/compiler-cli/test/compliance/test_cases/r3_view_compiler_bindings/host_bindings/host_dollar_any.ts new file mode 100644 index 00000000000..b3550d58f30 --- /dev/null +++ b/packages/compiler-cli/test/compliance/test_cases/r3_view_compiler_bindings/host_bindings/host_dollar_any.ts @@ -0,0 +1,11 @@ +import {Component} from '@angular/core'; + +@Component({ + selector: '[hostBindingDir]', + host: { + '[style.color]': '$any("red")', + }, + template: `` +}) +export class HostBindingDir { +} diff --git a/packages/compiler/src/template/pipeline/src/emit.ts b/packages/compiler/src/template/pipeline/src/emit.ts index a4a2dfddf63..babf9ccd26c 100644 --- a/packages/compiler/src/template/pipeline/src/emit.ts +++ b/packages/compiler/src/template/pipeline/src/emit.ts @@ -113,7 +113,7 @@ const phases: Phase[] = [ {kind: Kind.Tmpl, fn: generateProjectionDefs}, {kind: Kind.Tmpl, fn: generateVariables}, {kind: Kind.Tmpl, fn: saveAndRestoreView}, - {kind: Kind.Tmpl, fn: deleteAnyCasts}, + {kind: Kind.Both, fn: deleteAnyCasts}, {kind: Kind.Both, fn: resolveDollarEvent}, {kind: Kind.Tmpl, fn: generateRepeaterDerivedVars}, {kind: Kind.Tmpl, fn: generateTrackVariables},