Skip to content

Commit

Permalink
Avoid deleting properties on global varNodes [perf]
Browse files Browse the repository at this point in the history
  • Loading branch information
overlookmotel committed Sep 30, 2023
1 parent b355e50 commit 8ddb91f
Showing 1 changed file with 9 additions and 21 deletions.
30 changes: 9 additions & 21 deletions lib/serialize/output.js
Original file line number Diff line number Diff line change
Expand Up @@ -492,13 +492,12 @@ module.exports = {
if (globalVars.length > 0) {
if (this.options.inline) {
const usedGlobalVars = globalVars.filter(({record: globalRecord, node: globalNode}) => {
// Can't use `recordNeedsVar()` because some globals are traced and have dependents
// even when they're not used
if (globalRecord.usageCount === 1) {
replaceIdentifier(globalRecord.varNode, globalNode);
return false;
}
return true;
// Can't use `recordNeedsVar()` because globals don't have dependents
if (globalRecord.usageCount !== 1 || !this.options.inline) return true;

// Only used once - inline
Object.assign(globalRecord.varNode, globalNode);
return false;
});
if (usedGlobalVars.length > 0) localVars.unshift(...usedGlobalVars);
} else {
Expand Down Expand Up @@ -571,8 +570,10 @@ module.exports = {
node = varNode;
} else if (isGlobal) {
// Global - assign to var. Globals which are only used once are inlined later.
// Use a fake `Identifier` node with no `name` property as `varNode`.
// If is inlined later, this removes the need to delete the `name` property again.
this.globalVars.push({record, node});
node = varNode;
node = record.varNode = {type: 'Identifier'};
} else if (this.recordNeedsVar(record)) {
// Used more than once - assign to var.
// Wrap unnamed functions in `(0, fn)` to prevent them getting implicitly named.
Expand Down Expand Up @@ -813,19 +814,6 @@ function isWrappingMethod(node, keyNode) {
return objKeyNode.type === keyType && objKeyNode[valueKey] === keyValue;
}

/**
* Replace an identifier node with inline content by mutating identifier node.
* @param {Object} node - Identifier AST node
* @param {Object} replacementNode - Replacement AST node
* @returns {Object} - Input node (now with all props of replacement node)
*/
function replaceIdentifier(node, replacementNode) {
// Identifiers only have 2 properties - `type` and `name`.
// `node.type` will be overwritten so no need to delete it.
if (!Object.hasOwn(replacementNode, 'name')) delete node.name;
return Object.assign(node, replacementNode);
}

/**
* Replace a node in place.
* @param {Object} node - Babel node
Expand Down

0 comments on commit 8ddb91f

Please sign in to comment.