diff --git a/changelog_unreleased/api/12740.md b/changelog_unreleased/api/12740.md
index 9676f6a1d..70067e681 100644
--- a/changelog_unreleased/api/12740.md
+++ b/changelog_unreleased/api/12740.md
@@ -1,4 +1,4 @@
-#### [BREAKING] npm package file structures changed (#12740 by @fisker, #13530 by @fisker)
+#### [BREAKING] npm package file structures changed (#12740 by @fisker, #13530 by @fisker, #14570 by @fisker)
Export style changes:
@@ -46,9 +46,28 @@ File structures changes:
Check full list on .
+A new plugin has been added:
+
+- `plugins/estree.mjs` (ESM version)
+- `plugins/estree.js` (UMD version)
+
+If you use standalone version, this plugin should be loaded when printing JavaScript, TypeScript, Flow, or JSON.
+
```diff
-- import pluginBabel from "prettier/parser-babel";
-+ import pluginBabel from "prettier/plugins/babel";
+- import prettier from "prettier/standalone";
++ import * as prettier from "prettier/standalone";
+- import prettierPluginBabel from "prettier/parser-babel";
++ import prettierPluginBabel from "prettier/plugins/babel";
++ import prettierPluginEstree from "prettier/plugins/estree";
+
+console.log(
+- format(code, {
++ await format(code, {
+ parser: "babel",
+- plugins: [prettierPluginBabel],
++ plugins: [prettierPluginBabel, prettierPluginEstree],
+ })
+);
```
```diff
diff --git a/scripts/build-website.mjs b/scripts/build-website.mjs
index 5ca11608a..62568a58f 100644
--- a/scripts/build-website.mjs
+++ b/scripts/build-website.mjs
@@ -71,9 +71,11 @@ async function buildPlaygroundFiles() {
continue;
}
- const plugin = require(dist);
- for (const parser of Object.keys(plugin.parsers)) {
- parsersLocation[parser] = fileName;
+ const pluginModule = require(dist);
+ const plugin = pluginModule.default ?? pluginModule;
+ const parserNames = Object.keys(plugin.parsers ?? {});
+ for (const parserName of parserNames) {
+ parsersLocation[parserName] = fileName;
}
}
diff --git a/scripts/build/build-package-json.js b/scripts/build/build-package-json.js
index ae13d7a4d..98ac188d0 100644
--- a/scripts/build/build-package-json.js
+++ b/scripts/build/build-package-json.js
@@ -44,7 +44,12 @@ async function buildPackageJson({ file, files }) {
"./esm/standalone.mjs": "./standalone.mjs",
...Object.fromEntries(
files
- .filter((file) => file.isPlugin && file.output.format === "umd")
+ .filter(
+ (file) =>
+ file.isPlugin &&
+ file.output.format === "umd" &&
+ file.output.file !== "plugins/estree.js"
+ )
.flatMap((file) => {
let basename = path.basename(file.output.file, ".js");
if (basename === "acorn-and-espree") {
diff --git a/scripts/build/build-types.js b/scripts/build/build-types.js
index c4d2b16be..f18b7968b 100644
--- a/scripts/build/build-types.js
+++ b/scripts/build/build-types.js
@@ -1,8 +1,9 @@
import fs from "node:fs";
import path from "node:path";
import url from "node:url";
+import { isValidIdentifier } from "@babel/types";
+import { outdent } from "outdent";
import { PROJECT_ROOT, DIST_DIR, writeFile } from "../utils/index.mjs";
-import { format } from "../../index.js";
async function typesFileBuilder({ file }) {
/**
@@ -25,29 +26,36 @@ async function typesFileBuilder({ file }) {
await writeFile(path.join(DIST_DIR, file.output.file), text);
}
+function toPropertyKey(name) {
+ return isValidIdentifier(name) ? name : JSON.stringify(name);
+}
+
async function buildPluginTypes({ file: { input, output } }) {
- const plugin = await import(
+ const pluginModule = await import(
url.pathToFileURL(path.join(PROJECT_ROOT, input))
);
+ const plugin = pluginModule.default ?? pluginModule;
+ const parserNames = Object.keys(plugin.parsers ?? {});
- await writeFile(
- path.join(DIST_DIR, output.file),
- await format(
- /* indent */ `
+ // We only add `parsers` to types file, printers should not be used alone
+ // For `estree` plugin, we just write an empty file
+ const code =
+ parserNames.length === 0
+ ? ""
+ : outdent`
import { Parser } from "../index.js";
export declare const parsers: {
- ${Object.keys(plugin.parsers)
+ ${parserNames
.map(
(parserName) =>
- `${" ".repeat(4)}${JSON.stringify(parserName)}: Parser;`
+ `${" ".repeat(2)}${toPropertyKey(parserName)}: Parser;`
)
.join("\n")}
- };
- `,
- { parser: "typescript" }
- )
- );
+ };\n
+ `;
+
+ await writeFile(path.join(DIST_DIR, output.file), code);
}
function buildTypes(options) {
diff --git a/scripts/build/config.mjs b/scripts/build/config.mjs
index 640123fc1..848e82880 100644
--- a/scripts/build/config.mjs
+++ b/scripts/build/config.mjs
@@ -86,6 +86,7 @@ const extensions = {
};
const pluginFiles = [
+ "src/plugins/estree.js",
{
input: "src/language-js/parse/babel.js",
replaceModule: [
@@ -355,7 +356,7 @@ const pluginFiles = [
let { input, umdPropertyName, outputBaseName, ...buildOptions } = file;
outputBaseName ??= (
- input.match(/\/(?:parser-|parse\/)(?.*?)\.js$/) ??
+ input.match(/\/(?:parser-|parse\/|plugins\/)(?.*?)\.js$/) ??
input.match(/\/language-(?.*?)\/index\.js$/)
).groups.outputBaseName;
diff --git a/src/plugins/estree.js b/src/plugins/estree.js
new file mode 100644
index 000000000..e8a947835
--- /dev/null
+++ b/src/plugins/estree.js
@@ -0,0 +1,11 @@
+import 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 jsonLanguages from "../language-json/languages.evaluate.js";
+
+export const printers = {
+ estree: estreePrinter,
+ "estree-json": estreeJsonPrinter,
+};
+export const languages = [...jsLanguages, ...jsonLanguages];
+export { default as options } from "../language-js/options.js";
diff --git a/src/standalone.js b/src/standalone.js
index 6233e4053..30161a78f 100644
--- a/src/standalone.js
+++ b/src/standalone.js
@@ -1,9 +1,7 @@
import * as core from "./main/core.js";
import { getSupportInfo as getSupportInfoWithoutPlugins } from "./main/support.js";
-import * as prettierPluginJs from "./language-js/index.js";
-import * as prettierPluginJson from "./language-json/index.js";
-const builtinPlugins = [prettierPluginJs, prettierPluginJson];
+const builtinPlugins = [];
function withPlugins(
fn,
diff --git a/website/static/service-worker.js b/website/static/service-worker.js
index 5965c2085..53ca032c8 100644
--- a/website/static/service-worker.js
+++ b/website/static/service-worker.js
@@ -9,6 +9,7 @@ importScripts(
const plugins = [
...new Set(Object.values(parsersLocation).map((file) => `lib/${file}`)),
+ "lib/plugins/estree.js",
];
toolbox.precache([
diff --git a/website/static/worker.js b/website/static/worker.js
index 1a22f85d0..5fc5091e5 100644
--- a/website/static/worker.js
+++ b/website/static/worker.js
@@ -9,6 +9,7 @@ importScripts("lib/standalone.js");
for (const file of new Set(Object.values(parsersLocation))) {
importScripts(`lib/${file}`);
}
+importScripts("lib/plugins/estree.js");
const docExplorerPlugin = {
parsers: {