惯性聚合 高效追踪和阅读你感兴趣的博客、新闻、科技资讯
阅读原文 在惯性聚合中打开

推荐订阅源

博客园 - Franky
N
Netflix TechBlog - Medium
Google Online Security Blog
Google Online Security Blog
月光博客
月光博客
量子位
酷 壳 – CoolShell
酷 壳 – CoolShell
V
V2EX
腾讯CDC
OSCHINA 社区最新新闻
OSCHINA 社区最新新闻
博客园 - 聂微东
让小产品的独立变现更简单 - ezindie.com
让小产品的独立变现更简单 - ezindie.com
M
MIT News - Artificial intelligence
Vercel News
Vercel News
The GitHub Blog
The GitHub Blog
Hugging Face - Blog
Hugging Face - Blog
博客园 - 【当耐特】
Apple Machine Learning Research
Apple Machine Learning Research
aimingoo的专栏
aimingoo的专栏
博客园 - 三生石上(FineUI控件)
CTFtime.org: upcoming CTF events
CTFtime.org: upcoming CTF events
MongoDB | Blog
MongoDB | Blog
H
Help Net Security
The Cloudflare Blog
Blog — PlanetScale
Blog — PlanetScale
F
Full Disclosure
G
Google Developers Blog
罗磊的独立博客
Jina AI
Jina AI
钛媒体:引领未来商业与生活新知
钛媒体:引领未来商业与生活新知
Y
Y Combinator Blog
H
Hackread – Cybersecurity News, Data Breaches, AI and More
J
Java Code Geeks
A
About on SuperTechFans
IT之家
IT之家
大猫的无限游戏
大猫的无限游戏
S
SegmentFault 最新的问题
有赞技术团队
有赞技术团队
GbyAI
GbyAI
雷峰网
雷峰网
T
The Blog of Author Tim Ferriss
The Register - Security
The Register - Security
U
Unit 42
D
Docker
Martin Fowler
Martin Fowler
L
LINUX DO - 热门话题
NISL@THU
NISL@THU
阮一峰的网络日志
阮一峰的网络日志
C
Cybersecurity and Infrastructure Security Agency CISA
博客园_首页
Google DeepMind News
Google DeepMind News

Prettier Blog

Prettier 3.8: Support for Angular v21.1 Prettier 3.7: Improved formatting consistency and new plugin features! Prettier 3.6: Experimental fast CLI and new OXC and Hermes plugins! Prettier 3.5: New objectWrap option, experimentalOperatorPosition option and TS config file support! Prettier 3.4: A lot of bug fixes Prettier 3.3: New Flow features and a lot of bug fixes Prettier's CLI: A Performance Deep Dive $20k Bounty was Claimed! Prettier 3.1: New experimental ternaries formatting and Angular control flow syntax! A curious case of the ternaries Prettier 3.0: Hello, ECMAScript Modules! Prettier 2.8: improve --cache CLI option and TypeScript 4.9 satisfies operator! Prettier 2.7: new --cache CLI option and TypeScript 4.7 syntax! Prettier 2.6: new singleAttributePerLine option and new JavaScript features! Prettier begins paying maintainers Prettier 2.5: TypeScript 4.5 and MDX v2 comment syntax! Prettier 2.4: new bracketSameLine option and TypeScript 4.4 support! Prettier 2.3. In which assignments are consistent, short keys non-breaking, and Handlebars official Prettier for Ruby goes v1.0 🎉
Prettier 3.2: Support JSONC and Angular’s ICU expression
Sosuke Suzuki · 2024-01-12 · via Prettier Blog

This release includes new features such as adding a JSONC parser, adding Angular’s ICU expressions, and many bug fixes.

We are still seeking feedback for the --experimental-ternaries option released in Prettier 3.1. Please read A curious case of the ternaries and respond via the Google Forms link provided.

Additionally, we recommend reading Prettier's CLI: A Performance Deep Dive by Fabio Spampinato. This faster CLI is slated to be released as version 4.0.

If you appreciate Prettier and would like to support our work, please consider sponsoring us directly via our OpenCollective or by sponsoring the projects we depend on, such as typescript-eslint, remark, and Babel. Thank you for your continued support!

Highlights

