diff --git a/src/language-js/parentheses/needs-parentheses.js b/src/language-js/parentheses/needs-parentheses.js index 052064cd8..c091aa8ce 100644 --- a/src/language-js/parentheses/needs-parentheses.js +++ b/src/language-js/parentheses/needs-parentheses.js @@ -134,14 +134,13 @@ function needsParentheses(path, options) { break; case "ExportDefaultDeclaration": - return ( - // `export default function` or `export default class` can't be followed by - // anything after. So an expression like `export default (function(){}).toString()` - // needs to be followed by a parentheses - shouldWrapFunctionForExportDefault(path, options) || - // `export default (foo, bar)` also needs parentheses - node.type === "SequenceExpression" - ); + // `export default function` or `export default class` can't be followed by + // anything after. So an expression like `export default (function(){}).toString()` + // needs to be followed by a parentheses + if (shouldWrapFunctionForExportDefault(path, options)) { + return true; + } + break; case "Decorator": if ( @@ -771,6 +770,8 @@ function needsParentheses(path, options) { return key === "callee"; case "TaggedTemplateExpression": return true; // This is basically a kind of IIFE. + case "ExportDefaultDeclaration": + return key === "declaration"; default: return false; } @@ -817,6 +818,8 @@ function needsParentheses(path, options) { switch (parent.type) { case "NewExpression": return key === "callee"; + case "ExportDefaultDeclaration": + return key === "declaration"; default: return false; } diff --git a/tests/format/js/export-default/parentheses/__snapshots__/format.test.js.snap b/tests/format/js/export-default/parentheses/__snapshots__/format.test.js.snap new file mode 100644 index 000000000..df1584c6d --- /dev/null +++ b/tests/format/js/export-default/parentheses/__snapshots__/format.test.js.snap @@ -0,0 +1,586 @@ +// Jest Snapshot v1, https://jestjs.io/docs/snapshot-testing + +exports[`snippet: #0 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (a++); +=====================================output===================================== +export default a++; + +================================================================================ +`; + +exports[`snippet: #0 format 2`] = ` +====================================options===================================== +parsers: ["babel", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (await a); +=====================================output===================================== +export default await a; + +================================================================================ +`; + +exports[`snippet: #1 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (a++).toString(); +=====================================output===================================== +export default (a++).toString(); + +================================================================================ +`; + +exports[`snippet: #1 format 2`] = ` +====================================options===================================== +parsers: ["babel", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (await a).toString(); +=====================================output===================================== +export default (await a).toString(); + +================================================================================ +`; + +exports[`snippet: #2 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (a++)?.toString(); +=====================================output===================================== +export default (a++)?.toString(); + +================================================================================ +`; + +exports[`snippet: #2 format 2`] = ` +====================================options===================================== +parsers: ["babel", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (await a)?.toString(); +=====================================output===================================== +export default (await a)?.toString(); + +================================================================================ +`; + +exports[`snippet: #3 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (++ a); +=====================================output===================================== +export default ++a; + +================================================================================ +`; + +exports[`snippet: #4 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (++ a).toString(); +=====================================output===================================== +export default (++a).toString(); + +================================================================================ +`; + +exports[`snippet: #5 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (++ a)?.toString(); +=====================================output===================================== +export default (++a)?.toString(); + +================================================================================ +`; + +exports[`snippet: #6 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (+a); +=====================================output===================================== +export default +a; + +================================================================================ +`; + +exports[`snippet: #7 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (+a)?.toString(); +=====================================output===================================== +export default (+a)?.toString(); + +================================================================================ +`; + +exports[`snippet: #8 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (function this_is_a_expression_not_a_declaration() {}); +=====================================output===================================== +export default (function this_is_a_expression_not_a_declaration() {}); + +================================================================================ +`; + +exports[`snippet: #9 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (function this_is_a_expression_not_a_declaration() {}).toString(); +=====================================output===================================== +export default (function this_is_a_expression_not_a_declaration() {}.toString()); + +================================================================================ +`; + +exports[`snippet: #10 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (class this_is_a_expression_not_a_declaration {}); +=====================================output===================================== +export default (class this_is_a_expression_not_a_declaration {}); + +================================================================================ +`; + +exports[`snippet: #11 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (class this_is_a_expression_not_a_declaration {}).toString(); +=====================================output===================================== +export default (class this_is_a_expression_not_a_declaration {}.toString()); + +================================================================================ +`; + +exports[`snippet: #12 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (class this_is_a_expression_not_a_declaration {})?.toString(); +=====================================output===================================== +export default (class this_is_a_expression_not_a_declaration {}?.toString()); + +================================================================================ +`; + +exports[`snippet: #13 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (a in b); +=====================================output===================================== +export default a in b; + +================================================================================ +`; + +exports[`snippet: #14 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (a in b).toString(); +=====================================output===================================== +export default (a in b).toString(); + +================================================================================ +`; + +exports[`snippet: #15 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (a in b)?.toString(); +=====================================output===================================== +export default (a in b)?.toString(); + +================================================================================ +`; + +exports[`snippet: #16 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (a || b); +=====================================output===================================== +export default a || b; + +================================================================================ +`; + +exports[`snippet: #17 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (a || b).toString(); +=====================================output===================================== +export default (a || b).toString(); + +================================================================================ +`; + +exports[`snippet: #18 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (a || b)?.toString(); +=====================================output===================================== +export default (a || b)?.toString(); + +================================================================================ +`; + +exports[`snippet: #19 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (a , b); +=====================================output===================================== +export default (a, b); + +================================================================================ +`; + +exports[`snippet: #20 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (a , b)?.toString(); +=====================================output===================================== +export default (a, b)?.toString(); + +================================================================================ +`; + +exports[`snippet: #21 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (1.); +=====================================output===================================== +export default 1; + +================================================================================ +`; + +exports[`snippet: #22 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (1.).toString(); +=====================================output===================================== +export default (1).toString(); + +================================================================================ +`; + +exports[`snippet: #23 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (1.)?.toString(); +=====================================output===================================== +export default (1)?.toString(); + +================================================================================ +`; + +exports[`snippet: #24 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (a = b); +=====================================output===================================== +export default (a = b); + +================================================================================ +`; + +exports[`snippet: #25 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (a = b).toString(); +=====================================output===================================== +export default (a = b).toString(); + +================================================================================ +`; + +exports[`snippet: #26 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (a = b)?.toString(); +=====================================output===================================== +export default (a = b)?.toString(); + +================================================================================ +`; + +exports[`snippet: #27 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (a += b); +=====================================output===================================== +export default (a += b); + +================================================================================ +`; + +exports[`snippet: #28 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (a += b).toString(); +=====================================output===================================== +export default (a += b).toString(); + +================================================================================ +`; + +exports[`snippet: #29 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (a += b)?.toString(); +=====================================output===================================== +export default (a += b)?.toString(); + +================================================================================ +`; + +exports[`snippet: #30 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (a ? b : c); +=====================================output===================================== +export default (a ? b : c); + +================================================================================ +`; + +exports[`snippet: #31 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (a ? b : c).toString(); +=====================================output===================================== +export default (a ? b : c).toString(); + +================================================================================ +`; + +exports[`snippet: #32 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (a ? b : c)?.toString(); +=====================================output===================================== +export default (a ? b : c)?.toString(); + +================================================================================ +`; + +exports[`snippet: #33 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (() =>{}); +=====================================output===================================== +export default () => {}; + +================================================================================ +`; + +exports[`snippet: #34 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (() =>{}).toString(); +=====================================output===================================== +export default (() => {}).toString(); + +================================================================================ +`; + +exports[`snippet: #35 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (() =>{})?.toString(); +=====================================output===================================== +export default (() => {})?.toString(); + +================================================================================ +`; + +exports[`snippet: #36 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (a\`\`); +=====================================output===================================== +export default a\`\`; + +================================================================================ +`; + +exports[`snippet: #37 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (a\`\`).toString(); +=====================================output===================================== +export default a\`\`.toString(); + +================================================================================ +`; + +exports[`snippet: #38 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (a\`\`)?.toString(); +=====================================output===================================== +export default a\`\`?.toString(); + +================================================================================ +`; + +exports[`snippet: #39 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default (); +=====================================output===================================== +export default (); + +================================================================================ +`; + +exports[`snippet: #40 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default ().toString(); +=====================================output===================================== +export default ().toString(); + +================================================================================ +`; + +exports[`snippet: #41 format 1`] = ` +====================================options===================================== +parsers: ["babel", "flow", "typescript"] +printWidth: 80 + | printWidth +=====================================input====================================== +export default ()?.toString(); +=====================================output===================================== +export default ()?.toString(); + +================================================================================ +`; diff --git a/tests/format/js/export-default/parentheses/format.test.js b/tests/format/js/export-default/parentheses/format.test.js new file mode 100644 index 000000000..2e078d5a0 --- /dev/null +++ b/tests/format/js/export-default/parentheses/format.test.js @@ -0,0 +1,85 @@ +const snippets = [ + "export default (a++);", + "export default (a++).toString();", + "export default (a++)?.toString();", + + "export default (++ a);", + "export default (++ a).toString();", + "export default (++ a)?.toString();", + + "export default (+a);", + "export default (+a)?.toString();", + + "export default (function this_is_a_expression_not_a_declaration() {});", + "export default (function this_is_a_expression_not_a_declaration() {}).toString();", + + "export default (class this_is_a_expression_not_a_declaration {});", + "export default (class this_is_a_expression_not_a_declaration {}).toString();", + "export default (class this_is_a_expression_not_a_declaration {})?.toString();", + + "export default (a in b);", + "export default (a in b).toString();", + "export default (a in b)?.toString();", + + "export default (a || b);", + "export default (a || b).toString();", + "export default (a || b)?.toString();", + + "export default (a , b);", + "export default (a , b)?.toString();", + + "export default (1.);", + "export default (1.).toString();", + "export default (1.)?.toString();", + + "export default (a = b);", + "export default (a = b).toString();", + "export default (a = b)?.toString();", + + "export default (a += b);", + "export default (a += b).toString();", + "export default (a += b)?.toString();", + + "export default (a ? b : c);", + "export default (a ? b : c).toString();", + "export default (a ? b : c)?.toString();", + + "export default (() =>{});", + "export default (() =>{}).toString();", + "export default (() =>{})?.toString();", + + "export default (a``);", + "export default (a``).toString();", + "export default (a``)?.toString();", + + "export default ();", + "export default ().toString();", + "export default ()?.toString();", +]; + +runFormatTest( + { + snippets, + importMeta: import.meta, + }, + ["babel", "flow", "typescript"], +); + +const snippetsWithTla = [ + "export default (await a);", + "export default (await a).toString();", + "export default (await a)?.toString();", +]; + +runFormatTest( + { + snippets: snippetsWithTla, + importMeta: import.meta, + }, + [ + "babel", + // TODO: enable when it supports TLA + // "flow", + "typescript", + ], +);