diff --git a/changelog_unreleased/api/12740.md b/changelog_unreleased/api/12740.md index 70067e681..2ddd147e4 100644 --- a/changelog_unreleased/api/12740.md +++ b/changelog_unreleased/api/12740.md @@ -23,8 +23,8 @@ File structures changes: - `esm/parser-babel.mjs` -> `plugins/babel.mjs` - `parser-babel.js` -> `plugins/babel.js` - `esm/parser-espree.mjs` -> `plugins/acorn-and-espree.mjs` -- `parser-espree.js` -> `plugins/acorn-and-espree.js`\ - global object renamed `prettierPlugins.espree` -> `prettierPlugins.acornAndEspree` +- `parser-espree.js` -> `plugins/acorn.js`\ + global object renamed `prettierPlugins.espree` -> `prettierPlugins.acorn` - `esm/parser-flow.mjs` -> `plugins/flow.mjs` - `parser-flow.js` -> `plugins/flow.js` - `esm/parser-glimmer.mjs` -> `plugins/glimmer.mjs` diff --git a/scripts/build/build-javascript-module.js b/scripts/build/build-javascript-module.js index f0abf1f31..a8d24befc 100644 --- a/scripts/build/build-javascript-module.js +++ b/scripts/build/build-javascript-module.js @@ -170,20 +170,13 @@ function getEsbuildOptions({ file, files, shouldCollectLicenses, cliOptions }) { { module: "module", text: "export const createRequire = () => {};", + }, + // This module requires file access, should not include in universal bundle + { + module: path.join(PROJECT_ROOT, "src/utils/get-interpreter.js"), + text: "export default undefined;", } ); - - // Replace parser getters with `undefined` - for (const file of [ - "src/language-js/parse/parsers.js", - // This module requires file access, should not include in universal bundle - "src/utils/get-interpreter.js", - ]) { - replaceModule.push({ - module: path.join(PROJECT_ROOT, file), - text: "export default undefined;", - }); - } } const { buildOptions } = file; diff --git a/scripts/build/build-package-json.js b/scripts/build/build-package-json.js index 98ac188d0..65493072d 100644 --- a/scripts/build/build-package-json.js +++ b/scripts/build/build-package-json.js @@ -52,7 +52,7 @@ async function buildPackageJson({ file, files }) { ) .flatMap((file) => { let basename = path.basename(file.output.file, ".js"); - if (basename === "acorn-and-espree") { + if (basename === "acorn") { basename = "espree"; } return [ diff --git a/scripts/build/config.mjs b/scripts/build/config.mjs index 848e82880..f94390d5c 100644 --- a/scripts/build/config.mjs +++ b/scripts/build/config.mjs @@ -88,7 +88,7 @@ const extensions = { const pluginFiles = [ "src/plugins/estree.js", { - input: "src/language-js/parse/babel.js", + input: "src/plugins/babel.js", replaceModule: [ { // We don't use value of JSXText @@ -102,7 +102,7 @@ const pluginFiles = [ ], }, { - input: "src/language-js/parse/flow.js", + input: "src/plugins/flow.js", replaceModule: [ { module: require.resolve("flow-parser"), @@ -114,7 +114,7 @@ const pluginFiles = [ ], }, { - input: "src/language-js/parse/typescript.js", + input: "src/plugins/typescript.js", replaceModule: [ { module: require.resolve("typescript"), @@ -208,8 +208,7 @@ const pluginFiles = [ ], }, { - input: "src/language-js/parse/acorn-and-espree.js", - umdPropertyName: "acornAndEspree", + input: "src/plugins/acorn.js", replaceModule: [ { module: require.resolve("espree"), @@ -233,7 +232,7 @@ const pluginFiles = [ ], }, { - input: "src/language-js/parse/meriyah.js", + input: "src/plugins/meriyah.js", replaceModule: [ { // We don't use value of JSXText @@ -244,7 +243,7 @@ const pluginFiles = [ ], }, { - input: "src/language-js/parse/angular.js", + input: "src/plugins/angular.js", replaceModule: [ // We only use a small set of `@angular/compiler` from `esm2020/src/expression_parser/` // Those files can't be imported, they also not directly runnable, because `.mjs` extension is missing @@ -268,8 +267,7 @@ const pluginFiles = [ ], }, { - input: "src/language-css/index.js", - outputBaseName: "postcss", + input: "src/plugins/postcss.js", replaceModule: [ // The following two replacements prevent load `source-map` module { @@ -309,9 +307,9 @@ const pluginFiles = [ }, ], }, - "src/language-graphql/index.js", + "src/plugins/graphql.js", { - input: "src/language-markdown/index.js", + input: "src/plugins/markdown.js", replaceModule: [ { module: getPackageFile("parse-entities/decode-entity.browser.js"), @@ -320,8 +318,7 @@ const pluginFiles = [ ], }, { - input: "src/language-handlebars/index.js", - outputBaseName: "glimmer", + input: "src/plugins/glimmer.js", replaceModule: [ // See comment in `src/language-handlebars/parser-glimmer.js` file { @@ -346,8 +343,8 @@ const pluginFiles = [ }, ], }, - "src/language-html/index.js", - "src/language-yaml/index.js", + "src/plugins/html.js", + "src/plugins/yaml.js", ].map((file) => { if (typeof file === "string") { file = { input: file }; @@ -355,10 +352,8 @@ const pluginFiles = [ let { input, umdPropertyName, outputBaseName, ...buildOptions } = file; - outputBaseName ??= ( - input.match(/\/(?:parser-|parse\/|plugins\/)(?.*?)\.js$/) ?? - input.match(/\/language-(?.*?)\/index\.js$/) - ).groups.outputBaseName; + outputBaseName ??= input.match(/\/plugins\/(?.*?)\.js$/) + .groups.outputBaseName; const umdVariableName = `prettierPlugins.${ umdPropertyName ?? outputBaseName diff --git a/src/common/load-builtin-plugins.js b/src/common/load-builtin-plugins.js new file mode 100644 index 000000000..79b48d354 --- /dev/null +++ b/src/common/load-builtin-plugins.js @@ -0,0 +1,23 @@ +let builtinPlugins; + +async function loadBuiltinPlugins() { + builtinPlugins ??= await Promise.all([ + import("../plugins/estree.js"), + import("../plugins/babel.js"), + import("../plugins/flow.js"), + import("../plugins/typescript.js"), + import("../plugins/acorn.js"), + import("../plugins/meriyah.js"), + import("../plugins/angular.js"), + import("../plugins/postcss.js"), + import("../plugins/graphql.js"), + import("../plugins/markdown.js"), + import("../plugins/glimmer.js"), + import("../plugins/html.js"), + import("../plugins/yaml.js"), + ]); + + return builtinPlugins; +} + +export default loadBuiltinPlugins; diff --git a/src/document/public.d.ts b/src/document/public.d.ts index 66084a1e9..84aff5462 100644 --- a/src/document/public.d.ts +++ b/src/document/public.d.ts @@ -207,7 +207,7 @@ export namespace printer { * Indent lines with tabs instead of spaces * @default false */ - useTabs: boolean; + useTabs?: boolean; parentParser?: string | undefined; __embeddedInHtml?: boolean | undefined; } diff --git a/src/index.js b/src/index.js index 8d7b7dced..b5ab88ce1 100644 --- a/src/index.js +++ b/src/index.js @@ -12,7 +12,6 @@ import { resolveConfigFile, clearCache as clearConfigCache, } from "./config/resolve-config.js"; -import * as languages from "./languages.js"; import * as errors from "./common/errors.js"; import * as coreOptions from "./main/core-options.evaluate.js"; import { createIsIgnoredFunction } from "./utils/ignore.js"; @@ -21,8 +20,7 @@ import normalizeOptions from "./main/normalize-options.js"; import arrayify from "./utils/arrayify.js"; import partition from "./utils/partition.js"; import isNonEmptyArray from "./utils/is-non-empty-array.js"; - -const builtinPlugins = Object.values(languages); +import loadBuiltinPlugins from "./common/load-builtin-plugins.js"; /** * @param {*} fn @@ -35,13 +33,16 @@ function withPlugins( ) { return async (...args) => { const opts = args[optsArgIdx] || {}; + const plugins = ( + await Promise.all([ + loadBuiltinPlugins(), + loadPlugins(opts.plugins, opts.pluginSearchDirs), + ]) + ).flat(); args[optsArgIdx] = { ...opts, - plugins: [ - ...builtinPlugins, - ...(await loadPlugins(opts.plugins, opts.pluginSearchDirs)), - ], + plugins, }; return fn(...args); }; diff --git a/src/language-css/index.js b/src/language-css/index.js index 1965ea92f..75a42ae38 100644 --- a/src/language-css/index.js +++ b/src/language-css/index.js @@ -1,10 +1,17 @@ import createParsers from "../utils/create-parsers.js"; -import { default as parsersConfig } from "./parsers.js"; import printer from "./printer-postcss.js"; export const printers = { postcss: printer, }; -export const parsers = createParsers(parsersConfig); +export const parsers = createParsers( + // TODO: switch these to just `postcss` and use `language` instead. + [ + { + importParsers: () => import("./parser-postcss.js"), + parserNames: ["css", "less", "scss"], + }, + ] +); export { default as languages } from "./languages.evaluate.js"; export { default as options } from "./options.js"; diff --git a/src/language-css/parser-postcss.js b/src/language-css/parser-postcss.js index 88744ac68..887142f77 100644 --- a/src/language-css/parser-postcss.js +++ b/src/language-css/parser-postcss.js @@ -436,18 +436,6 @@ const postCssParser = { locEnd, }; -// Export as a plugin so we can reuse the same bundle for UMD loading -export const parsers = { - css: { - ...postCssParser, - parse: parseCss, - }, - less: { - ...postCssParser, - parse: parseLess, - }, - scss: { - ...postCssParser, - parse: parseScss, - }, -}; +export const css = { ...postCssParser, parse: parseCss }; +export const less = { ...postCssParser, parse: parseLess }; +export const scss = { ...postCssParser, parse: parseScss }; diff --git a/src/language-css/parsers.js b/src/language-css/parsers.js deleted file mode 100644 index 92fbf3835..000000000 --- a/src/language-css/parsers.js +++ /dev/null @@ -1,9 +0,0 @@ -// TODO: switch these to just `postcss` and use `language` instead. -const parsers = [ - { - importPlugin: () => import("./parser-postcss.js"), - parserNames: ["css", "less", "scss"], - }, -]; - -export default parsers; diff --git a/src/language-graphql/index.js b/src/language-graphql/index.js index c3913fdc9..de7b6379a 100644 --- a/src/language-graphql/index.js +++ b/src/language-graphql/index.js @@ -1,10 +1,14 @@ import createParsers from "../utils/create-parsers.js"; -import { default as parsersConfig } from "./parsers.js"; import printer from "./printer-graphql.js"; export const printers = { graphql: printer, }; -export const parsers = createParsers(parsersConfig); +export const parsers = createParsers([ + { + importParsers: () => import("./parser-graphql.js"), + parserNames: ["graphql"], + }, +]); export { default as languages } from "./languages.evaluate.js"; export { default as options } from "./options.js"; diff --git a/src/language-graphql/parser-graphql.js b/src/language-graphql/parser-graphql.js index ff64bfa1c..0d6480f06 100644 --- a/src/language-graphql/parser-graphql.js +++ b/src/language-graphql/parser-graphql.js @@ -45,12 +45,10 @@ function parse(text /*, options */) { return ast; } -export const parsers = { - graphql: { - parse, - astFormat: "graphql", - hasPragma, - locStart, - locEnd, - }, +export const graphql = { + parse, + astFormat: "graphql", + hasPragma, + locStart, + locEnd, }; diff --git a/src/language-graphql/parsers.js b/src/language-graphql/parsers.js deleted file mode 100644 index cb0c6bc26..000000000 --- a/src/language-graphql/parsers.js +++ /dev/null @@ -1,8 +0,0 @@ -const parsers = [ - { - importPlugin: () => import("./parser-graphql.js"), - parserNames: ["graphql"], - }, -]; - -export default parsers; diff --git a/src/language-handlebars/index.js b/src/language-handlebars/index.js index 8ccca6f65..daafefe10 100644 --- a/src/language-handlebars/index.js +++ b/src/language-handlebars/index.js @@ -1,9 +1,13 @@ import createParsers from "../utils/create-parsers.js"; -import { default as parsersConfig } from "./parsers.js"; import printer from "./printer-glimmer.js"; export const printers = { glimmer: printer, }; -export const parsers = createParsers(parsersConfig); +export const parsers = createParsers([ + { + importParsers: () => import("./parser-glimmer.js"), + parserNames: ["glimmer"], + }, +]); export { default as languages } from "./languages.evaluate.js"; diff --git a/src/language-handlebars/parser-glimmer.js b/src/language-handlebars/parser-glimmer.js index ea25b2b93..2a776dbeb 100644 --- a/src/language-handlebars/parser-glimmer.js +++ b/src/language-handlebars/parser-glimmer.js @@ -146,11 +146,9 @@ function getErrorLocation(error) { } } -export const parsers = { - glimmer: { - parse, - astFormat: "glimmer", - locStart, - locEnd, - }, +export const glimmer = { + parse, + astFormat: "glimmer", + locStart, + locEnd, }; diff --git a/src/language-handlebars/parsers.js b/src/language-handlebars/parsers.js deleted file mode 100644 index dbd2c880e..000000000 --- a/src/language-handlebars/parsers.js +++ /dev/null @@ -1,8 +0,0 @@ -const parsers = [ - { - importPlugin: () => import("./parser-glimmer.js"), - parserNames: ["glimmer"], - }, -]; - -export default parsers; diff --git a/src/language-html/index.js b/src/language-html/index.js index 3f095847f..a76a25a9e 100644 --- a/src/language-html/index.js +++ b/src/language-html/index.js @@ -1,10 +1,14 @@ import createParsers from "../utils/create-parsers.js"; -import { default as parsersConfig } from "./parsers.js"; import printer from "./printer-html.js"; export const printers = { html: printer, }; -export const parsers = createParsers(parsersConfig); +export const parsers = createParsers([ + { + importParsers: () => import("./parser-html.js"), + parserNames: ["html", "vue", "angular", "lwc"], + }, +]); export { default as languages } from "./languages.evaluate.js"; export { default as options } from "./options.js"; diff --git a/src/language-html/parser-html.js b/src/language-html/parser-html.js index e1d492b69..77386f463 100644 --- a/src/language-html/parser-html.js +++ b/src/language-html/parser-html.js @@ -374,26 +374,28 @@ const HTML_PARSE_OPTIONS = { allowHtmComponentClosingTags: true, }; -export const parsers = { - html: createParser(HTML_PARSE_OPTIONS), - angular: createParser({ name: "angular" }), - vue: createParser({ - name: "vue", - isTagNameCaseSensitive: true, - shouldParseAsRawText(tagName, prefix, hasParent, attrs) { - return ( - tagName.toLowerCase() !== "html" && - !hasParent && - (tagName !== "template" || - attrs.some( - ({ name, value }) => - name === "lang" && - value !== "html" && - value !== "" && - value !== undefined - )) - ); - }, - }), - lwc: createParser({ name: "lwc", canSelfClose: false }), -}; +// HTML +export const html = createParser(HTML_PARSE_OPTIONS); +// Angular +export const angular = createParser({ name: "angular" }); +// Vue +export const vue = createParser({ + name: "vue", + isTagNameCaseSensitive: true, + shouldParseAsRawText(tagName, prefix, hasParent, attrs) { + return ( + tagName.toLowerCase() !== "html" && + !hasParent && + (tagName !== "template" || + attrs.some( + ({ name, value }) => + name === "lang" && + value !== "html" && + value !== "" && + value !== undefined + )) + ); + }, +}); +// Lightning Web Components +export const lwc = createParser({ name: "lwc", canSelfClose: false }); diff --git a/src/language-html/parsers.js b/src/language-html/parsers.js deleted file mode 100644 index cd3249a22..000000000 --- a/src/language-html/parsers.js +++ /dev/null @@ -1,17 +0,0 @@ -const parsers = [ - { - importPlugin: () => import("./parser-html.js"), - parserNames: [ - // HTML - "html", - // Vue - "vue", - // Angular - "angular", - // Lightning Web Components - "lwc", - ], - }, -]; - -export default parsers; diff --git a/src/language-js/index.js b/src/language-js/index.js deleted file mode 100644 index ce7f1314f..000000000 --- a/src/language-js/index.js +++ /dev/null @@ -1,10 +0,0 @@ -import createParsers from "../utils/create-parsers.js"; -import { default as parsersConfig } from "./parse/parsers.js"; -import estreePrinter from "./printer-estree.js"; - -export const printers = { - estree: estreePrinter, -}; -export const parsers = createParsers(parsersConfig); -export { default as languages } from "./languages.evaluate.js"; -export { default as options } from "./options.js"; diff --git a/src/language-js/parse/acorn-and-espree.js b/src/language-js/parse/acorn-and-espree.js deleted file mode 100644 index 87c941ea0..000000000 --- a/src/language-js/parse/acorn-and-espree.js +++ /dev/null @@ -1,7 +0,0 @@ -import acorn from "./acorn.js"; -import espree from "./espree.js"; - -export const parsers = { - acorn, - espree, -}; diff --git a/src/language-js/parse/acorn.js b/src/language-js/parse/acorn.js index 5264f6789..57d804602 100644 --- a/src/language-js/parse/acorn.js +++ b/src/language-js/parse/acorn.js @@ -82,4 +82,4 @@ function parse(text, options = {}) { return postprocess(ast, { text }); } -export default createParser(parse); +export const acorn = createParser(parse); diff --git a/src/language-js/parse/angular.js b/src/language-js/parse/angular.js index d07c5026e..acfd1a040 100644 --- a/src/language-js/parse/angular.js +++ b/src/language-js/parse/angular.js @@ -28,9 +28,7 @@ function createParser(parseMethod) { }; } -export const parsers = { - __ng_action: createParser(parseAction), - __ng_binding: createParser(parseBinding), - __ng_interpolation: createParser(parseInterpolationExpression), - __ng_directive: createParser(parseTemplateBindings), -}; +export const __ng_action = createParser(parseAction); +export const __ng_binding = createParser(parseBinding); +export const __ng_interpolation = createParser(parseInterpolationExpression); +export const __ng_directive = createParser(parseTemplateBindings); diff --git a/src/language-js/parse/babel.js b/src/language-js/parse/babel.js index 767e30ef5..b26cfb2a5 100644 --- a/src/language-js/parse/babel.js +++ b/src/language-js/parse/babel.js @@ -2,8 +2,6 @@ import { parse as babelParse, parseExpression } from "@babel/parser"; import tryCombinations from "../../utils/try-combinations.js"; import getShebang from "../utils/get-shebang.js"; import getNextNonSpaceNonCommentCharacterIndex from "../../utils/get-next-non-space-non-comment-character-index.js"; -// JSON parsers are bundled here so we can reduce package size -import jsonParsers from "../../language-json/parser-json.js"; import createParser from "./utils/create-parser.js"; import createBabelParseError from "./utils/create-babel-parse-error.js"; import postprocess from "./postprocess/index.js"; @@ -248,12 +246,10 @@ const babelEstree = createBabelParser({ ), }); -// Export as a plugin so we can reuse the same bundle for UMD loading -export const parsers = { +export default { babel, "babel-flow": babelFlow, "babel-ts": babelTs, - ...jsonParsers, /** @internal */ __js_expression: babelExpression, /** for vue filter */ diff --git a/src/language-js/parse/espree.js b/src/language-js/parse/espree.js index 28e6c0b4a..4dcc1e0ca 100644 --- a/src/language-js/parse/espree.js +++ b/src/language-js/parse/espree.js @@ -55,4 +55,4 @@ function parse(text, options = {}) { return postprocess(ast, { text }); } -export default createParser(parse); +export const espree = createParser(parse); diff --git a/src/language-js/parse/flow.js b/src/language-js/parse/flow.js index f5f90d219..66bf9dcf8 100644 --- a/src/language-js/parse/flow.js +++ b/src/language-js/parse/flow.js @@ -50,7 +50,4 @@ function parse(text) { return postprocess(ast, { text }); } -// Export as a plugin so we can reuse the same bundle for UMD loading -export const parsers = { - flow: createParser(parse), -}; +export const flow = createParser(parse); diff --git a/src/language-js/parse/meriyah.js b/src/language-js/parse/meriyah.js index 396ad9c21..30731ec8c 100644 --- a/src/language-js/parse/meriyah.js +++ b/src/language-js/parse/meriyah.js @@ -102,6 +102,4 @@ function parse(text, options = {}) { return postprocess(ast, { parser: "meriyah", text }); } -export const parsers = { - meriyah: createParser(parse), -}; +export const meriyah = createParser(parse); diff --git a/src/language-js/parse/parsers.js b/src/language-js/parse/parsers.js deleted file mode 100644 index e503031ce..000000000 --- a/src/language-js/parse/parsers.js +++ /dev/null @@ -1,46 +0,0 @@ -const parsers = [ - { - importPlugin: () => import("./babel.js"), - parserNames: [ - "babel", - "babel-flow", - "babel-ts", - "json", - "json5", - "json-stringify", - "__js_expression", - "__vue_expression", - "__vue_ts_expression", - "__vue_event_binding", - "__vue_ts_event_binding", - "__babel_estree", - ], - }, - { - importPlugin: () => import("./flow.js"), - parserNames: ["flow"], - }, - { - importPlugin: () => import("./typescript.js"), - parserNames: ["typescript"], - }, - { - importPlugin: () => import("./angular.js"), - parserNames: [ - "__ng_action", - "__ng_binding", - "__ng_interpolation", - "__ng_directive", - ], - }, - { - importPlugin: () => import("./acorn-and-espree.js"), - parserNames: ["acorn", "espree"], - }, - { - importPlugin: () => import("./meriyah.js"), - parserNames: ["meriyah"], - }, -]; - -export default parsers; diff --git a/src/language-js/parse/typescript.js b/src/language-js/parse/typescript.js index 438c1d9c0..3784071d4 100644 --- a/src/language-js/parse/typescript.js +++ b/src/language-js/parse/typescript.js @@ -77,7 +77,4 @@ function isProbablyJsx(text) { ).test(text); } -// Export as a plugin so we can reuse the same bundle for UMD loading -export const parsers = { - typescript: createParser(parse), -}; +export const typescript = createParser(parse); diff --git a/src/language-js/printer-estree.js b/src/language-js/printer-estree.js index 699ecae84..1f0aced0e 100644 --- a/src/language-js/printer-estree.js +++ b/src/language-js/printer-estree.js @@ -13,10 +13,7 @@ import { import { replaceEndOfLine, inheritLabel } from "../document/utils.js"; import UnexpectedNodeError from "../utils/unexpected-node-error.js"; import isNonEmptyArray from "../utils/is-non-empty-array.js"; -import embed from "./embed.js"; -import clean from "./clean.js"; -import { insertPragma } from "./pragma.js"; -import * as commentsRelatedPrinterMethods from "./comments/printer-methods.js"; + import pathNeedsParens from "./needs-parens.js"; import { hasComment, @@ -35,7 +32,6 @@ import { import { locStart, locEnd } from "./loc.js"; import isBlockComment from "./utils/is-block-comment.js"; import isIgnored from "./utils/is-ignored.js"; -import getVisitorKeys from "./traverse/get-visitor-keys.js"; import { printHtmlBinding, @@ -773,13 +769,9 @@ function printPathNoParens(path, options, print, args) { } } -const printer = { - print: genericPrint, - embed, - insertPragma, - massageAstNode: clean, - getVisitorKeys, - ...commentsRelatedPrinterMethods, -}; - -export default printer; +export { genericPrint as print }; +export * from "./comments/printer-methods.js"; +export { default as embed } from "./embed.js"; +export { default as massageAstNode } from "./clean.js"; +export { insertPragma } from "./pragma.js"; +export { default as getVisitorKeys } from "./traverse/get-visitor-keys.js"; diff --git a/src/language-json/index.js b/src/language-json/index.js deleted file mode 100644 index bc0daef2f..000000000 --- a/src/language-json/index.js +++ /dev/null @@ -1,6 +0,0 @@ -import estreeJsonPrinter from "./printer-estree-json.js"; - -export const printers = { - "estree-json": estreeJsonPrinter, -}; -export { default as languages } from "./languages.evaluate.js"; diff --git a/src/language-json/printer-estree-json.js b/src/language-json/printer-estree-json.js index 0f0e9d2c6..cf139dce0 100644 --- a/src/language-json/printer-estree-json.js +++ b/src/language-json/printer-estree-json.js @@ -1,6 +1,5 @@ import { hardline, indent, join } from "../document/builders.js"; import UnexpectedNodeError from "../utils/unexpected-node-error.js"; -import getVisitorKeys from "./get-visitor-keys.js"; function genericPrint(path, options, print) { const { node } = path; @@ -113,10 +112,5 @@ function clean(node, newNode /*, parent*/) { clean.ignoredProperties = ignoredProperties; -const printer = { - print: genericPrint, - massageAstNode: clean, - getVisitorKeys, -}; - -export default printer; +export { genericPrint as print, clean as massageAstNode }; +export { default as getVisitorKeys } from "./get-visitor-keys.js"; diff --git a/src/language-markdown/index.js b/src/language-markdown/index.js index de70a59ea..cf1492d0a 100644 --- a/src/language-markdown/index.js +++ b/src/language-markdown/index.js @@ -1,10 +1,14 @@ import createParsers from "../utils/create-parsers.js"; -import { default as parsersConfig } from "./parsers.js"; import printer from "./printer-markdown.js"; export const printers = { mdast: printer, }; -export const parsers = createParsers(parsersConfig); +export const parsers = createParsers([ + { + importParsers: () => import("./parser-markdown.js"), + parserNames: ["remark", "markdown", "mdx"], + }, +]); export { default as languages } from "./languages.evaluate.js"; export { default as options } from "./options.js"; diff --git a/src/language-markdown/parser-markdown.js b/src/language-markdown/parser-markdown.js index 7c704f1ff..7d483fc6b 100644 --- a/src/language-markdown/parser-markdown.js +++ b/src/language-markdown/parser-markdown.js @@ -53,12 +53,6 @@ const baseParser = { locEnd, }; -const markdownParser = { ...baseParser, parse: createParse({ isMDX: false }) }; - -const mdxParser = { ...baseParser, parse: createParse({ isMDX: true }) }; - -export const parsers = { - remark: markdownParser, - markdown: markdownParser, - mdx: mdxParser, -}; +export const markdown = { ...baseParser, parse: createParse({ isMDX: false }) }; +export const mdx = { ...baseParser, parse: createParse({ isMDX: true }) }; +export { markdown as remark }; diff --git a/src/language-markdown/parsers.js b/src/language-markdown/parsers.js deleted file mode 100644 index 63bd7dc1a..000000000 --- a/src/language-markdown/parsers.js +++ /dev/null @@ -1,8 +0,0 @@ -const parsers = [ - { - importPlugin: () => import("./parser-markdown.js"), - parserNames: ["remark", "markdown", "mdx"], - }, -]; - -export default parsers; diff --git a/src/language-yaml/index.js b/src/language-yaml/index.js index 42619dd75..6f96ee690 100644 --- a/src/language-yaml/index.js +++ b/src/language-yaml/index.js @@ -1,10 +1,14 @@ import createParsers from "../utils/create-parsers.js"; -import { default as parsersConfig } from "./parsers.js"; import printer from "./printer-yaml.js"; export const printers = { yaml: printer, }; -export const parsers = createParsers(parsersConfig); +export const parsers = createParsers([ + { + importParsers: () => import("./parser-yaml.js"), + parserNames: ["yaml"], + }, +]); export { default as languages } from "./languages.evaluate.js"; export { default as options } from "./options.js"; diff --git a/src/language-yaml/parser-yaml.js b/src/language-yaml/parser-yaml.js index 3abae43bd..bae509941 100644 --- a/src/language-yaml/parser-yaml.js +++ b/src/language-yaml/parser-yaml.js @@ -29,14 +29,10 @@ function parse(text) { } } -const parser = { +export const yaml = { astFormat: "yaml", parse, hasPragma, locStart, locEnd, }; - -export const parsers = { - yaml: parser, -}; diff --git a/src/language-yaml/parsers.js b/src/language-yaml/parsers.js deleted file mode 100644 index a89c5f77a..000000000 --- a/src/language-yaml/parsers.js +++ /dev/null @@ -1,8 +0,0 @@ -const parsers = [ - { - importPlugin: () => import("./parser-yaml.js"), - parserNames: ["yaml"], - }, -]; - -export default parsers; diff --git a/src/languages.js b/src/languages.js deleted file mode 100644 index e9861713e..000000000 --- a/src/languages.js +++ /dev/null @@ -1,8 +0,0 @@ -export * as js from "./language-js/index.js"; -export * as css from "./language-css/index.js"; -export * as handlebars from "./language-handlebars/index.js"; -export * as graphql from "./language-graphql/index.js"; -export * as markdown from "./language-markdown/index.js"; -export * as html from "./language-html/index.js"; -export * as yaml from "./language-yaml/index.js"; -export * as json from "./language-json/index.js"; diff --git a/src/main/normalize-format-options.js b/src/main/normalize-format-options.js index 3a7c70044..f2dda6bc2 100644 --- a/src/main/normalize-format-options.js +++ b/src/main/normalize-format-options.js @@ -49,7 +49,6 @@ async function normalizeFormatOptions(options, opts = {}) { } } } - const parser = await resolveParser( // @ts-expect-error normalizeOptions( diff --git a/src/plugins/acorn.js b/src/plugins/acorn.js new file mode 100644 index 000000000..9dbab7295 --- /dev/null +++ b/src/plugins/acorn.js @@ -0,0 +1,13 @@ +import createParsers from "../utils/create-parsers.js"; + +export const parsers = createParsers([ + { + importParsers: () => import("../language-js/parse/acorn.js"), + parserNames: ["acorn"], + }, + { + importParsers: () => import("../language-js/parse/espree.js"), + parserNames: ["espree"], + }, +]); +export default { parsers }; diff --git a/src/plugins/angular.js b/src/plugins/angular.js new file mode 100644 index 000000000..d71875b8d --- /dev/null +++ b/src/plugins/angular.js @@ -0,0 +1,14 @@ +import createParsers from "../utils/create-parsers.js"; + +export const parsers = createParsers([ + { + importParsers: () => import("../language-js/parse/angular.js"), + parserNames: [ + "__ng_action", + "__ng_binding", + "__ng_interpolation", + "__ng_directive", + ], + }, +]); +export default { parsers }; diff --git a/src/plugins/babel.js b/src/plugins/babel.js new file mode 100644 index 000000000..752da8a6d --- /dev/null +++ b/src/plugins/babel.js @@ -0,0 +1,26 @@ +import createParsers from "../utils/create-parsers.js"; + +export const parsers = createParsers([ + { + importParsers: async () => + (await import("../language-js/parse/babel.js")).default, + parserNames: [ + "babel", + "babel-flow", + "babel-ts", + "__js_expression", + "__vue_expression", + "__vue_ts_expression", + "__vue_event_binding", + "__vue_ts_event_binding", + "__babel_estree", + ], + }, + // JSON parsers are based on babel, bundle together to reduce package size + { + importParsers: async () => + (await import("../language-json/parser-json.js")).default, + parserNames: ["json", "json5", "json-stringify"], + }, +]); +export default { parsers }; diff --git a/src/plugins/estree.js b/src/plugins/estree.js index e8a947835..682c470b2 100644 --- a/src/plugins/estree.js +++ b/src/plugins/estree.js @@ -1,11 +1,13 @@ -import estreePrinter from "../language-js/printer-estree.js"; +import * as estreePrinter from "../language-js/printer-estree.js"; import jsLanguages from "../language-js/languages.evaluate.js"; -import estreeJsonPrinter from "../language-json/printer-estree-json.js"; +import * as estreeJsonPrinter from "../language-json/printer-estree-json.js"; import jsonLanguages from "../language-json/languages.evaluate.js"; +import options from "../language-js/options.js"; export const printers = { estree: estreePrinter, "estree-json": estreeJsonPrinter, }; export const languages = [...jsLanguages, ...jsonLanguages]; -export { default as options } from "../language-js/options.js"; +export { options }; +export default { printers, languages, options }; diff --git a/src/plugins/flow.js b/src/plugins/flow.js new file mode 100644 index 000000000..6de6b1a1d --- /dev/null +++ b/src/plugins/flow.js @@ -0,0 +1,9 @@ +import createParsers from "../utils/create-parsers.js"; + +export const parsers = createParsers([ + { + importParsers: () => import("../language-js/parse/flow.js"), + parserNames: ["flow"], + }, +]); +export default { parsers }; diff --git a/src/plugins/glimmer.js b/src/plugins/glimmer.js new file mode 100644 index 000000000..86f4d64d7 --- /dev/null +++ b/src/plugins/glimmer.js @@ -0,0 +1,2 @@ +export * from "../language-handlebars/index.js"; +export * as default from "../language-handlebars/index.js"; diff --git a/src/plugins/graphql.js b/src/plugins/graphql.js new file mode 100644 index 000000000..1279f5de1 --- /dev/null +++ b/src/plugins/graphql.js @@ -0,0 +1,2 @@ +export * from "../language-graphql/index.js"; +export * as default from "../language-graphql/index.js"; diff --git a/src/plugins/html.js b/src/plugins/html.js new file mode 100644 index 000000000..22fd2f977 --- /dev/null +++ b/src/plugins/html.js @@ -0,0 +1,2 @@ +export * from "../language-html/index.js"; +export * as default from "../language-html/index.js"; diff --git a/src/plugins/markdown.js b/src/plugins/markdown.js new file mode 100644 index 000000000..97ac2f4a5 --- /dev/null +++ b/src/plugins/markdown.js @@ -0,0 +1,2 @@ +export * from "../language-markdown/index.js"; +export * as default from "../language-markdown/index.js"; diff --git a/src/plugins/meriyah.js b/src/plugins/meriyah.js new file mode 100644 index 000000000..1d054a8d0 --- /dev/null +++ b/src/plugins/meriyah.js @@ -0,0 +1,9 @@ +import createParsers from "../utils/create-parsers.js"; + +export const parsers = createParsers([ + { + importParsers: () => import("../language-js/parse/meriyah.js"), + parserNames: ["meriyah"], + }, +]); +export default { parsers }; diff --git a/src/plugins/postcss.js b/src/plugins/postcss.js new file mode 100644 index 000000000..96e4e90f6 --- /dev/null +++ b/src/plugins/postcss.js @@ -0,0 +1,2 @@ +export * from "../language-css/index.js"; +export * as default from "../language-css/index.js"; diff --git a/src/plugins/typescript.js b/src/plugins/typescript.js new file mode 100644 index 000000000..6180a7e2a --- /dev/null +++ b/src/plugins/typescript.js @@ -0,0 +1,9 @@ +import createParsers from "../utils/create-parsers.js"; + +export const parsers = createParsers([ + { + importParsers: () => import("../language-js/parse/typescript.js"), + parserNames: ["typescript"], + }, +]); +export default { parsers }; diff --git a/src/plugins/yaml.js b/src/plugins/yaml.js new file mode 100644 index 000000000..62da32e91 --- /dev/null +++ b/src/plugins/yaml.js @@ -0,0 +1,2 @@ +export * from "../language-yaml/index.js"; +export * as default from "../language-yaml/index.js"; diff --git a/src/standalone.js b/src/standalone.js index 30161a78f..631e15f70 100644 --- a/src/standalone.js +++ b/src/standalone.js @@ -1,8 +1,6 @@ import * as core from "./main/core.js"; import { getSupportInfo as getSupportInfoWithoutPlugins } from "./main/support.js"; -const builtinPlugins = []; - function withPlugins( fn, optsArgIdx = 1 // Usually `opts` is the 2nd argument @@ -15,10 +13,7 @@ function withPlugins( args[optsArgIdx] = { ...opts, - plugins: [ - ...builtinPlugins, - ...(Array.isArray(plugins) ? plugins : Object.values(plugins)), - ], + plugins: Array.isArray(plugins) ? plugins : Object.values(plugins), }; return fn(...args); diff --git a/src/utils/create-parsers.js b/src/utils/create-parsers.js index a69d983b4..fad8d484a 100644 --- a/src/utils/create-parsers.js +++ b/src/utils/create-parsers.js @@ -1,18 +1,10 @@ function createParsers(modules) { - /* c8 ignore start */ - if (!modules) { - return; - } - /* c8 ignore end */ - const parsers = Object.create(null); - for (const { importPlugin, parserNames } of modules) { + for (const { importParsers, parserNames } of modules) { for (const parserName of parserNames) { - parsers[parserName] = async () => { - const plugin = await importPlugin(); - return Object.assign(parsers, plugin.parsers)[parserName]; - }; + parsers[parserName] = async () => + Object.assign(parsers, await importParsers())[parserName]; } } diff --git a/tests/dts/unit/cases/doc.ts b/tests/dts/unit/cases/doc.ts index 05602205e..c5aace0d5 100644 --- a/tests/dts/unit/cases/doc.ts +++ b/tests/dts/unit/cases/doc.ts @@ -1,5 +1,5 @@ import * as doc from "../../../../src/document/public.js"; -doc.builders.dedent; -doc.printer.printDocToString; -doc.utils.mapDoc; +doc.builders.dedent(doc.builders.hardline); +doc.printer.printDocToString(["doc"], { printWidth: 80, tabWidth: 2 }); +doc.utils.mapDoc(["doc"], (doc) => doc); diff --git a/tests/dts/unit/cases/parsers.ts b/tests/dts/unit/cases/parsers.ts index c74d402bb..aae6bbe6c 100644 --- a/tests/dts/unit/cases/parsers.ts +++ b/tests/dts/unit/cases/parsers.ts @@ -1,50 +1,54 @@ import * as prettier from "../../../../dist/index.js"; -import * as acornEspreePlugin from "../../../../dist/plugins/acorn-and-espree.js"; -import * as angularPlugin from "../../../../dist/plugins/angular.js"; -import * as babelPlugin from "../../../../dist/plugins/babel.js"; -import * as flowPlugin from "../../../../dist/plugins/flow.js"; -import * as glimmerPlugin from "../../../../dist/plugins/glimmer.js"; -import * as graphqlPlugin from "../../../../dist/plugins/graphql.js"; -import * as htmlPlugin from "../../../../dist/plugins/html.js"; -import * as markdownPlugin from "../../../../dist/plugins/markdown.js"; -import * as typescriptPlugin from "../../../../dist/plugins/typescript.js"; -import * as meriyahPlugin from "../../../../dist/plugins/meriyah.js"; -import * as postcssPlugin from "../../../../dist/plugins/postcss.js"; -import * as yamlPlugin from "../../../../dist/plugins/yaml.js"; +import * as prettierPluginEstree from "../../../../dist/plugins/estree.js"; +import * as prettierPluginBabel from "../../../../dist/plugins/babel.js"; +import * as prettierPluginFlow from "../../../../dist/plugins/flow.js"; +import * as prettierPluginTypeScript from "../../../../dist/plugins/typescript.js"; +import * as prettierPluginAcorn from "../../../../dist/plugins/acorn.js"; +import * as prettierPluginMeriyah from "../../../../dist/plugins/meriyah.js"; +import * as prettierPluginAngular from "../../../../dist/plugins/angular.js"; +import * as prettierPluginPostcss from "../../../../dist/plugins/postcss.js"; +import * as prettierPluginGraphql from "../../../../dist/plugins/graphql.js"; +import * as prettierPluginMarkdown from "../../../../dist/plugins/markdown.js"; +import * as prettierPluginGlimmer from "../../../../dist/plugins/glimmer.js"; +import * as prettierPluginHtml from "../../../../dist/plugins/html.js"; +import * as prettierPluginYaml from "../../../../dist/plugins/yaml.js"; -acornEspreePlugin.parsers.acorn.parse; -acornEspreePlugin.parsers.espree.parse; -angularPlugin.parsers.__ng_action.parse; -babelPlugin.parsers.babel.parse; -flowPlugin.parsers.flow.parse; -glimmerPlugin.parsers.glimmer.parse; -graphqlPlugin.parsers.graphql.parse; -htmlPlugin.parsers.html.parse; -htmlPlugin.parsers.vue.parse; -htmlPlugin.parsers.lwc.parse; -htmlPlugin.parsers.angular.parse; -markdownPlugin.parsers.markdown.parse; -markdownPlugin.parsers.mdx.parse; -typescriptPlugin.parsers.typescript.parse; -meriyahPlugin.parsers.meriyah.parse; -postcssPlugin.parsers.css.parse; -postcssPlugin.parsers.less.parse; -postcssPlugin.parsers.scss.parse; -yamlPlugin.parsers.yaml.parse; +prettierPluginBabel.parsers.babel.parse("code"); +prettierPluginFlow.parsers.flow.parse("code"); +prettierPluginTypeScript.parsers.typescript.parse("code"); +prettierPluginAcorn.parsers.acorn.parse("code"); +prettierPluginAcorn.parsers.espree.parse("code"); +prettierPluginMeriyah.parsers.meriyah.parse("code"); +prettierPluginAngular.parsers.__ng_action.parse("code"); +prettierPluginPostcss.parsers.css.parse("code"); +prettierPluginPostcss.parsers.less.parse("code"); +prettierPluginPostcss.parsers.scss.parse("code"); +prettierPluginGraphql.parsers.graphql.parse("code"); +prettierPluginMarkdown.parsers.remark.parse("code"); +prettierPluginMarkdown.parsers.markdown.parse("code"); +prettierPluginMarkdown.parsers.mdx.parse("code"); +prettierPluginGlimmer.parsers.glimmer.parse("code"); +prettierPluginHtml.parsers.html.parse("code"); +prettierPluginHtml.parsers.vue.parse("code"); +prettierPluginHtml.parsers.lwc.parse("code"); +prettierPluginHtml.parsers.angular.parse("code"); +prettierPluginYaml.parsers.yaml.parse("code"); prettier.format("hello world", { plugins: [ - acornEspreePlugin, - angularPlugin, - babelPlugin, - flowPlugin, - glimmerPlugin, - htmlPlugin, - markdownPlugin, - meriyahPlugin, - postcssPlugin, - typescriptPlugin, - yamlPlugin, + prettierPluginEstree, + prettierPluginBabel, + prettierPluginFlow, + prettierPluginTypeScript, + prettierPluginAcorn, + prettierPluginMeriyah, + prettierPluginAngular, + prettierPluginPostcss, + prettierPluginGraphql, + prettierPluginMarkdown, + prettierPluginGlimmer, + prettierPluginHtml, + prettierPluginYaml, ], }); diff --git a/tests/dts/unit/run.js b/tests/dts/unit/run.js index 2cd5a132d..31ca0d8e2 100644 --- a/tests/dts/unit/run.js +++ b/tests/dts/unit/run.js @@ -3,7 +3,7 @@ import path from "node:path"; import url from "node:url"; import { default as ts } from "typescript"; -const isProduction = process.env.NODE_ENV === "production"; +// const isProduction = process.env.NODE_ENV === "production"; describe("Unit tests for dts files", () => { test("no errors", () => { @@ -12,7 +12,9 @@ describe("Unit tests for dts files", () => { ); const testCaseFiles = fs .readdirSync(testCasesDirPath) - .filter((file) => (isProduction ? true : file !== "parsers.ts")) + // Disabled due to OOM issue + // .filter((file) => (isProduction ? true : file !== "parsers.ts")) + .filter((file) => file !== "parsers.ts") .map((file) => path.join(testCasesDirPath, file)); /** @type {import("typescript").CompilerOptions} */ diff --git a/tests/integration/__tests__/plugin-parsers.js b/tests/integration/__tests__/plugin-parsers.js deleted file mode 100644 index a2584bb62..000000000 --- a/tests/integration/__tests__/plugin-parsers.js +++ /dev/null @@ -1,18 +0,0 @@ -test("parsers", async () => { - for (const parsersConfigModule of [ - "../../../src/language-css/parsers.js", - "../../../src/language-graphql/parsers.js", - "../../../src/language-handlebars/parsers.js", - "../../../src/language-html/parsers.js", - "../../../src/language-js/parse/parsers.js", - "../../../src/language-markdown/parsers.js", - "../../../src/language-yaml/parsers.js", - ]) { - const { default: parserConfigs } = await import(parsersConfigModule); - - for (const { importPlugin, parserNames } of parserConfigs) { - const plugin = await importPlugin(); - expect(Object.keys(plugin.parsers).sort()).toEqual(parserNames.sort()); - } - } -}); diff --git a/tests/unit/builtin-parsers.js b/tests/unit/builtin-parsers.js new file mode 100644 index 000000000..b0473b5ca --- /dev/null +++ b/tests/unit/builtin-parsers.js @@ -0,0 +1,47 @@ +import loadBuiltinPlugins from "../../src/common/load-builtin-plugins.js"; + +// Snapshot to avoid mistakes +test("builtin parsers", async () => { + const parserNames = (await loadBuiltinPlugins()) + .flatMap((plugin) => (plugin.parsers ? Object.keys(plugin.parsers) : [])) + .sort(); + + expect(parserNames).toMatchInlineSnapshot(` + [ + "__babel_estree", + "__js_expression", + "__ng_action", + "__ng_binding", + "__ng_directive", + "__ng_interpolation", + "__vue_event_binding", + "__vue_expression", + "__vue_ts_event_binding", + "__vue_ts_expression", + "acorn", + "angular", + "babel", + "babel-flow", + "babel-ts", + "css", + "espree", + "flow", + "glimmer", + "graphql", + "html", + "json", + "json-stringify", + "json5", + "less", + "lwc", + "markdown", + "mdx", + "meriyah", + "remark", + "scss", + "typescript", + "vue", + "yaml", + ] + `); +});