fix(@ngtools/webpack): emit diagnostic for unsupported conditional templateUrl expressions#32888
fix(@ngtools/webpack): emit diagnostic for unsupported conditional templateUrl expressions#32888maruthang wants to merge 1 commit intoangular:mainfrom
Conversation
…mplateUrl expressions Fixes angular#27611
There was a problem hiding this comment.
Code Review
This pull request updates the resource replacement transformer to pass the component class name through the transformation process and adds build-time validation to ensure 'templateUrl' properties are string literals, preventing unsupported dynamic expressions. It also includes unit tests for these changes. Feedback suggests extending this validation to 'styleUrl' and 'styleUrls' for consistency and refactoring the error message to use a single template literal for better readability.
| if (!url) { | ||
| return node; | ||
| const sourceFile = node.getSourceFile(); | ||
| const { line } = sourceFile.getLineAndCharacterOfPosition(node.initializer.getStart()); | ||
|
|
||
| throw new Error( | ||
| `Component '${className}' in '${sourceFile.fileName}' contains a non-string literal ` + | ||
| `'templateUrl' value at line ${line + 1}. The 'templateUrl' property must be a ` + | ||
| `string literal. Expressions, variables, or other dynamic values are not supported.`, | ||
| ); | ||
| } |
There was a problem hiding this comment.
This change correctly adds a build-time error for dynamic templateUrl values. However, the PR description states that this should also apply to styleUrls, but that case is not handled. Non-string literal values in styleUrls are still silently ignored, which can lead to confusing runtime issues.
To ensure consistency and prevent these issues, a similar error should be thrown for non-string literal expressions in styleUrl and styleUrls.
This would likely involve:
- In
visitComponentMetadata, for thestyleUrl/styleUrlscase, check ifnode.initializeris not a string or array literal and throw an error if so. - Passing the
classNametotransformInlineStyleLiteral. - In
transformInlineStyleLiteral, when!ts.isStringLiteralLike(node)and!isInlineStyle, throw an error similar to the one fortemplateUrl.
Additionally, please add tests for these styleUrls cases to replace_resources_spec.ts to cover these scenarios.
| throw new Error( | ||
| `Component '${className}' in '${sourceFile.fileName}' contains a non-string literal ` + | ||
| `'templateUrl' value at line ${line + 1}. The 'templateUrl' property must be a ` + | ||
| `string literal. Expressions, variables, or other dynamic values are not supported.`, | ||
| ); |
There was a problem hiding this comment.
For improved readability and maintainability, consider using a template literal for this error message instead of string concatenation.
throw new Error(`Component '${className}' in '${sourceFile.fileName}' contains a non-string literal 'templateUrl' value at line ${line + 1}. The 'templateUrl' property must be a string literal. Expressions, variables, or other dynamic values are not supported.`);
PR Checklist
PR Type
What is the current behavior?
When a component uses a conditional expression (ternary) in
templateUrl, the replace resource transformer silently ignores it. The build succeeds but the template is not processed correctly, leading to confusing runtime errors.Issue Number: #27611
What is the new behavior?
The transformer now emits a TypeScript diagnostic warning when it encounters a non-string-literal expression in
templateUrlorstyleUrls, clearly informing the developer that conditional expressions are not supported in AOT compilation.Does this PR introduce a breaking change?