Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Properly transpile exported classes that shadowed builtins #15294

Merged
merged 1 commit into from Dec 22, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
@@ -0,0 +1,3 @@
export class TypeError {
#message
}
@@ -0,0 +1,4 @@
{
"plugins": ["proposal-class-properties"],
"externalHelpers": false
}
@@ -0,0 +1,12 @@
function _classPrivateFieldInitSpec(obj, privateMap, value) { _checkPrivateRedeclaration(obj, privateMap); privateMap.set(obj, value); }
function _checkPrivateRedeclaration(obj, privateCollection) { if (privateCollection.has(obj)) { throw new TypeError("Cannot initialize the same private elements twice on an object"); } }
var _message = /*#__PURE__*/new WeakMap();
class _TypeError {
constructor() {
_classPrivateFieldInitSpec(this, _message, {
writable: true,
value: void 0
});
}
}
export { _TypeError as TypeError };
@@ -0,0 +1,3 @@
export class TypeError {
#message
}
@@ -0,0 +1,4 @@
{
"plugins": ["proposal-class-properties"],
"externalHelpers": false
}
@@ -0,0 +1,12 @@
function _classPrivateFieldInitSpec(obj, privateMap, value) { _checkPrivateRedeclaration(obj, privateMap); privateMap.set(obj, value); }
function _checkPrivateRedeclaration(obj, privateCollection) { if (privateCollection.has(obj)) { throw new TypeError("Cannot initialize the same private elements twice on an object"); } }
var _message = /*#__PURE__*/new WeakMap();
class _TypeError {
constructor() {
_classPrivateFieldInitSpec(this, _message, {
writable: true,
value: void 0
});
}
}
export { _TypeError as TypeError };
@@ -0,0 +1,3 @@
export class TypeError {
message
}
@@ -0,0 +1,4 @@
{
"plugins": ["proposal-class-properties"],
"externalHelpers": false
}
@@ -0,0 +1,9 @@
function _defineProperty(obj, key, value) { key = _toPropertyKey(key); if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
function _toPropertyKey(arg) { var key = _toPrimitive(arg, "string"); return typeof key === "symbol" ? key : String(key); }
function _toPrimitive(input, hint) { if (typeof input !== "object" || input === null) return input; var prim = input[Symbol.toPrimitive]; if (prim !== undefined) { var res = prim.call(input, hint || "default"); if (typeof res !== "object") return res; throw new TypeError("@@toPrimitive must return a primitive value."); } return (hint === "string" ? String : Number)(input); }
class _TypeError {
constructor() {
_defineProperty(this, "message", void 0);
}
}
export { _TypeError as TypeError };
@@ -0,0 +1,3 @@
export class TypeError {
message
}
@@ -0,0 +1,4 @@
{
"plugins": ["proposal-class-properties"],
"externalHelpers": false
}
@@ -0,0 +1,9 @@
function _defineProperty(obj, key, value) { key = _toPropertyKey(key); if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
function _toPropertyKey(arg) { var key = _toPrimitive(arg, "string"); return typeof key === "symbol" ? key : String(key); }
function _toPrimitive(input, hint) { if (typeof input !== "object" || input === null) return input; var prim = input[Symbol.toPrimitive]; if (prim !== undefined) { var res = prim.call(input, hint || "default"); if (typeof res !== "object") return res; throw new TypeError("@@toPrimitive must return a primitive value."); } return (hint === "string" ? String : Number)(input); }
class _TypeError {
constructor() {
_defineProperty(this, "message", void 0);
}
}
export { _TypeError as TypeError };
17 changes: 13 additions & 4 deletions packages/babel-traverse/src/path/modification.ts
Expand Up @@ -13,6 +13,7 @@ import {
expressionStatement,
isAssignmentExpression,
isCallExpression,
isExportNamedDeclaration,
isExpression,
isIdentifier,
isSequenceExpression,
Expand All @@ -34,12 +35,19 @@ export function insertBefore(

const nodes = this._verifyNodeList(nodes_);

const { parentPath } = this;
const { parentPath, parent } = this;

if (
parentPath.isExpressionStatement() ||
parentPath.isLabeledStatement() ||
parentPath.isExportNamedDeclaration() ||
// https://github.com/babel/babel/issues/15293
// When Babel transforms `export class String { field }`, the class properties plugin will inject the defineProperty
// helper, which depends on the builtins e.g. String, Number, Symbol, etc. To prevent them from being shadowed by local
// exports, the helper injector replaces the named export into `class _String { field }; export { _String as String }`,
// with `parentPath` here changed to the moved ClassDeclaration, causing rare inconsistency between `parent` and `parentPath`.
// Here we retrieve the parent type from the `parent` property. This is a temporary fix and we should revisit when
// helpers should get injected.
isExportNamedDeclaration(parent) ||
(parentPath.isExportDefaultDeclaration() && this.isDeclaration())
) {
return parentPath.insertBefore(nodes);
Expand Down Expand Up @@ -169,11 +177,12 @@ export function insertAfter(

const nodes = this._verifyNodeList(nodes_);

const { parentPath } = this;
const { parentPath, parent } = this;
if (
parentPath.isExpressionStatement() ||
parentPath.isLabeledStatement() ||
parentPath.isExportNamedDeclaration() ||
// see insertBefore
isExportNamedDeclaration(parent) ||
(parentPath.isExportDefaultDeclaration() && this.isDeclaration())
) {
return parentPath.insertAfter(
Expand Down