JSON

New jsonc parser added (#15831 by @fisker)

Previously, we infer the parser of .jsonc files to be json, but if we want keep the trailing comma, we'll have to use a hacky workaround config {parser: "json5", quoteProps: "preserve", singleQuote: false}.

The new added jsonc parser:

  • Always quote the object keys.
  • Wrap strings with double quotes.
  • Of course, respect the trailingComma option.

Angular

Support formatting for Angular ICU expression (#15777 by @sosukesuzuki)

Support two kinds of Angular ICU expressions: plural and select.

<span i18n>

Updated:

{minutes, plural,

=0 {just now}

=1 {one minute ago}

other {{{minutes}} minutes ago}

}

</span>

<span i18n>

The author is {gender, select, male {male} female {female} other {other}}

</span>

Other Changes

JavaScript

Avoid introducing linebreaks in template interpolations (#15209 by @bakkot)

In a template string like

`this is a long message which contains an interpolation: ${format(data)} <- like this`;

avoid adding a linebreak when formatting the expression unless one is already present or it's unavoidable due to e.g. a nested function. Previously a linebreak could be introduced whenever some interpolation in the template was sufficiently "not simple":

`this is a long message which contains an interpolation: ${format(

data,

)} <- like this`;

Now it will instead be left alone.

If a linebreak is already present within the ${...}, format as normal.

Fix non-idempotent formatting of method chain with empty line (#15522 by @seiyab)

// Input

Foo.a()

.b();

// Prettier 3.1 (first format)

Foo.a()

.b();

// Prettier 3.1 (second format)

Foo.a().b();

// Prettier 3.2

Foo.a()

.b();

Fix formatting of ternary in function call (#15677 by @fisker)

// Input

stopDirectory = await (useCache

? memoizedFindProjectRoot

: findProjectRootWithoutCache)(path.dirname(path.resolve(filePath)));

// Prettier 3.1

stopDirectory = await (useCache

? memoizedFindProjectRoot

: findProjectRootWithoutCache)(path.dirname(path.resolve(filePath)));

// Prettier 3.2

stopDirectory = await (

useCache ? memoizedFindProjectRoot : findProjectRootWithoutCache

)(path.dirname(path.resolve(filePath)));

Fix inconsistencies for optional-chaining (#15806 by @fisker)

Only happens when using typescript, meriyah or other ESTree parsers except babel.

// Input

function someFunctionName() {

return isEqual(a.map(([t, _]) => t?.id), b.map(([t, _]) => t?.id));

return isEqual(a?.map(([t, _]) => t?.id), b?.map(([t, _]) => t?.id));

}

theValue = Object.entries(someLongObjectName).filter(

([listingId]) => someListToCompareToHere.includes(listingId),

);

theValue = Object.entries(someLongObjectName).filter(

([listingId]) => someListToCompareToHere?.includes(listingId),

);

// Prettier 3.1

function someFunctionName() {

return isEqual(

a.map(([t, _]) => t?.id),

b.map(([t, _]) => t?.id),

);

return isEqual(a?.map(([t, _]) => t?.id), b?.map(([t, _]) => t?.id));

}

theValue = Object.entries(someLongObjectName).filter(([listingId]) =>

someListToCompareToHere.includes(listingId),

);

theValue = Object.entries(someLongObjectName).filter(

([listingId]) => someListToCompareToHere?.includes(listingId),

);

// Prettier 3.2

function someFunctionName() {

return isEqual(

a.map(([t, _]) => t?.id),

b.map(([t, _]) => t?.id),

);

return isEqual(

a?.map(([t, _]) => t?.id),

b?.map(([t, _]) => t?.id),

);

}

theValue = Object.entries(someLongObjectName).filter(([listingId]) =>

someListToCompareToHere.includes(listingId),

);

theValue = Object.entries(someLongObjectName).filter(([listingId]) =>

someListToCompareToHere?.includes(listingId),

);

// Input

if (foo) for (i = 2; i > 0; i--) console.log(i); // comment 1

else bar();

for (;;){

if (foo) continue; // comment 2

else bar();

}

// Prettier 3.1

Error: Comment "comment 2" was not printed. Please report this error!

// Prettier 3.2

if (foo)

for (i = 2; i > 0; i--) console.log(i); // comment 1

else bar();

for (;;) {

if (foo)

continue; // comment 2

else bar();

}

TypeScript

Improve conditional type alias layout (#15811 by @seiyab)

// Input

type FallbackFlags<F extends Flags | undefined> =

Equals<NonNullableFlag<F>["flags"], {}> extends true

? Dict<any>

: NonNullableFlag<F>["flags"];

// Prettier 3.1

type FallbackFlags<F extends Flags | undefined> = Equals<

NonNullableFlag<F>["flags"],

{}

> extends true

? Dict<any>

: NonNullableFlag<F>["flags"];

// Prettier 3.2

type FallbackFlags<F extends Flags | undefined> =

Equals<NonNullableFlag<F>["flags"], {}> extends true

? Dict<any>

: NonNullableFlag<F>["flags"];

HTML

Fix formatting of prettier-ignored unclosed elements (#15748 by @fisker)

<!-- Input -->

<!-- prettier-ignore -->

<h1>

Hello <span>world!

<!-- Prettier 3.1 -->

<!-- prettier-ignore -->

<h1>

<!-- Prettier 3.2 -->

<!-- prettier-ignore -->

<h1>

Hello <span>world!

Angular

Fix prettier-ignored angular control flow block (#15827 by @fisker)

<!-- Input -->

<!-- prettier-ignore -->

@if (condition) {

Foo

} @else {

Other

}

<!-- Prettier 3.1 -->

<!-- prettier-ignore -->

@if (condition) {

Foo

}

} @else {

Other

}

<!-- Prettier 3.2 -->

<!-- prettier-ignore -->

@if (condition) {

Foo

}

@else {

Other

}

Avoid adding colon for track in 3rd expression of for blocks (#15887 by @sosukesuzuki)

<!-- Input -->

@for (item of items; let i = $index; track block) {}

<!-- Prettier 3.1 -->

@for (item of items; let i = $index; track: block) {}

<!-- Prettier 3.2 -->

@for (item of items; let i = $index; track block) {}

Ember / Handlebars

Preserve path literal segments (#15605 by @maxpowa)

Fixes scenarios where an input handlebars file containing literal segments would be reformatted to unwrap the literal segments, causing syntax errors in the resulting output.

<!-- Input -->

{{input.[funky<api!response]}}

{{input.[this one has spaces]}}

{{input.[anotherone].[0]}}

<!-- Prettier 3.1 -->

{{input.funky<api!response}}

{{input.this one has spaces}}

{{input.anotherone.0}}

<!-- Prettier 3.2 -->

{{input.[funky<api!response]}}

{{input.[this one has spaces]}}

{{input.anotherone.[0]}}

GraphQL

Improve GraphQL union types formatting (#15870 by @ArchitGajjar)

# Input

union SearchResult = Conference| Festival | Concert | Venue | Conference| Festival | Concert | Venue

# Prettier 3.1

union SearchResult =

Conference

| Festival

| Concert

| Venue

| Conference

| Festival

| Concert

| Venue

# Prettier 3.2

union SearchResult =

| Conference

| Festival

| Concert

| Venue

| Conference

| Festival

| Concert

| Venue

API

Support absolute path as plugin in config file (#15666 by @fisker)

// prettier.config.cjs

module.exports = {

plugins: [

// posix style

"/path/to/plugin.js",

// Windows style

"D:\\\\path\\to\\plugin.js",

// Use `require.resolve`

require.resolve("my-awesome-prettier-plugin"),

],

};

Fix getFileInfo and getSupportInfo type definitions (#15854 by @auvred)

const plugin: Plugin = {};

prettier.getFileInfo("./file.ext", {

plugins: [plugin],

});

prettier.getSupportInfo({ plugins: [plugin], showDeprecated: true });

Miscellaneous

Fix false claim in docs that cursorOffset is incompatible with rangeStart/rangeEnd (#15750 by @ExplodingCabbage)

The cursorOffset option has in fact been compatible with rangeStart/rangeEnd for over 5 years, thanks to work by @ds300. However, Prettier's documentation (including the CLI --help text) continued to claim otherwise, falsely. The documentation is now fixed.