Skip to content

Commit

Permalink
Support Angular inline styles as single template literal (prettier#15968
Browse files Browse the repository at this point in the history
)
  • Loading branch information
sosukesuzuki authored and medikoo committed Feb 18, 2024
1 parent d5f1b0e commit 1a3a44d
Show file tree
Hide file tree
Showing 5 changed files with 231 additions and 9 deletions.
32 changes: 32 additions & 0 deletions changelog_unreleased/angular/15968.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
#### Support Angular inline styles as single template literal (#15968 by @sosukesuzuki)

[Angular v17](https://blog.angular.io/introducing-angular-v17-4d7033312e4b) supports single string inline styles.

<!-- prettier-ignore -->
```ts
// Input
@Component({
template: `<div>...</div>`,
styles: `h1 { color: blue; }`,
})
export class AppComponent {}

// Prettier stable
@Component({
template: `<div>...</div>`,
styles: `h1 { color: blue; }`,
})
export class AppComponent {}

// Prettier main
@Component({
template: `<div>...</div>`,
styles: `
h1 {
color: blue;
}
`,
})
export class AppComponent {}

```
28 changes: 19 additions & 9 deletions src/language-js/embed/utils.js
Original file line number Diff line number Diff line change
Expand Up @@ -30,15 +30,25 @@ const angularComponentObjectExpressionPredicates = [
* })
*/
function isAngularComponentStyles(path) {
return path.match(
(node) => node.type === "TemplateLiteral",
(node, name) => isArrayOrTupleExpression(node) && name === "elements",
(node, name) =>
isObjectProperty(node) &&
node.key.type === "Identifier" &&
node.key.name === "styles" &&
name === "value",
...angularComponentObjectExpressionPredicates,
const isTemplateLiteral = (node) => node.type === "TemplateLiteral";
const isObjectPropertyNamedStyles = (node, key) =>
isObjectProperty(node) &&
!node.computed &&
node.key.type === "Identifier" &&
node.key.name === "styles" &&
key === "value";
return (
path.match(
isTemplateLiteral,
(node, name) => isArrayOrTupleExpression(node) && name === "elements",
isObjectPropertyNamedStyles,
...angularComponentObjectExpressionPredicates,
) ||
path.match(
isTemplateLiteral,
isObjectPropertyNamedStyles,
...angularComponentObjectExpressionPredicates,
)
);
}
function isAngularComponentTemplate(path) {
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
import { Component } from '@angular/core';

const styles = "foobar";

@Component({
selector: 'app-root',
template: `
<h1>My App</h1>
<app-todo-list></app-todo-list>
`,
[styles]: `h1 { color: blue }`
})
export class AppComponent {}
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
import { Component } from '@angular/core';

@Component({
selector: 'app-root',
template: `
<h1>My App</h1>
<app-todo-list></app-todo-list>
`,
styles: `h1 { color: blue }`
})
export class AppComponent {}
Original file line number Diff line number Diff line change
@@ -1,5 +1,161 @@
// Jest Snapshot v1, https://goo.gl/fbAQLP

exports[`15934.component.ts - {"trailingComma":"es5"} format 1`] = `
====================================options=====================================
parsers: ["typescript"]
printWidth: 80
trailingComma: "es5"
| printWidth
=====================================input======================================
import { Component } from '@angular/core';
@Component({
selector: 'app-root',
template: \`
<h1>My App</h1>
<app-todo-list></app-todo-list>
\`,
styles: \`h1 { color: blue }\`
})
export class AppComponent {}
=====================================output=====================================
import { Component } from "@angular/core";
@Component({
selector: "app-root",
template: \`
<h1>My App</h1>
<app-todo-list></app-todo-list>
\`,
styles: \`
h1 {
color: blue;
}
\`,
})
export class AppComponent {}
================================================================================
`;
exports[`15934.component.ts - {"trailingComma":"none"} format 1`] = `
====================================options=====================================
parsers: ["typescript"]
printWidth: 80
trailingComma: "none"
| printWidth
=====================================input======================================
import { Component } from '@angular/core';
@Component({
selector: 'app-root',
template: \`
<h1>My App</h1>
<app-todo-list></app-todo-list>
\`,
styles: \`h1 { color: blue }\`
})
export class AppComponent {}
=====================================output=====================================
import { Component } from "@angular/core";
@Component({
selector: "app-root",
template: \`
<h1>My App</h1>
<app-todo-list></app-todo-list>
\`,
styles: \`
h1 {
color: blue;
}
\`
})
export class AppComponent {}
================================================================================
`;
exports[`15934-computed.component.ts - {"trailingComma":"es5"} format 1`] = `
====================================options=====================================
parsers: ["typescript"]
printWidth: 80
trailingComma: "es5"
| printWidth
=====================================input======================================
import { Component } from '@angular/core';
const styles = "foobar";
@Component({
selector: 'app-root',
template: \`
<h1>My App</h1>
<app-todo-list></app-todo-list>
\`,
[styles]: \`h1 { color: blue }\`
})
export class AppComponent {}
=====================================output=====================================
import { Component } from "@angular/core";
const styles = "foobar";
@Component({
selector: "app-root",
template: \`
<h1>My App</h1>
<app-todo-list></app-todo-list>
\`,
[styles]: \`h1 { color: blue }\`,
})
export class AppComponent {}
================================================================================
`;
exports[`15934-computed.component.ts - {"trailingComma":"none"} format 1`] = `
====================================options=====================================
parsers: ["typescript"]
printWidth: 80
trailingComma: "none"
| printWidth
=====================================input======================================
import { Component } from '@angular/core';
const styles = "foobar";
@Component({
selector: 'app-root',
template: \`
<h1>My App</h1>
<app-todo-list></app-todo-list>
\`,
[styles]: \`h1 { color: blue }\`
})
export class AppComponent {}
=====================================output=====================================
import { Component } from "@angular/core";
const styles = "foobar";
@Component({
selector: "app-root",
template: \`
<h1>My App</h1>
<app-todo-list></app-todo-list>
\`,
[styles]: \`h1 { color: blue }\`
})
export class AppComponent {}
================================================================================
`;
exports[`test.component.ts - {"trailingComma":"es5"} format 1`] = `
====================================options=====================================
parsers: ["typescript"]
Expand Down

0 comments on commit 1a3a44d

Please sign in to comment.