diff --git a/scripts/build/build-types.js b/scripts/build/build-types.js new file mode 100644 index 000000000..ab413321e --- /dev/null +++ b/scripts/build/build-types.js @@ -0,0 +1,63 @@ +import fs from "node:fs"; +import path from "node:path"; +import url from "node:url"; +import { PROJECT_ROOT, DIST_DIR, writeFile } from "../utils/index.mjs"; +import { format } from "../../index.js"; + +async function typesFileBuilder({ file }) { + /** + * @typedef {{ from: string, to: string }} ImportPathReplacement + * @typedef {{ [input: string]: Array }} ReplacementMap + */ + + /** @type {ReplacementMap} */ + const pathReplacementMap = { + "src/index.d.ts": [{ from: "./document/public.js", to: "./doc.js" }], + }; + const replacements = pathReplacementMap[file.input] ?? []; + let text = await fs.promises.readFile(file.input, "utf8"); + for (const { from, to } of replacements) { + text = text.replaceAll( + new RegExp(` from "${from}";`, "g"), + ` from "${to}";` + ); + } + await writeFile(path.join(DIST_DIR, file.output.file), text); +} + +async function buildPluginTypes({ file: { input, output } }) { + const { default: plugin } = await import( + url.pathToFileURL(path.join(PROJECT_ROOT, input)) + ); + + await writeFile( + path.join(DIST_DIR, output.file), + await format( + /* indent */ ` + import { Parser } from "../index.js"; + + declare const plugin: { + parsers: { + ${Object.keys(plugin.parsers) + .map( + (parserName) => + `${" ".repeat(4)}${JSON.stringify(parserName)}: Parser;` + ) + .join("\n")} + }; + }; + + export default plugin; + `, + { parser: "typescript" } + ) + ); +} + +function buildTypes(options) { + return options.file.isPlugin + ? buildPluginTypes(options) + : typesFileBuilder(options); +} + +export default buildTypes; diff --git a/scripts/build/config.mjs b/scripts/build/config.mjs index febb683da..96cd52352 100644 --- a/scripts/build/config.mjs +++ b/scripts/build/config.mjs @@ -3,15 +3,11 @@ import url from "node:url"; import fs from "node:fs"; import { createRequire } from "node:module"; import createEsmUtils from "esm-utils"; -import { - PROJECT_ROOT, - DIST_DIR, - copyFile, - writeFile, -} from "../utils/index.mjs"; +import { PROJECT_ROOT, DIST_DIR, copyFile } from "../utils/index.mjs"; import buildJavascriptModule from "./build-javascript-module.js"; import buildPackageJson from "./build-package-json.js"; import buildLicense from "./build-license.js"; +import buildTypes from "./build-types.js"; import modifyTypescriptModule from "./modify-typescript-module.mjs"; import { getPackageFile } from "./utils.js"; @@ -28,41 +24,14 @@ const copyFileBuilder = ({ file }) => path.join(DIST_DIR, file.output.file) ); -async function typesFileBuilder({ file }) { - /** - * @typedef {{ from: string, to: string }} ImportPathReplacement - * @typedef {{ [input: string]: Array }} ReplacementMap - */ +function getTypesFileConfig({ input: jsFileInput, outputBaseName, isPlugin }) { + let input = jsFileInput; + if (!isPlugin) { + input = jsFileInput.replace(/\.[cm]?js$/, ".d.ts"); - /** @type {Array} */ - const jsParsersImportReplacement = [ - { from: "../../index.js", to: "../index.js" }, - ]; - /** @type {ReplacementMap} */ - const pathReplacementMap = { - "src/index.d.ts": [{ from: "./document/public.js", to: "./doc.js" }], - "src/language-js/parse/acorn-and-espree.d.ts": jsParsersImportReplacement, - "src/language-js/parse/angular.d.ts": jsParsersImportReplacement, - "src/language-js/parse/babel.d.ts": jsParsersImportReplacement, - "src/language-js/parse/flow.d.ts": jsParsersImportReplacement, - "src/language-js/parse/meriyah.d.ts": jsParsersImportReplacement, - "src/language-js/parse/typescript.d.ts": jsParsersImportReplacement, - }; - const replacements = pathReplacementMap[file.input] ?? []; - let data = await fs.promises.readFile(file.input, "utf8"); - for (const { from, to } of replacements) { - data = data.replaceAll( - new RegExp(` from "${from}";`, "g"), - ` from "${to}";` - ); - } - await writeFile(path.join(DIST_DIR, file.output.file), data); -} - -function getTypesFileConfig({ input: jsFileInput, outputBaseName }) { - const input = jsFileInput.replace(/\.[cm]?js$/, ".d.ts"); - if (!fs.existsSync(path.join(PROJECT_ROOT, input))) { - return; + if (!fs.existsSync(path.join(PROJECT_ROOT, input))) { + return; + } } return { @@ -71,7 +40,8 @@ function getTypesFileConfig({ input: jsFileInput, outputBaseName }) { file: outputBaseName + ".d.ts", }, kind: "types", - build: typesFileBuilder, + isPlugin, + build: buildTypes, }; } @@ -464,7 +434,7 @@ const universalFiles = [...nonPluginUniversalFiles, ...pluginFiles].flatMap( build: buildJavascriptModule, kind: "javascript", })), - getTypesFileConfig({ input, outputBaseName }), + getTypesFileConfig({ input, outputBaseName, isPlugin }), ]; } ); diff --git a/src/language-css/parser-postcss.d.ts b/src/language-css/parser-postcss.d.ts deleted file mode 100644 index 74c7d83ea..000000000 --- a/src/language-css/parser-postcss.d.ts +++ /dev/null @@ -1,11 +0,0 @@ -import { Parser } from "../index.js"; - -declare const plugin: { - parsers: { - css: Parser; - less: Parser; - scss: Parser; - }; -}; - -export default plugin; diff --git a/src/language-graphql/parser-graphql.d.ts b/src/language-graphql/parser-graphql.d.ts deleted file mode 100644 index 79e9794da..000000000 --- a/src/language-graphql/parser-graphql.d.ts +++ /dev/null @@ -1,9 +0,0 @@ -import { Parser } from "../index.js"; - -declare const plugin: { - parsers: { - graphql: Parser; - }; -}; - -export default plugin; diff --git a/src/language-handlebars/parser-glimmer.d.ts b/src/language-handlebars/parser-glimmer.d.ts deleted file mode 100644 index f4fd6267a..000000000 --- a/src/language-handlebars/parser-glimmer.d.ts +++ /dev/null @@ -1,9 +0,0 @@ -import { Parser } from "../index.js"; - -declare const plugin: { - parsers: { - glimmer: Parser; - }; -}; - -export default plugin; diff --git a/src/language-html/parser-html.d.ts b/src/language-html/parser-html.d.ts deleted file mode 100644 index 98881d2cf..000000000 --- a/src/language-html/parser-html.d.ts +++ /dev/null @@ -1,12 +0,0 @@ -import { Parser } from "../index.js"; - -declare const plugin: { - parsers: { - html: Parser; - angular: Parser; - vue: Parser; - lwc: Parser; - }; -}; - -export default plugin; diff --git a/src/language-js/parse/acorn-and-espree.d.ts b/src/language-js/parse/acorn-and-espree.d.ts deleted file mode 100644 index d538a8af4..000000000 --- a/src/language-js/parse/acorn-and-espree.d.ts +++ /dev/null @@ -1,10 +0,0 @@ -import { Parser } from "../../index.js"; - -declare const plugin: { - parsers: { - acorn: Parser; - espree: Parser; - }; -}; - -export default plugin; diff --git a/src/language-js/parse/angular.d.ts b/src/language-js/parse/angular.d.ts deleted file mode 100644 index 575726e25..000000000 --- a/src/language-js/parse/angular.d.ts +++ /dev/null @@ -1,12 +0,0 @@ -import { Parser } from "../../index.js"; - -declare const plugin: { - parsers: { - __ng_action: Parser; - __ng_binding: Parser; - __ng_interpolation: Parser; - __ng_directive: Parser; - }; -}; - -export default plugin; diff --git a/src/language-js/parse/babel.d.ts b/src/language-js/parse/babel.d.ts deleted file mode 100644 index 8c796931a..000000000 --- a/src/language-js/parse/babel.d.ts +++ /dev/null @@ -1,17 +0,0 @@ -import { Parser } from "../../index.js"; - -declare const plugin: { - parsers: { - babel: Parser; - "babel-flow": Parser; - "babel-ts": Parser; - json: Parser; - json5: Parser; - "json-stringify": Parser; - __js_expression: Parser; - __vue_expression: Parser; - __vue_event_binding: Parser; - }; -}; - -export default plugin; diff --git a/src/language-js/parse/flow.d.ts b/src/language-js/parse/flow.d.ts deleted file mode 100644 index 0018e4400..000000000 --- a/src/language-js/parse/flow.d.ts +++ /dev/null @@ -1,9 +0,0 @@ -import { Parser } from "../../index.js"; - -declare const plugin: { - parsers: { - flow: Parser; - }; -}; - -export default plugin; diff --git a/src/language-js/parse/meriyah.d.ts b/src/language-js/parse/meriyah.d.ts deleted file mode 100644 index 2945de18e..000000000 --- a/src/language-js/parse/meriyah.d.ts +++ /dev/null @@ -1,9 +0,0 @@ -import { Parser } from "../../index.js"; - -declare const plugin: { - parsers: { - meriyah: Parser; - }; -}; - -export default plugin; diff --git a/src/language-js/parse/typescript.d.ts b/src/language-js/parse/typescript.d.ts deleted file mode 100644 index fc8e13609..000000000 --- a/src/language-js/parse/typescript.d.ts +++ /dev/null @@ -1,9 +0,0 @@ -import { Parser } from "../../index.js"; - -declare const plugin: { - parsers: { - typescript: Parser; - }; -}; - -export default plugin; diff --git a/src/language-markdown/parser-markdown.d.ts b/src/language-markdown/parser-markdown.d.ts deleted file mode 100644 index 0b05b59eb..000000000 --- a/src/language-markdown/parser-markdown.d.ts +++ /dev/null @@ -1,11 +0,0 @@ -import { Parser } from "../index.js"; - -declare const plugin: { - parsers: { - remark: Parser; - markdown: Parser; - mdx: Parser; - }; -}; - -export default plugin; diff --git a/src/language-yaml/parser-yaml.d.ts b/src/language-yaml/parser-yaml.d.ts deleted file mode 100644 index 6525baba9..000000000 --- a/src/language-yaml/parser-yaml.d.ts +++ /dev/null @@ -1,9 +0,0 @@ -import { Parser } from "../index.js"; - -declare const plugin: { - parsers: { - yaml: Parser; - }; -}; - -export default plugin; diff --git a/tests/dts/unit/cases/index.ts b/tests/dts/unit/cases/index.ts index 9ff2286ab..eab307cbc 100644 --- a/tests/dts/unit/cases/index.ts +++ b/tests/dts/unit/cases/index.ts @@ -1,4 +1,4 @@ -import * as prettier from "../../../../src/index"; +import * as prettier from "../../../../src/index.js"; prettier.format("foo ( );", { semi: false }); prettier.check("foo ( );", { semi: false }); diff --git a/tests/dts/unit/cases/parsers.ts b/tests/dts/unit/cases/parsers.ts index 5b2553742..d4059da3f 100644 --- a/tests/dts/unit/cases/parsers.ts +++ b/tests/dts/unit/cases/parsers.ts @@ -1,50 +1,50 @@ -import * as prettier from "../../../../src/index"; +import * as prettier from "../../../../dist/index.js"; -import acornEspreeParser from "../../../../src/language-js/parse/acorn-and-espree"; -import angularParser from "../../../../src/language-js/parse/angular"; -import babelParser from "../../../../src/language-js/parse/babel"; -import flowParser from "../../../../src/language-js/parse/flow"; -import glimmerParser from "../../../../src/language-handlebars/parser-glimmer"; -import graphqlParser from "../../../../src/language-graphql/parser-graphql"; -import htmlParser from "../../../../src/language-html/parser-html"; -import markdownParser from "../../../../src/language-markdown/parser-markdown"; -import meriyahParser from "../../../../src/language-js/parse/meriyah"; -import postcssParser from "../../../../src/language-css/parser-postcss"; -import typescriptParser from "../../../../src/language-js/parse/typescript"; -import yamlParser from "../../../../src/language-yaml/parser-yaml"; +import acornEspreePlugin from "../../../../dist/plugins/acorn-and-espree.js"; +import angularPlugin from "../../../../dist/plugins/angular.js"; +import babelPlugin from "../../../../dist/plugins/babel.js"; +import flowPlugin from "../../../../dist/plugins/flow.js"; +import glimmerPlugin from "../../../../dist/plugins/glimmer.js"; +import graphqlPlugin from "../../../../dist/plugins/graphql.js"; +import htmlPlugin from "../../../../dist/plugins/html.js"; +import markdownPlugin from "../../../../dist/plugins/markdown.js"; +import typescriptPlugin from "../../../../dist/plugins/typescript.js"; +import meriyahPlugin from "../../../../dist/plugins/meriyah.js"; +import postcssPlugin from "../../../../dist/plugins/postcss.js"; +import yamlPlugin from "../../../../dist/plugins/yaml.js"; -acornEspreeParser.parsers.acorn.parse; -acornEspreeParser.parsers.espree.parse; -angularParser.parsers.__ng_action.parse; -babelParser.parsers.babel.parse; -flowParser.parsers.flow.parse; -glimmerParser.parsers.glimmer.parse; -graphqlParser.parsers.graphql.parse; -htmlParser.parsers.html.parse; -htmlParser.parsers.vue.parse; -htmlParser.parsers.lwc.parse; -htmlParser.parsers.angular.parse; -markdownParser.parsers.markdown.parse; -markdownParser.parsers.mdx.parse; -meriyahParser.parsers.meriyah.parse; -postcssParser.parsers.css.parse; -postcssParser.parsers.less.parse; -postcssParser.parsers.scss.parse; -typescriptParser.parsers.typescript.parse; -yamlParser.parsers.yaml.parse; +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; prettier.format("hello world", { plugins: [ - acornEspreeParser, - angularParser, - babelParser, - flowParser, - glimmerParser, - htmlParser, - markdownParser, - meriyahParser, - postcssParser, - typescriptParser, - yamlParser, + acornEspreePlugin, + angularPlugin, + babelPlugin, + flowPlugin, + glimmerPlugin, + htmlPlugin, + markdownPlugin, + meriyahPlugin, + postcssPlugin, + typescriptPlugin, + yamlPlugin, ], }); diff --git a/tests/dts/unit/cases/plugins.ts b/tests/dts/unit/cases/plugins.ts index 6b0ff24ac..a85dec1e4 100644 --- a/tests/dts/unit/cases/plugins.ts +++ b/tests/dts/unit/cases/plugins.ts @@ -1,4 +1,4 @@ -import * as prettier from "../../../../src/index"; +import * as prettier from "../../../../src/index.js"; import { expectType } from "ts-expect"; interface PluginAST { diff --git a/tests/dts/unit/cases/print.ts b/tests/dts/unit/cases/print.ts index 12710b14c..444cab186 100644 --- a/tests/dts/unit/cases/print.ts +++ b/tests/dts/unit/cases/print.ts @@ -1,4 +1,4 @@ -import * as prettier from "../../../../src/index"; +import * as prettier from "../../../../src/index.js"; import { expectType } from "ts-expect"; type NestedAst = Nested1 | Nested2 | Nested3; diff --git a/tests/dts/unit/cases/standalone.ts b/tests/dts/unit/cases/standalone.ts index 52aa0297b..2a23e24d0 100644 --- a/tests/dts/unit/cases/standalone.ts +++ b/tests/dts/unit/cases/standalone.ts @@ -1,4 +1,4 @@ -import * as prettierStandalone from "../../../../src/standalone"; +import * as prettierStandalone from "../../../../src/standalone.js"; prettierStandalone.formatWithCursor(" 1", { cursorOffset: 2, parser: "babel" }); prettierStandalone.formatWithCursor(" 1", { diff --git a/tests/dts/unit/run.js b/tests/dts/unit/run.js index 746ff64a1..2cd5a132d 100644 --- a/tests/dts/unit/run.js +++ b/tests/dts/unit/run.js @@ -3,6 +3,8 @@ import path from "node:path"; import url from "node:url"; import { default as ts } from "typescript"; +const isProduction = process.env.NODE_ENV === "production"; + describe("Unit tests for dts files", () => { test("no errors", () => { const testCasesDirPath = url.fileURLToPath( @@ -10,6 +12,7 @@ describe("Unit tests for dts files", () => { ); const testCaseFiles = fs .readdirSync(testCasesDirPath) + .filter((file) => (isProduction ? true : file !== "parsers.ts")) .map((file) => path.join(testCasesDirPath, file)); /** @type {import("typescript").CompilerOptions} */