diff --git a/changelog_unreleased/typescript/19897-2.md b/changelog_unreleased/typescript/19897-2.md new file mode 100644 index 000000000..bccbfd07c --- /dev/null +++ b/changelog_unreleased/typescript/19897-2.md @@ -0,0 +1,32 @@ +#### Fix comment before the first heritage clause (#19897 by @fisker) + + +```tsx +// Input +class Foo + extends Bar + implements + // Comment for Ifoo + IFoo, + IBar { + // ... +} + +// Prettier stable +class Foo + extends Bar + // Comment for Ifoo + implements IFoo, IBar { + // ... +} + +// Prettier main +class Foo + extends Bar + implements + // Comment for Ifoo + IFoo, + IBar { + // ... +} +``` diff --git a/changelog_unreleased/typescript/19897.md b/changelog_unreleased/typescript/19897.md new file mode 100644 index 000000000..6acb9e147 --- /dev/null +++ b/changelog_unreleased/typescript/19897.md @@ -0,0 +1,30 @@ +#### Fix unstable comment before the first heritage clause (#19897 by @fisker) + + +```tsx +// Input +class MyClass extends MySuperClass implements /* foo */ ISomething, /* bar */ IOtherThing, /* baz */ IThirdThing { +} + +// Prettier stable (First format) +class MyClass + extends MySuperClass + implements + /* foo */ ISomething, + /* bar */ IOtherThing, + /* baz */ IThirdThing {} + +// Prettier stable (Second format) +class MyClass + extends MySuperClass + /* foo */ + implements ISomething, /* bar */ IOtherThing, /* baz */ IThirdThing {} + +// Prettier main +class MyClass + extends MySuperClass + implements + /* foo */ ISomething, + /* bar */ IOtherThing, + /* baz */ IThirdThing {} +``` diff --git a/src/language-js/comments/handle-comments.js b/src/language-js/comments/handle-comments.js index 423905194..a98029ac9 100644 --- a/src/language-js/comments/handle-comments.js +++ b/src/language-js/comments/handle-comments.js @@ -316,6 +316,7 @@ function handleClassComments({ precedingNode, enclosingNode, followingNode, + options, }) { if (isClassLikeNode(enclosingNode)) { // @ts-expect-error -- Safe @@ -332,13 +333,12 @@ function handleClassComments({ // Don't add leading comments to `implements`, `extends`, `mixins` to // avoid printing the comment after the keyword. - if (followingNode) { + if (followingNode && precedingNode) { // @ts-expect-error -- Safe const { superClass } = enclosingNode; if ( superClass && followingNode === superClass && - precedingNode && (precedingNode === enclosingNode.id || precedingNode === enclosingNode.typeParameters) ) { @@ -346,19 +346,26 @@ function handleClassComments({ return true; } - for (const prop of ["implements", "extends", "mixins"]) { - if (enclosingNode[prop] && followingNode === enclosingNode[prop][0]) { + for (const property of ["implements", "extends", "mixins"]) { + const firstHeritageClause = enclosingNode[property]?.[0]; + if (followingNode === firstHeritageClause) { if ( - precedingNode && - (precedingNode === enclosingNode.id || - precedingNode === enclosingNode.typeParameters || - precedingNode === superClass) + precedingNode === enclosingNode.id || + precedingNode === enclosingNode.typeParameters || + precedingNode === superClass ) { - addTrailingComment(precedingNode, comment); + if ( + stripComments(options) + .slice(locEnd(comment), locStart(firstHeritageClause)) + .trim() === property + ) { + addTrailingComment(precedingNode, comment); + return true; + } } else { - addDanglingComment(enclosingNode, comment, prop); + addDanglingComment(enclosingNode, comment, property); + return true; } - return true; } } } diff --git a/tests/format/typescript/class-comment/__snapshots__/format.test.js.snap b/tests/format/typescript/class-comment/__snapshots__/format.test.js.snap index 60a0a6aa5..54442b8b7 100644 --- a/tests/format/typescript/class-comment/__snapshots__/format.test.js.snap +++ b/tests/format/typescript/class-comment/__snapshots__/format.test.js.snap @@ -94,8 +94,10 @@ class a2 extends b implements z { class a3 extends b - // comment - implements z, y + implements + // comment + z, + y { constructor() {} } @@ -121,8 +123,8 @@ class a5 class a6 extends b - // comment-z1 implements + // comment-z1 z, // comment-z2 // comment-y1 y @@ -133,8 +135,8 @@ class a6 class a7 extends b - // comment-z1 implements + // comment-z1 z, // comment-z2 // comment-y1 y @@ -147,8 +149,8 @@ class a7 class a8 extends b // comment-b - // comment-z1 implements + // comment-z1 z, // comment-z2 // comment-y1 y @@ -161,8 +163,8 @@ class a9 // comment-b1 extends b // comment-b2 // comment-b3 - // comment-z1 implements + // comment-z1 z, // comment-z2 // comment-y1 y @@ -263,6 +265,40 @@ class G4< ================================================================================ `; +exports[`issue-16228.ts format 1`] = ` +====================================options===================================== +parsers: ["typescript", "flow"] + printWidth: 80 (default) | +=====================================input====================================== +class C11 extends S implements /* foo */ Foo, /* bar */ Bar { +} +class C12 extends S implements /* foo */ Foo, /* bar */ Bar, /* baz */ Baz__________________________________ { +} + +interface I11 extends /* foo */ Foo, /* bar */ Bar { +} +interface I12 extends /* foo */ Foo, /* bar */ Bar, /* baz */ Baz__________________________________ { +} + +=====================================output===================================== +class C11 extends S implements /* foo */ Foo, /* bar */ Bar {} +class C12 + extends S + implements + /* foo */ Foo, + /* bar */ Bar, + /* baz */ Baz__________________________________ {} + +interface I11 extends /* foo */ Foo, /* bar */ Bar {} +interface I12 + extends + /* foo */ Foo, + /* bar */ Bar, + /* baz */ Baz__________________________________ {} + +================================================================================ +`; + exports[`misc.ts format 1`] = ` ====================================options===================================== parsers: ["typescript", "flow"] diff --git a/tests/format/typescript/class-comment/issue-16228.ts b/tests/format/typescript/class-comment/issue-16228.ts new file mode 100644 index 000000000..ec01fe415 --- /dev/null +++ b/tests/format/typescript/class-comment/issue-16228.ts @@ -0,0 +1,9 @@ +class C11 extends S implements /* foo */ Foo, /* bar */ Bar { +} +class C12 extends S implements /* foo */ Foo, /* bar */ Bar, /* baz */ Baz__________________________________ { +} + +interface I11 extends /* foo */ Foo, /* bar */ Bar { +} +interface I12 extends /* foo */ Foo, /* bar */ Bar, /* baz */ Baz__________________________________ { +}