Skip to content

Commit

Permalink
Fix import { types } from "@babel/core" with native ESM (#14663)
Browse files Browse the repository at this point in the history
* Fix `import { types } from "@babel/core"` with native ESM

* Avoid default `@babel/core` import in tests (not available in ESM)
  • Loading branch information
nicolo-ribaudo committed Jun 18, 2022
1 parent ae462a6 commit a32306d
Show file tree
Hide file tree
Showing 14 changed files with 73 additions and 33 deletions.
49 changes: 49 additions & 0 deletions babel.config.js
Expand Up @@ -220,6 +220,15 @@ module.exports = function (api) {
],
],
},
convertESM && {
test: ["./packages/babel-core/src"].map(normalize),
plugins: [
[
pluginInjectNodeReexportsHints,
{ names: ["types", "tokTypes", "traverse", "template"] },
],
],
},
convertESM && {
test: sources.map(normalize),
exclude: lazyRequireSources.map(normalize),
Expand Down Expand Up @@ -730,3 +739,43 @@ function pluginDynamicESLintVersionCheck({ template }) {
},
};
}

// Inject `0 && exports.foo = 0` hints for the specified exports,
// to help the Node.js CJS-ESM interop. This is only
// needed when compiling ESM re-exports to CJS in `lazy` mode.
function pluginInjectNodeReexportsHints({ types: t, template }, { names }) {
return {
visitor: {
Program: {
exit(path) {
const seen = [];
for (const stmt of path.get("body")) {
if (!stmt.isExpressionStatement()) continue;
const expr = stmt.get("expression");
if (
!expr.isCallExpression() ||
!expr.get("callee").matchesPattern("Object.defineProperty") ||
expr.node.arguments.length !== 3 ||
!expr.get("arguments.0").isIdentifier({ name: "exports" }) ||
!expr.get("arguments.1").isStringLiteral() ||
!names.includes(expr.node.arguments[1].value)
) {
continue;
}

expr
.get("arguments.0")
.replaceWith(template.expression.ast`(0, exports)`);
seen.push(expr.node.arguments[1].value);
}

const assign = seen.reduce(
(rhs, name) => template.expression.ast`exports.${name} = ${rhs}`,
t.numericLiteral(0)
);
path.pushContainer("body", template.statement.ast`0 && (${assign})`);
},
},
},
};
}
4 changes: 3 additions & 1 deletion packages/babel-core/src/index.ts
Expand Up @@ -8,9 +8,11 @@ export { resolvePlugin, resolvePreset } from "./config/files";

export { getEnv } from "./config/helpers/environment";

// NOTE: Lazy re-exports aren't detected by the Node.js CJS-ESM interop.
// These are handled by pluginInjectNodeReexportsHints in our babel.config.js
// so that they can work well.
export * as types from "@babel/types";
export { tokTypes } from "@babel/parser";

export { default as traverse } from "@babel/traverse";
export { default as template } from "@babel/template";

Expand Down
2 changes: 1 addition & 1 deletion packages/babel-core/test/api.js
@@ -1,4 +1,4 @@
import babel from "../lib/index.js";
import * as babel from "../lib/index.js";
import { TraceMap, originalPositionFor } from "@jridgewell/trace-mapping";
import path from "path";
import generator from "@babel/generator";
Expand Down
2 changes: 1 addition & 1 deletion packages/babel-core/test/config-chain.js
Expand Up @@ -2,7 +2,7 @@ import fs from "fs";
import os from "os";
import path from "path";
import { fileURLToPath } from "url";
import babel from "../lib/index.js";
import * as babel from "../lib/index.js";
import rimraf from "rimraf";

import _getTargets from "@babel/helper-compilation-targets";
Expand Down
6 changes: 2 additions & 4 deletions packages/babel-core/test/fixtures/babel-compile-async.mjs
Expand Up @@ -2,10 +2,8 @@

// Usage:
// babel-compile-async.js [filename]
import babel from "../../lib/index.js";
import { transformAsync } from "../../lib/index.js";

(async () => {
process.stdout.write(
JSON.stringify(await babel.transformAsync(""))
);
process.stdout.write(JSON.stringify(await transformAsync("")));
})();
6 changes: 2 additions & 4 deletions packages/babel-core/test/fixtures/babel-compile-sync.mjs
Expand Up @@ -2,8 +2,6 @@

// Usage:
// babel-compile-async.js [filename]
import babel from "../../lib/index.js";
import { transformSync } from "../../lib/index.js";

process.stdout.write(
JSON.stringify(babel.transformSync(""))
);
process.stdout.write(JSON.stringify(transformSync("")));
Expand Up @@ -2,12 +2,12 @@

// Usage:
// babel-load-options-async.js [filename]
import babel from "../../lib/index.js";
import { loadOptionsAsync } from "../../lib/index.js";

const [, , filename, cwd] = process.argv;

(async () => {
process.stdout.write(
JSON.stringify(await babel.loadOptionsAsync({ filename, cwd }))
JSON.stringify(await loadOptionsAsync({ filename, cwd }))
);
})();
5 changes: 2 additions & 3 deletions packages/babel-helper-check-duplicate-nodes/test/index.js
@@ -1,6 +1,5 @@
import _checkDuplicateNodes from "../lib/index.js";
import babel from "@babel/core";
const { parseSync, traverse, types: t } = babel;
import { parseSync, traverse, types as t } from "@babel/core";
const checkDuplicateNodes = _checkDuplicateNodes.default;

describe("checkDuplicateNodes", () => {
Expand Down Expand Up @@ -53,7 +52,7 @@ describe("checkDuplicateNodes", () => {
});
it("should throw when more than one arguments are passed", () => {
expect(() => {
checkDuplicateNodes(babel, {});
checkDuplicateNodes({}, {});
}).toThrow("checkDuplicateNodes accepts only one argument: ast");
});
});
@@ -1,6 +1,5 @@
import { shouldTransform } from "../lib/util.js";
import babel from "@babel/core";
const { parseSync, traverse } = babel;
import { parseSync, traverse } from "@babel/core";

function getPath(input, parserOpts = {}) {
let targetPath;
Expand Down
@@ -1,6 +1,5 @@
import { shouldTransform } from "../lib/util.js";
import babel from "@babel/core";
const { parseSync, traverse } = babel;
import { parseSync, traverse } from "@babel/core";

function getPath(input, parserOpts = {}) {
let targetPath;
Expand Down
@@ -1,4 +1,4 @@
import babel from "@babel/core";
import { transformSync } from "@babel/core";
import proposalDestructuringPrivate from "../lib/index.js";

describe("plugin ordering", () => {
Expand All @@ -12,7 +12,7 @@ describe("plugin ordering", () => {
`;
expect(
() =>
babel.transformSync(source, {
transformSync(source, {
filename: "example.js",
highlightCode: false,
configFile: false,
Expand Down
@@ -1,8 +1,5 @@
import babel from "@babel/core";
import { parseSync, traverse, types as t } from "@babel/core";
import { traversePattern, privateKeyPathIterator } from "../lib/util.js";
const { isObjectProperty, isPrivateName } = babel.types;

const { parseSync, traverse } = babel;

function wrapSourceInClassEnvironment(input) {
const usedPrivateNames = new Set();
Expand Down Expand Up @@ -44,9 +41,9 @@ describe("traversePattern", () => {
);
const keys = [
...traversePattern(patternPath.node, function* (node) {
if (isObjectProperty(node)) {
if (t.isObjectProperty(node)) {
const propertyKey = node.key;
if (isPrivateName(propertyKey)) {
if (t.isPrivateName(propertyKey)) {
yield propertyKey.id.name;
}
}
Expand Down
@@ -1,6 +1,5 @@
import { willPathCastToBoolean } from "../lib/util.js";
import babel from "@babel/core";
const { parseSync, traverse } = babel;
import { parseSync, traverse } from "@babel/core";

function getPath(input, parserOpts) {
let targetPath;
Expand Down
6 changes: 3 additions & 3 deletions packages/babel-plugin-transform-runtime/scripts/build-dist.js
Expand Up @@ -2,7 +2,7 @@ import path from "path";
import fs from "fs";
import { createRequire } from "module";
import helpers from "@babel/helpers";
import babel from "@babel/core";
import { transformFromAstSync, File } from "@babel/core";
import template from "@babel/template";
import t from "@babel/types";
import { fileURLToPath } from "url";
Expand Down Expand Up @@ -217,7 +217,7 @@ function buildHelper(

if (!esm) {
bindings = [];
helpers.ensure(helperName, babel.File);
helpers.ensure(helperName, File);
for (const dep of helpers.getDependencies(helperName)) {
const id = (dependencies[dep] = t.identifier(t.toIdentifier(dep)));
tree.body.push(template.statement.ast`
Expand All @@ -235,7 +235,7 @@ function buildHelper(
);
tree.body.push(...helper.nodes);

return babel.transformFromAstSync(tree, null, {
return transformFromAstSync(tree, null, {
filename: helperFilename,
presets: [["@babel/preset-env", { modules: false }]],
plugins: [
Expand Down

0 comments on commit a32306d

Please sign in to comment.