From e68beeb5bbb4721a3bab306df8cb82f90cf3eb6a Mon Sep 17 00:00:00 2001 From: Eric Eldredge Date: Tue, 10 May 2022 16:42:21 -0400 Subject: [PATCH 01/15] Add tests for chained reexports from a hybrid module (#7980) * Add test for chained reexports from a hybrid module This captures a case where a CJS export is missing. * Add test for reexports as default from a hybrid module This captures a case where packaging fails with `Asset was skipped or not found`. * Use strict equality checks * nit: match similar test terminology Co-authored-by: Niklas Mischkulnig <4586894+mischnic@users.noreply.github.com> --- .../es6/re-export-default-hybrid/a.js | 3 +++ .../es6/re-export-default-hybrid/b.js | 2 ++ .../es6/re-export-default-hybrid/c.js | 2 ++ .../es6/re-export-default-hybrid/d.js | 1 + .../scope-hoisting/es6/re-export-hybrid/a.js | 3 +++ .../scope-hoisting/es6/re-export-hybrid/b.js | 1 + .../scope-hoisting/es6/re-export-hybrid/c.js | 2 ++ .../scope-hoisting/es6/re-export-hybrid/d.js | 1 + .../integration-tests/test/scope-hoisting.js | 22 +++++++++++++++++++ 9 files changed, 37 insertions(+) create mode 100644 packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-default-hybrid/a.js create mode 100644 packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-default-hybrid/b.js create mode 100644 packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-default-hybrid/c.js create mode 100644 packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-default-hybrid/d.js create mode 100644 packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-hybrid/a.js create mode 100644 packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-hybrid/b.js create mode 100644 packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-hybrid/c.js create mode 100644 packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-hybrid/d.js diff --git a/packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-default-hybrid/a.js b/packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-default-hybrid/a.js new file mode 100644 index 00000000000..7f129231c85 --- /dev/null +++ b/packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-default-hybrid/a.js @@ -0,0 +1,3 @@ +import b from './b'; + +output = b.foo + b.bar; diff --git a/packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-default-hybrid/b.js b/packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-default-hybrid/b.js new file mode 100644 index 00000000000..1d134aa51d1 --- /dev/null +++ b/packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-default-hybrid/b.js @@ -0,0 +1,2 @@ +import * as c from './c'; +export default c; diff --git a/packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-default-hybrid/c.js b/packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-default-hybrid/c.js new file mode 100644 index 00000000000..29a35de9403 --- /dev/null +++ b/packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-default-hybrid/c.js @@ -0,0 +1,2 @@ +export foo from './d'; +export const bar = require('./d'); diff --git a/packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-default-hybrid/d.js b/packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-default-hybrid/d.js new file mode 100644 index 00000000000..bd816eaba4c --- /dev/null +++ b/packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-default-hybrid/d.js @@ -0,0 +1 @@ +module.exports = 1; diff --git a/packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-hybrid/a.js b/packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-hybrid/a.js new file mode 100644 index 00000000000..d1d39e3bc64 --- /dev/null +++ b/packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-hybrid/a.js @@ -0,0 +1,3 @@ +import {foo, bar} from './b'; + +output = foo + bar; diff --git a/packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-hybrid/b.js b/packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-hybrid/b.js new file mode 100644 index 00000000000..34a28aa08d0 --- /dev/null +++ b/packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-hybrid/b.js @@ -0,0 +1 @@ +export * from './c'; diff --git a/packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-hybrid/c.js b/packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-hybrid/c.js new file mode 100644 index 00000000000..29a35de9403 --- /dev/null +++ b/packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-hybrid/c.js @@ -0,0 +1,2 @@ +export foo from './d'; +export const bar = require('./d'); diff --git a/packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-hybrid/d.js b/packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-hybrid/d.js new file mode 100644 index 00000000000..bd816eaba4c --- /dev/null +++ b/packages/core/integration-tests/test/integration/scope-hoisting/es6/re-export-hybrid/d.js @@ -0,0 +1 @@ +module.exports = 1; diff --git a/packages/core/integration-tests/test/scope-hoisting.js b/packages/core/integration-tests/test/scope-hoisting.js index 63ddafd760a..2c9508fe405 100644 --- a/packages/core/integration-tests/test/scope-hoisting.js +++ b/packages/core/integration-tests/test/scope-hoisting.js @@ -1997,6 +1997,28 @@ describe('scope hoisting', function () { assert(new output[3]() instanceof output[2]); }); + it('should support chained reexports from hybrid modules', async function () { + let b = await bundle( + path.join( + __dirname, + '/integration/scope-hoisting/es6/re-export-hybrid/a.js', + ), + ); + let output = await run(b); + assert.strictEqual(output, 2); + }); + + it('should support chained reexports as default from hybrid modules', async function () { + let b = await bundle( + path.join( + __dirname, + '/integration/scope-hoisting/es6/re-export-default-hybrid/a.js', + ), + ); + let output = await run(b); + assert.strictEqual(output, 2); + }); + it('support chained namespace reexports of CommonJS', async function () { let b = await bundle( path.join( From 38bb2eefbe74b469afb6d427a3c4cb85a6d6c9ed Mon Sep 17 00:00:00 2001 From: Brian Do Date: Thu, 12 May 2022 16:01:29 -0700 Subject: [PATCH 02/15] More experimental bundler fixes (#7783) * internalization bug * Cleanup * Always add assets to reachable bundles * cleanup * fixed test regressions * add ref edges whenever there are bundle edges * add edge from bundlegroups to bundles wip * * Get inline bundles in bundle group in HTML packager * Traverse each bundle instead of iterating each outbound node * Add edge between root and bundle * use and follow reference edges again * set env whenever we create bundles * Check to add parallel edges from all paths to an asset from a bundle * Always register referenced bundles before pruning when building bundle manifest * Revert "set env whenever we create bundles" This reverts commit 73ad8286f58bdd1e8a036665b439fb65697df67b. * Add test for referenced roots in bundle manifest * Add reused sibling bundles to asyncBundleRootGraph * Add test case for asset that has both an async and sync import * ExperimentalBundler: stop at isolated bundles * ExperimentalBundler: fix step 7 comment * ExperimentalBundler: initialize entry bundles with no ancestors * ExperimentalBundler: accept shared bundles extracted from workers * Remove unused async bundles if needed * Scope-hositing with new bundler: allow less duplication * Uncomment line in getSymbolResolution * Consider sibling availability before removing from ancestorAssets * Uncomment line in getSymbolResolution * Upgrade flow to 0.173.0 (#7809) * Remove reachableBundles * Bump lmdb (#7797) * Replace typeof before DCE (#7788) * Consider sibling availability before removing from ancestorAssets * Consider assets in siblings before duplicating * Remove unrelated change * Don't consider any of parent's async bundles as sibling * Remove unused structure * remove eager bundle reuse and related lending code * Alter tests with mode production and correct assets with logic for splittable bundles * Skip unused dependencies in experimental bundler * Implement getBundleFromBundleRoot * Only add dependencies to CSS module JS, not CSS * Handle multiple assets on dependencies in reachability * ScopeHoistingPackager: Handle different wrapped ancestries in wrapping dfs * skip assets for reachable if isolated or inline fix invariant * Use bundleGroup instead of bundle root for determining needsStableName * Add bundle.mainEntryAsset * fixup! Add bundle.mainEntryAsset Co-authored-by: Gora Kong Co-authored-by: Will Binns-Smith Co-authored-by: Eric Eldredge Co-authored-by: Niklas Mischkulnig <4586894+mischnic@users.noreply.github.com> Co-authored-by: Agnieszka Gawrys Co-authored-by: Devon Govett --- .../experimental/src/ExperimentalBundler.js | 363 ++++++------------ packages/core/integration-tests/test/html.js | 30 ++ .../html-shared-referenced/async.js | 3 + .../html-shared-referenced/async2.js | 0 .../html-shared-referenced/index1.html | 1 + .../html-shared-referenced/index1.js | 1 + .../html-shared-referenced/index2.html | 1 + .../html-shared-referenced/index2.js | 3 + .../html-shared-referenced/package.json | 5 + .../html-shared-referenced/shared.js | 1 + .../html-shared-referenced/yarn.lock | 0 .../html-sync-async-asset/index.html | 1 + .../html-sync-async-asset/index.js | 4 + .../html-sync-async-asset/other.js | 1 + .../integration/html-sync-async-asset/test.js | 1 + .../index.html | 6 + .../core/integration-tests/test/javascript.js | 49 ++- .../integration-tests/test/scope-hoisting.js | 6 +- packages/runtimes/js/src/JSRuntime.js | 5 + packages/transformers/js/native.js | 2 +- .../utils/fs-write-stream-atomic/index.js | 18 +- packages/utils/hash/browser.js | 10 +- 22 files changed, 230 insertions(+), 281 deletions(-) create mode 100644 packages/core/integration-tests/test/integration/html-shared-referenced/async.js create mode 100644 packages/core/integration-tests/test/integration/html-shared-referenced/async2.js create mode 100644 packages/core/integration-tests/test/integration/html-shared-referenced/index1.html create mode 100644 packages/core/integration-tests/test/integration/html-shared-referenced/index1.js create mode 100644 packages/core/integration-tests/test/integration/html-shared-referenced/index2.html create mode 100644 packages/core/integration-tests/test/integration/html-shared-referenced/index2.js create mode 100644 packages/core/integration-tests/test/integration/html-shared-referenced/package.json create mode 100644 packages/core/integration-tests/test/integration/html-shared-referenced/shared.js create mode 100644 packages/core/integration-tests/test/integration/html-shared-referenced/yarn.lock create mode 100644 packages/core/integration-tests/test/integration/html-sync-async-asset/index.html create mode 100644 packages/core/integration-tests/test/integration/html-sync-async-asset/index.js create mode 100644 packages/core/integration-tests/test/integration/html-sync-async-asset/other.js create mode 100644 packages/core/integration-tests/test/integration/html-sync-async-asset/test.js create mode 100644 packages/core/integration-tests/test/integration/scope-hoisting/es6/export-intermediate-wrapped-reexports/index.html diff --git a/packages/bundlers/experimental/src/ExperimentalBundler.js b/packages/bundlers/experimental/src/ExperimentalBundler.js index c4ed607eac7..12d85953d9a 100644 --- a/packages/bundlers/experimental/src/ExperimentalBundler.js +++ b/packages/bundlers/experimental/src/ExperimentalBundler.js @@ -19,7 +19,7 @@ import {ContentGraph, Graph} from '@parcel/graph'; import invariant from 'assert'; import {ALL_EDGE_TYPES} from '@parcel/graph'; import {Bundler} from '@parcel/plugin'; -import {validateSchema, DefaultMap} from '@parcel/utils'; +import {setIntersect, validateSchema, DefaultMap} from '@parcel/utils'; import nullthrows from 'nullthrows'; import {encodeJSONKeyComponent} from '@parcel/diagnostic'; @@ -58,6 +58,7 @@ export type Bundle = {| internalizedAssetIds: Array, bundleBehavior?: ?BundleBehavior, needsStableName: boolean, + mainEntryAsset: ?Asset, size: number, sourceBundles: Array, target: Target, @@ -118,11 +119,12 @@ function decorateLegacyGraph( // Step 1: Create bundle groups, bundles, and shared bundles and add assets to them for (let [bundleNodeId, idealBundle] of idealBundleGraph.nodes) { if (idealBundle === 'root') continue; - let [entryAsset] = [...idealBundle.assets]; + let entryAsset = idealBundle.mainEntryAsset; let bundleGroup; let bundle; if (bundleGroupBundleIds.includes(bundleNodeId)) { + invariant(entryAsset != null); let dependencies = dependencyBundleGraph .getNodeIdsConnectedTo( dependencyBundleGraph.getNodeIdByContentKey(String(bundleNodeId)), @@ -178,6 +180,7 @@ function decorateLegacyGraph( }), ); } else { + invariant(entryAsset != null); bundle = nullthrows( bundleGraph.createBundle({ entryAsset, @@ -194,6 +197,7 @@ function decorateLegacyGraph( bundleGraph.addAssetToBundle(asset, bundle); } } + // Step 2: Internalize dependencies for bundles for (let [, idealBundle] of idealBundleGraph.nodes) { if (idealBundle === 'root') continue; @@ -212,18 +216,31 @@ function decorateLegacyGraph( } } } + // Step 3: Add bundles to their bundle groups - for (let [bundleId, bundleGroup] of entryBundleToBundleGroup) { - let outboundNodeIds = idealBundleGraph.getNodeIdsConnectedFrom(bundleId); + idealBundleGraph.traverse((nodeId, _, actions) => { + let node = idealBundleGraph.getNode(nodeId); + if (node === 'root') { + return; + } + actions.skipChildren(); + + let outboundNodeIds = idealBundleGraph.getNodeIdsConnectedFrom(nodeId); + let entryBundle = nullthrows(idealBundleGraph.getNode(nodeId)); + invariant(entryBundle !== 'root'); + let legacyEntryBundle = nullthrows( + idealBundleToLegacyBundle.get(entryBundle), + ); + for (let id of outboundNodeIds) { let siblingBundle = nullthrows(idealBundleGraph.getNode(id)); invariant(siblingBundle !== 'root'); let legacySiblingBundle = nullthrows( idealBundleToLegacyBundle.get(siblingBundle), ); - bundleGraph.addBundleToBundleGroup(legacySiblingBundle, bundleGroup); + bundleGraph.createBundleReference(legacyEntryBundle, legacySiblingBundle); } - } + }); // Step 4: Add references to all bundles for (let [asset, references] of idealGraph.assetReference) { @@ -263,12 +280,6 @@ function createIdealGraph( Array<[Dependency, Bundle]>, > = new DefaultMap(() => []); - // bundleRoot to all bundleRoot descendants - let reachableBundles: DefaultMap< - BundleRoot, - Set, - > = new DefaultMap(() => new Set()); - let bundleGraph: Graph = new Graph(); let stack: Array<[BundleRoot, NodeId]> = []; @@ -411,20 +422,6 @@ function createIdealGraph( ), dependencyPriorityEdges[dependency.priority], ); - - // Walk up the stack until we hit a different asset type - // and mark each bundle as reachable from every parent bundle - for (let i = stack.length - 1; i >= 0; i--) { - let [stackAsset] = stack[i]; - if ( - stackAsset.type !== childAsset.type || - stackAsset.env.context !== childAsset.env.context || - stackAsset.env.isIsolated() - ) { - break; - } - reachableBundles.get(stackAsset).add(childAsset); - } continue; } if ( @@ -432,9 +429,7 @@ function createIdealGraph( dependency.priority === 'parallel' || childAsset.bundleBehavior === 'inline' ) { - let [parentBundleRoot, bundleGroupNodeId] = nullthrows( - stack[stack.length - 1], - ); + let [, bundleGroupNodeId] = nullthrows(stack[stack.length - 1]); let bundleGroup = nullthrows( bundleGraph.getNode(bundleGroupNodeId), ); @@ -467,12 +462,6 @@ function createIdealGraph( let bundle; if (bundleId == null) { - let parentBundleId = nullthrows(bundles.get(parentBundleRoot.id)); - let parentBundle = nullthrows( - bundleGraph.getNode(parentBundleId), - ); - invariant(parentBundle !== 'root'); - // Create a new bundle if none of the same type exists already. bundle = createBundle({ // We either have an entry asset or a unique key. @@ -489,7 +478,7 @@ function createIdealGraph( (dependency.priority === 'parallel' && !dependency.needsStableName) ? false - : parentBundle.needsStableName, + : bundleGroup.needsStableName, }); bundleId = bundleGraph.addNode(bundle); } else { @@ -566,22 +555,18 @@ function createIdealGraph( let reachableRoots: ContentGraph = new ContentGraph(); for (let [root] of bundleRoots) { let rootNodeId = reachableRoots.addNodeByContentKeyIfNeeded(root.id, root); - assetGraph.traverse((node, isAsync, actions) => { + assetGraph.traverse((node, _, actions) => { if (node.value === root) { return; } - if (node.type === 'dependency') { let dependency = node.value; if (dependencyBundleGraph.hasContentKey(dependency.id)) { - if ( - dependency.priority === 'lazy' || - dependency.priority === 'parallel' - ) { + if (dependency.priority !== 'sync') { let assets = assetGraph.getDependencyAssets(dependency); if (assets.length === 0) { - return node; + return; } invariant(assets.length === 1); @@ -601,16 +586,23 @@ function createIdealGraph( ); } } - return; + } + + if (dependency.priority !== 'sync') { + actions.skipChildren(); } return; } - - if (bundleRoots.has(node.value)) { + //asset node type + let asset = node.value; + if ( + asset.bundleBehavior === 'isolated' || + asset.bundleBehavior === 'inline' || + root.type !== asset.type + ) { actions.skipChildren(); return; } - let nodeId = reachableRoots.addNodeByContentKeyIfNeeded( node.value.id, node.value, @@ -621,99 +613,75 @@ function createIdealGraph( // Maps a given bundleRoot to the assets reachable from it, // and the bundleRoots reachable from each of these assets - let ancestorAssets: Map< - BundleRoot, - Map | null>, - > = new Map(); - - // Reference count of each asset available within a given bundleRoot's bundle group - let assetRefsInBundleGroup: DefaultMap< - BundleRoot, - DefaultMap, - > = new DefaultMap(() => new DefaultMap(() => 0)); + let asyncAncestorAssets: Map> = new Map(); // Step 4: Determine assets that should be duplicated by computing asset availability in each bundle group + for (let entry of entries.keys()) { + // Initialize an empty set of ancestors available to entries + asyncAncestorAssets.set(entry, new Set()); + } + + // Visit nodes in a topological order, visiting parent nodes before child nodes. + // This allows us to construct an understanding of which assets will already be + // loaded and available when a bundle runs, by pushing available assets downwards and + // computing the intersection of assets available through all possible paths to a bundle. for (let nodeId of asyncBundleRootGraph.topoSort()) { const bundleRoot = asyncBundleRootGraph.getNode(nodeId); if (bundleRoot === 'root') continue; invariant(bundleRoot != null); - let ancestors = ancestorAssets.get(bundleRoot); - - // First consider bundle group asset availability, processing only - // non-isolated bundles within that bundle group let bundleGroupId = nullthrows(bundleRoots.get(bundleRoot))[1]; - // Map of assets in the bundle group to their refcounts - let assetRefs = assetRefsInBundleGroup.get(bundleRoot); - - for (let bundleIdInGroup of [ - bundleGroupId, - ...bundleGraph.getNodeIdsConnectedFrom(bundleGroupId), - ]) { - let bundleInGroup = nullthrows(bundleGraph.getNode(bundleIdInGroup)); - invariant(bundleInGroup !== 'root'); - if ( - bundleInGroup.bundleBehavior === 'isolated' || - bundleInGroup.bundleBehavior === 'inline' - ) { - continue; - } - let [bundleRoot] = [...bundleInGroup.assets]; - // Assets directly connected to current bundleRoot - let assetsFromBundleRoot = reachableRoots - .getNodeIdsConnectedFrom( - reachableRoots.getNodeIdByContentKey(bundleRoot.id), - ) - .map(id => nullthrows(reachableRoots.getNode(id))); - for (let asset of assetsFromBundleRoot) { - assetRefs.set(asset, assetRefs.get(asset) + 1); - } - } + let available; + if (bundleRoot.bundleBehavior === 'isolated') { + available = new Set(); + } else { + available = new Set(asyncAncestorAssets.get(bundleRoot)); + for (let bundleIdInGroup of [ + bundleGroupId, + ...bundleGraph.getNodeIdsConnectedFrom(bundleGroupId), + ]) { + let bundleInGroup = nullthrows(bundleGraph.getNode(bundleIdInGroup)); + invariant(bundleInGroup !== 'root'); + if ( + bundleInGroup.bundleBehavior === 'isolated' || + bundleInGroup.bundleBehavior === 'inline' + ) { + continue; + } - // Enumerate bundleRoots connected to the node (parent), taking the intersection - // between the assets synchronously loaded by the parent, and those loaded by the child. - let bundleGroupAssets = new Set(assetRefs.keys()); + for (let bundleRoot of bundleInGroup.assets) { + // Assets directly connected to current bundleRoot + let assetsFromBundleRoot = reachableRoots + .getNodeIdsConnectedFrom( + reachableRoots.getNodeIdByContentKey(bundleRoot.id), + ) + .map(id => nullthrows(reachableRoots.getNode(id))); - let combined = ancestors - ? new Map([...bundleGroupAssets, ...ancestors.keys()].map(a => [a, null])) - : new Map([...bundleGroupAssets].map(a => [a, null])); + for (let asset of [bundleRoot, ...assetsFromBundleRoot]) { + available.add(asset); + } + } + } + } let children = asyncBundleRootGraph.getNodeIdsConnectedFrom(nodeId); - + // Group assets available across our children by the child. This will be used + // to determine borrowers if needed below. for (let childId of children) { let child = asyncBundleRootGraph.getNode(childId); invariant(child !== 'root' && child != null); - const availableAssets = ancestorAssets.get(child); - - if (availableAssets != null) { - ancestryIntersect(availableAssets, combined); - } else { - ancestorAssets.set(child, combined); + if ( + child.bundleBehavior === 'isolated' || + child.bundleBehavior === 'inline' + ) { + continue; } - } - - let siblingAncestors = ancestors - ? ancestryUnion(new Set(ancestors.keys()), assetRefs, bundleRoot) - : new Map([...bundleGroupAssets].map(a => [a, [bundleRoot]])); - - for (let bundleIdInGroup of bundleGraph.getNodeIdsConnectedFrom( - bundleGroupId, - )) { - let bundleInGroup = bundleGraph.getNode(bundleIdInGroup); - invariant( - bundleInGroup != null && - bundleInGroup !== 'root' && - bundleInGroup.assets != null, - ); - let [bundleRoot] = [...bundleInGroup.assets]; - - const availableAssets = ancestorAssets.get(bundleRoot); - - if (availableAssets != null) { - ancestryIntersect(availableAssets, siblingAncestors); + const childAvailableAssets = asyncAncestorAssets.get(child); + if (childAvailableAssets != null) { + setIntersect(childAvailableAssets, available); } else { - ancestorAssets.set(bundleRoot, siblingAncestors); + asyncAncestorAssets.set(child, new Set(available)); } } } @@ -730,96 +698,24 @@ function createIdealGraph( // Filter out bundles from this asset's reachable array if // bundle does not contain the asset in its ancestry - // or if any of the bundles in the ancestry have a refcount of <= 1 for that asset, - // meaning it may not be deduplicated. Otherwise, decrement all references in - // the ancestry and keep it - reachable = reachable.filter(b => { - let ancestry = ancestorAssets.get(b)?.get(asset); - if (ancestry === undefined) { - // No reachable bundles from this asset - return true; - } else if (ancestry === null) { - // Asset is reachable from this bundle - return false; - } else { - // If every bundle in its ancestry has more than 1 reference to the asset - if ( - ancestry.every( - bundleId => assetRefsInBundleGroup.get(bundleId).get(asset) > 1, - ) - ) { - for (let bundleRoot of ancestry) { - assetRefsInBundleGroup - .get(bundleRoot) - .set( - asset, - assetRefsInBundleGroup.get(bundleRoot).get(asset) - 1, - ); - } - return false; - } - return true; - } - }); - - let rootBundleTuple = bundleRoots.get(asset); - if (rootBundleTuple != null) { - let rootBundle = nullthrows(bundleGraph.getNode(rootBundleTuple[0])); - invariant(rootBundle !== 'root'); - - if (!rootBundle.env.isIsolated()) { - if (!bundles.has(asset.id)) { - bundles.set(asset.id, rootBundleTuple[0]); - } - - for (let reachableAsset of reachable) { - if (reachableAsset !== asset) { - bundleGraph.addEdge( - nullthrows(bundleRoots.get(reachableAsset))[1], - rootBundleTuple[0], - ); - } - } - - let willInternalizeRoots = asyncBundleRootGraph - .getNodeIdsConnectedTo( - asyncBundleRootGraph.getNodeIdByContentKey(asset.id), - ) - .map(id => nullthrows(asyncBundleRootGraph.getNode(id))) - .filter(bundleRoot => { - if (bundleRoot === 'root') { - return false; - } + reachable = reachable.filter(b => !asyncAncestorAssets.get(b)?.has(asset)); - return ( - reachableRoots.hasEdge( - reachableRoots.getNodeIdByContentKey(bundleRoot.id), - reachableRoots.getNodeIdByContentKey(asset.id), - ) || ancestorAssets.get(bundleRoot)?.has(asset) - ); - }) - .map(bundleRoot => { - // For Flow - invariant(bundleRoot !== 'root'); - return bundleRoot; - }); - - for (let bundleRoot of willInternalizeRoots) { - if (bundleRoot !== asset) { - let bundle = nullthrows( - bundleGraph.getNode(nullthrows(bundles.get(bundleRoot.id))), - ); - invariant(bundle !== 'root'); - bundle.internalizedAssetIds.push(asset.id); - } - } - } - } else if (reachable.length > 0) { + if (reachable.length > 0) { let reachableEntries = reachable.filter( - a => entries.has(a) || !a.isBundleSplittable, + a => + entries.has(a) || + !a.isBundleSplittable || + getBundleFromBundleRoot(a).needsStableName || + getBundleFromBundleRoot(a).bundleBehavior === 'inline' || + getBundleFromBundleRoot(a).bundleBehavior === 'isolated', ); reachable = reachable.filter( - a => !entries.has(a) && a.isBundleSplittable, + a => + !entries.has(a) && + a.isBundleSplittable && + !getBundleFromBundleRoot(a).needsStableName && + getBundleFromBundleRoot(a).bundleBehavior !== 'inline' && + getBundleFromBundleRoot(a).bundleBehavior !== 'isolated', ); // Add assets to non-splittable bundles. @@ -872,8 +768,8 @@ function createIdealGraph( } } - // Step 7: Merge any sibling bundles required by entry bundles back into the entry bundle. - // Entry bundles must be predictable, so cannot have unpredictable siblings. + // Step 7: Merge any shared bundles under the minimum bundle size back into + // their source bundles, and remove the bundle. for (let [bundleNodeId, bundle] of bundleGraph.nodes) { if (bundle === 'root') continue; if (bundle.sourceBundles.length > 0 && bundle.size < config.minBundleSize) { @@ -882,6 +778,14 @@ function createIdealGraph( } } + function getBundleFromBundleRoot(bundleRoot: BundleRoot): Bundle { + let bundle = bundleGraph.getNode( + nullthrows(bundleRoots.get(bundleRoot))[0], + ); + invariant(bundle !== 'root' && bundle != null); + return bundle; + } + return { bundleGraph, dependencyBundleGraph, @@ -925,6 +829,7 @@ function createBundle(opts: {| uniqueKey: opts.uniqueKey, assets: new Set(), internalizedAssetIds: [], + mainEntryAsset: null, size: 0, sourceBundles: [], target: opts.target, @@ -940,6 +845,7 @@ function createBundle(opts: {| uniqueKey: opts.uniqueKey, assets: new Set([asset]), internalizedAssetIds: [], + mainEntryAsset: asset, size: asset.stats.size, sourceBundles: [], target: opts.target, @@ -1002,43 +908,6 @@ async function loadBundlerConfig( }; } -function ancestryUnion( - ancestors: Set, - assetRefs: Map, - bundleRoot: BundleRoot, -): Map | null> { - let map = new Map(); - for (let a of ancestors) { - map.set(a, null); - } - for (let [asset, refCount] of assetRefs) { - if (!ancestors.has(asset) && refCount > 1) { - map.set(asset, [bundleRoot]); - } - } - return map; -} - -function ancestryIntersect( - currentMap: Map | null>, - map: Map | null>, -): void { - for (let [bundleRoot, currentAssets] of currentMap) { - if (map.has(bundleRoot)) { - let assets = map.get(bundleRoot); - if (assets) { - if (currentAssets) { - currentAssets.push(...assets); - } else { - currentMap.set(bundleRoot, [...assets]); - } - } - } else { - currentMap.delete(bundleRoot); - } - } -} - function getReachableBundleRoots(asset, graph): Array { return graph .getNodeIdsConnectedTo(graph.getNodeIdByContentKey(asset.id)) diff --git a/packages/core/integration-tests/test/html.js b/packages/core/integration-tests/test/html.js index a215957a03c..b8b20d51191 100644 --- a/packages/core/integration-tests/test/html.js +++ b/packages/core/integration-tests/test/html.js @@ -2841,4 +2841,34 @@ describe('html', function () { }, ); }); + + it('extracts shared bundles that load referenced bundle roots across entries', async () => { + let b = await bundle( + ['index1.html', 'index2.html'].map(entry => + path.join(__dirname, 'integration/html-shared-referenced', entry), + ), + { + mode: 'production', + defaultTargetOptions: { + shouldOptimize: false, + }, + }, + ); + + await run(b); + }); + + it('should not skip bundleRoots if an asset is both async required and static required', async function () { + let b = await bundle( + path.join(__dirname, 'integration/html-sync-async-asset/index.html'), + { + mode: 'production', + defaultTargetOptions: { + shouldOptimize: false, + }, + }, + ); + + await run(b, {output: null}, {require: false}); + }); }); diff --git a/packages/core/integration-tests/test/integration/html-shared-referenced/async.js b/packages/core/integration-tests/test/integration/html-shared-referenced/async.js new file mode 100644 index 00000000000..ad07c1e9102 --- /dev/null +++ b/packages/core/integration-tests/test/integration/html-shared-referenced/async.js @@ -0,0 +1,3 @@ +import './async2.js'; + +import('./async2.js'); diff --git a/packages/core/integration-tests/test/integration/html-shared-referenced/async2.js b/packages/core/integration-tests/test/integration/html-shared-referenced/async2.js new file mode 100644 index 00000000000..e69de29bb2d diff --git a/packages/core/integration-tests/test/integration/html-shared-referenced/index1.html b/packages/core/integration-tests/test/integration/html-shared-referenced/index1.html new file mode 100644 index 00000000000..befa6f91239 --- /dev/null +++ b/packages/core/integration-tests/test/integration/html-shared-referenced/index1.html @@ -0,0 +1 @@ + diff --git a/packages/core/integration-tests/test/integration/html-shared-referenced/index1.js b/packages/core/integration-tests/test/integration/html-shared-referenced/index1.js new file mode 100644 index 00000000000..c21c06aca8a --- /dev/null +++ b/packages/core/integration-tests/test/integration/html-shared-referenced/index1.js @@ -0,0 +1 @@ +import './shared'; diff --git a/packages/core/integration-tests/test/integration/html-shared-referenced/index2.html b/packages/core/integration-tests/test/integration/html-shared-referenced/index2.html new file mode 100644 index 00000000000..edbd81997e9 --- /dev/null +++ b/packages/core/integration-tests/test/integration/html-shared-referenced/index2.html @@ -0,0 +1 @@ + diff --git a/packages/core/integration-tests/test/integration/html-shared-referenced/index2.js b/packages/core/integration-tests/test/integration/html-shared-referenced/index2.js new file mode 100644 index 00000000000..04c9991d158 --- /dev/null +++ b/packages/core/integration-tests/test/integration/html-shared-referenced/index2.js @@ -0,0 +1,3 @@ +import './async.js'; +import './shared.js'; + diff --git a/packages/core/integration-tests/test/integration/html-shared-referenced/package.json b/packages/core/integration-tests/test/integration/html-shared-referenced/package.json new file mode 100644 index 00000000000..c5f216e03fd --- /dev/null +++ b/packages/core/integration-tests/test/integration/html-shared-referenced/package.json @@ -0,0 +1,5 @@ +{ + "@parcel/bundler-default": { + "minBundleSize": 0 + } +} diff --git a/packages/core/integration-tests/test/integration/html-shared-referenced/shared.js b/packages/core/integration-tests/test/integration/html-shared-referenced/shared.js new file mode 100644 index 00000000000..6c111b7bca1 --- /dev/null +++ b/packages/core/integration-tests/test/integration/html-shared-referenced/shared.js @@ -0,0 +1 @@ +import('./async.js'); diff --git a/packages/core/integration-tests/test/integration/html-shared-referenced/yarn.lock b/packages/core/integration-tests/test/integration/html-shared-referenced/yarn.lock new file mode 100644 index 00000000000..e69de29bb2d diff --git a/packages/core/integration-tests/test/integration/html-sync-async-asset/index.html b/packages/core/integration-tests/test/integration/html-sync-async-asset/index.html new file mode 100644 index 00000000000..8ef9a70b216 --- /dev/null +++ b/packages/core/integration-tests/test/integration/html-sync-async-asset/index.html @@ -0,0 +1 @@ + diff --git a/packages/core/integration-tests/test/integration/html-sync-async-asset/index.js b/packages/core/integration-tests/test/integration/html-sync-async-asset/index.js new file mode 100644 index 00000000000..afd241a43f8 --- /dev/null +++ b/packages/core/integration-tests/test/integration/html-sync-async-asset/index.js @@ -0,0 +1,4 @@ +import t from "./test.js"; + +import("./other.js") + .then((v) => v.default) diff --git a/packages/core/integration-tests/test/integration/html-sync-async-asset/other.js b/packages/core/integration-tests/test/integration/html-sync-async-asset/other.js new file mode 100644 index 00000000000..6be91ea6cc7 --- /dev/null +++ b/packages/core/integration-tests/test/integration/html-sync-async-asset/other.js @@ -0,0 +1 @@ +export default import("./test.js"); diff --git a/packages/core/integration-tests/test/integration/html-sync-async-asset/test.js b/packages/core/integration-tests/test/integration/html-sync-async-asset/test.js new file mode 100644 index 00000000000..58c57157d36 --- /dev/null +++ b/packages/core/integration-tests/test/integration/html-sync-async-asset/test.js @@ -0,0 +1 @@ +export default "test"; diff --git a/packages/core/integration-tests/test/integration/scope-hoisting/es6/export-intermediate-wrapped-reexports/index.html b/packages/core/integration-tests/test/integration/scope-hoisting/es6/export-intermediate-wrapped-reexports/index.html new file mode 100644 index 00000000000..233f9c37633 --- /dev/null +++ b/packages/core/integration-tests/test/integration/scope-hoisting/es6/export-intermediate-wrapped-reexports/index.html @@ -0,0 +1,6 @@ + + + + + + diff --git a/packages/core/integration-tests/test/javascript.js b/packages/core/integration-tests/test/javascript.js index 2ca75a87198..592a4d4d008 100644 --- a/packages/core/integration-tests/test/javascript.js +++ b/packages/core/integration-tests/test/javascript.js @@ -1036,31 +1036,42 @@ describe('javascript', function () { let b = await bundle( path.join(__dirname, '/integration/workers-module/index.js'), { + mode: 'production', defaultTargetOptions: { + shouldOptimize: false, shouldScopeHoist: true, }, }, ); - assertBundles(b, [ { - assets: ['dedicated-worker.js', 'index.js'], + assets: ['dedicated-worker.js'], }, { name: 'index.js', - assets: ['index.js', 'bundle-url.js', 'get-worker-url.js'], + assets: [ + 'index.js', + 'bundle-url.js', + 'get-worker-url.js', + 'bundle-manifest.js', + ], }, { - assets: ['shared-worker.js', 'index.js'], + assets: ['shared-worker.js'], + }, + { + assets: ['index.js'], }, ]); let dedicated, shared; b.traverseBundles((bundle, ctx, traversal) => { - if (bundle.getMainEntry().filePath.endsWith('shared-worker.js')) { + let mainEntry = bundle.getMainEntry(); + if (mainEntry && mainEntry.filePath.endsWith('shared-worker.js')) { shared = bundle; } else if ( - bundle.getMainEntry().filePath.endsWith('dedicated-worker.js') + mainEntry && + mainEntry.filePath.endsWith('dedicated-worker.js') ) { dedicated = bundle; } @@ -1086,7 +1097,9 @@ describe('javascript', function () { let b = await bundle( path.join(__dirname, '/integration/workers-module/index.js'), { + mode: 'production', defaultTargetOptions: { + shouldOptimize: false, shouldScopeHoist, engines: { browsers: '>= 0.25%', @@ -1097,31 +1110,36 @@ describe('javascript', function () { assertBundles(b, [ { - assets: [ - 'dedicated-worker.js', - !shouldScopeHoist && 'esmodule-helpers.js', - 'index.js', - ].filter(Boolean), + assets: ['dedicated-worker.js'], }, { name: 'index.js', - assets: ['index.js', 'bundle-url.js', 'get-worker-url.js'], + assets: [ + 'index.js', + 'bundle-url.js', + 'get-worker-url.js', + 'bundle-manifest.js', + ], }, { assets: [ !shouldScopeHoist && 'esmodule-helpers.js', - 'shared-worker.js', 'index.js', ].filter(Boolean), }, + { + assets: ['shared-worker.js'], + }, ]); let dedicated, shared; b.traverseBundles((bundle, ctx, traversal) => { - if (bundle.getMainEntry().filePath.endsWith('shared-worker.js')) { + let mainEntry = bundle.getMainEntry(); + if (mainEntry && mainEntry.filePath.endsWith('shared-worker.js')) { shared = bundle; } else if ( - bundle.getMainEntry().filePath.endsWith('dedicated-worker.js') + mainEntry && + mainEntry.filePath.endsWith('dedicated-worker.js') ) { dedicated = bundle; } @@ -1977,6 +1995,7 @@ describe('javascript', function () { }); it('should contain duplicate assets in workers when in development', async () => { + if (process.env.PARCEL_TEST_EXPERIMENTAL_BUNDLER) return; let b = await bundle( path.join(__dirname, '/integration/worker-shared/index.js'), {mode: 'development'}, diff --git a/packages/core/integration-tests/test/scope-hoisting.js b/packages/core/integration-tests/test/scope-hoisting.js index 2c9508fe405..5ff9f13fb24 100644 --- a/packages/core/integration-tests/test/scope-hoisting.js +++ b/packages/core/integration-tests/test/scope-hoisting.js @@ -5063,7 +5063,11 @@ describe('scope hoisting', function () { ], }, {assets: ['dep.js']}, - {assets: ['async-has-dep.js', 'dep.js', 'get-dep.js']}, + { + assets: process.env.PARCEL_TEST_EXPERIMENTAL_BUNDLER + ? ['async-has-dep.js'] + : ['async-has-dep.js', 'dep.js', 'get-dep.js'], + }, {assets: ['get-dep.js']}, ]); diff --git a/packages/runtimes/js/src/JSRuntime.js b/packages/runtimes/js/src/JSRuntime.js index f7751dbe971..a05f1cf7a13 100644 --- a/packages/runtimes/js/src/JSRuntime.js +++ b/packages/runtimes/js/src/JSRuntime.js @@ -552,6 +552,11 @@ function getRegisterCode( idToName[bundle.publicId] = path.basename(nullthrows(bundle.name)); if (bundle !== entryBundle && isNewContext(bundle, bundleGraph)) { + for (let referenced of bundleGraph.getReferencedBundles(bundle)) { + idToName[referenced.publicId] = path.basename( + nullthrows(referenced.name), + ); + } // New contexts have their own manifests, so there's no need to continue. actions.skipChildren(); } diff --git a/packages/transformers/js/native.js b/packages/transformers/js/native.js index ad423318745..ce1d82238c9 100644 --- a/packages/transformers/js/native.js +++ b/packages/transformers/js/native.js @@ -18,7 +18,7 @@ if (process.env.PARCEL_BUILD_ENV === 'production') { } else if (process.env.PARCEL_SWC_WASM) { const {transform} = require('./wasm/dist-node/parcel_js_swc_wasm.js'); - module.exports.transform = function(config) { + module.exports.transform = function (config) { let result = transform(config); return { ...result, diff --git a/packages/utils/fs-write-stream-atomic/index.js b/packages/utils/fs-write-stream-atomic/index.js index eec056fb25f..849ea300260 100644 --- a/packages/utils/fs-write-stream-atomic/index.js +++ b/packages/utils/fs-write-stream-atomic/index.js @@ -64,25 +64,25 @@ function WriteStreamAtomic(path, options) { // data has been written to our target stream. So we suppress // finish from being emitted here, and only emit it after our // target stream is closed and we've moved everything around. -WriteStreamAtomic.prototype.emit = function(event) { +WriteStreamAtomic.prototype.emit = function (event) { if (event === 'finish') return this.__atomicStream.end(); return Writable.prototype.emit.apply(this, arguments); }; -WriteStreamAtomic.prototype._write = function(buffer, encoding, cb) { +WriteStreamAtomic.prototype._write = function (buffer, encoding, cb) { var flushed = this.__atomicStream.write(buffer, encoding); if (flushed) return cb(); this.__atomicStream.once('drain', cb); }; function handleOpen(writeStream) { - return function(fd) { + return function (fd) { writeStream.emit('open', fd); }; } function handleClose(writeStream) { - return function() { + return function () { if (writeStream.__atomicClosed) return; writeStream.__atomicClosed = true; if (writeStream.__atomicChown) { @@ -127,13 +127,13 @@ function handleClose(writeStream) { var targetFileHash = crypto.createHash('sha512'); fs.createReadStream(writeStream.__atomicTmp) - .on('data', function(data, enc) { + .on('data', function (data, enc) { tmpFileHash.update(data, enc); }) .on('error', fileHashError) .on('end', fileHashComplete); fs.createReadStream(writeStream.__atomicTarget) - .on('data', function(data, enc) { + .on('data', function (data, enc) { targetFileHash.update(data, enc); }) .on('error', fileHashError) @@ -157,7 +157,7 @@ function handleClose(writeStream) { } function cleanup(err) { - fs.unlink(writeStream.__atomicTmp, function() { + fs.unlink(writeStream.__atomicTmp, function () { if (err) { writeStream.emit('error', err); writeStream.emit('close'); @@ -175,14 +175,14 @@ function handleClose(writeStream) { // Delay the close to provide the same temporal separation a physical // file operation would have– that is, the close event is emitted only // after the async close operation completes. - setImmediate(function() { + setImmediate(function () { writeStream.emit('close'); }); } } function handleError(writeStream) { - return function(er) { + return function (er) { cleanupSync(); writeStream.emit('error', er); writeStream.__atomicClosed = true; diff --git a/packages/utils/hash/browser.js b/packages/utils/hash/browser.js index d5f4dbc8d27..7f75a142370 100644 --- a/packages/utils/hash/browser.js +++ b/packages/utils/hash/browser.js @@ -49,13 +49,7 @@ function concatUint8Arrays(arrays) { function toHex(arr) { let dataView = new DataView(arr.buffer); return ( - dataView - .getUint32(0, true) - .toString(16) - .padStart(8, '0') + - dataView - .getUint32(4, true) - .toString(16) - .padStart(8, '0') + dataView.getUint32(0, true).toString(16).padStart(8, '0') + + dataView.getUint32(4, true).toString(16).padStart(8, '0') ); } From fe587664039c0ead3c1be7aacf462cd63b58238c Mon Sep 17 00:00:00 2001 From: Rasmus Melchior Jacobsen Date: Fri, 13 May 2022 09:39:51 +0200 Subject: [PATCH 03/15] Module declarations must use "export declare" instead of "declare export". (#8085) --- .../test/integration/ts-types/main/expected.d.ts | 3 +++ .../test/integration/ts-types/main/index.ts | 6 ++++++ packages/transformers/typescript-types/src/shake.js | 10 +++++++++- yarn.lock | 6 +++--- 4 files changed, 21 insertions(+), 4 deletions(-) diff --git a/packages/core/integration-tests/test/integration/ts-types/main/expected.d.ts b/packages/core/integration-tests/test/integration/ts-types/main/expected.d.ts index ad621f4099b..f1f1655c63e 100644 --- a/packages/core/integration-tests/test/integration/ts-types/main/expected.d.ts +++ b/packages/core/integration-tests/test/integration/ts-types/main/expected.d.ts @@ -11,5 +11,8 @@ export default function test(params: Params): number; export function foo(): number; export var x: number; export var hi: number; +export declare module mod { + function bar(): number; +} //# sourceMappingURL=types.d.ts.map diff --git a/packages/core/integration-tests/test/integration/ts-types/main/index.ts b/packages/core/integration-tests/test/integration/ts-types/main/index.ts index 62ea94b0aaf..bd198d08f2a 100644 --- a/packages/core/integration-tests/test/integration/ts-types/main/index.ts +++ b/packages/core/integration-tests/test/integration/ts-types/main/index.ts @@ -23,3 +23,9 @@ export function foo() { var x = 2; var p = x + 2, q = 3; export {p as hi, x}; + +export module mod { + export function bar() { + return 2; + } +} \ No newline at end of file diff --git a/packages/transformers/typescript-types/src/shake.js b/packages/transformers/typescript-types/src/shake.js index 6e54366ffb2..571b1158b97 100644 --- a/packages/transformers/typescript-types/src/shake.js +++ b/packages/transformers/typescript-types/src/shake.js @@ -36,7 +36,15 @@ export function shake( // Deeply nested module declarations are assumed to be module augmentations and left alone. if (moduleStack.length >= 1) { // Since we are hoisting them to the top-level scope, we need to add a "declare" keyword to make them ambient. - node.modifiers.unshift(ts.createModifier(ts.SyntaxKind.DeclareKeyword)); + // we also want the declare keyword to come after the export keyword to guarantee a valid typings file. + node.modifiers ??= []; + const index = + node.modifiers[0]?.kind === ts.SyntaxKind.ExportKeyword ? 1 : 0; + node.modifiers.splice( + index, + 0, + ts.createModifier(ts.SyntaxKind.DeclareKeyword), + ); return node; } diff --git a/yarn.lock b/yarn.lock index e599f7c558e..8aad2f35233 100644 --- a/yarn.lock +++ b/yarn.lock @@ -12708,9 +12708,9 @@ typedarray@^0.0.6: integrity sha1-hnrHTjhkGHsdPUfZlqeOxciDB3c= typescript@>=3.0.0: - version "4.5.3" - resolved "https://registry.yarnpkg.com/typescript/-/typescript-4.5.3.tgz#afaa858e68c7103317d89eb90c5d8906268d353c" - integrity sha512-eVYaEHALSt+s9LbvgEv4Ef+Tdq7hBiIZgii12xXJnukryt3pMgJf6aKhoCZ3FWQsu6sydEnkg11fYXLzhLBjeQ== + version "4.6.4" + resolved "https://registry.yarnpkg.com/typescript/-/typescript-4.6.4.tgz#caa78bbc3a59e6a5c510d35703f6a09877ce45e9" + integrity sha512-9ia/jWHIEbo49HfjrLGfKbZSuWo9iTMwXO+Ca3pRsSpbsMbc7/IU8NKdCZVRRBafVPGnoJeFL76ZOAA84I9fEg== uglify-js@^3.1.4: version "3.7.6" From a1e9ce5b2e48ea5dd1c50f2f8bb6b5903e646a02 Mon Sep 17 00:00:00 2001 From: Niklas Mischkulnig <4586894+mischnic@users.noreply.github.com> Date: Tue, 17 May 2022 15:06:07 +0200 Subject: [PATCH 04/15] Preserve correct `this` for named/default imports (#7956) --- .../test/integration/js-import-this/index.js | 17 +++++++++++++++++ .../js-import-this/other-wrapped.js | 13 +++++++++++++ .../test/integration/js-import-this/other.js | 7 +++++++ .../core/integration-tests/test/javascript.js | 15 +++++++++++++++ .../integration-tests/test/output-formats.js | 2 +- .../integration-tests/test/scope-hoisting.js | 17 +++++++++++++++++ .../integration-tests/test/transpilation.js | 18 ++++++++++-------- packages/transformers/js/core/src/hoist.rs | 11 +++++++++++ packages/transformers/js/core/src/modules.rs | 12 +++++++++--- 9 files changed, 100 insertions(+), 12 deletions(-) create mode 100644 packages/core/integration-tests/test/integration/js-import-this/index.js create mode 100644 packages/core/integration-tests/test/integration/js-import-this/other-wrapped.js create mode 100644 packages/core/integration-tests/test/integration/js-import-this/other.js diff --git a/packages/core/integration-tests/test/integration/js-import-this/index.js b/packages/core/integration-tests/test/integration/js-import-this/index.js new file mode 100644 index 00000000000..7b8c0725ad5 --- /dev/null +++ b/packages/core/integration-tests/test/integration/js-import-this/index.js @@ -0,0 +1,17 @@ +import returnThisDefault, { returnThis } from "./other.js"; +import * as other from "./other.js"; + +import returnThisWrappedDefault, { returnThis as returnThisWrapped } from "./other-wrapped.js"; +import * as otherWrapped from "./other-wrapped.js"; + +let result = { + unwrappedNamed: returnThis(), + unwrappedDefault: returnThisDefault(), + unwrappedNamespace: other.returnThis(), + wrappedNamed: returnThisWrapped(), + wrappedDefault: returnThisWrappedDefault(), + wrappedNamespace: otherWrapped.returnThis(), +}; + +output = result; +export default result; diff --git a/packages/core/integration-tests/test/integration/js-import-this/other-wrapped.js b/packages/core/integration-tests/test/integration/js-import-this/other-wrapped.js new file mode 100644 index 00000000000..8eb0cfb8f4f --- /dev/null +++ b/packages/core/integration-tests/test/integration/js-import-this/other-wrapped.js @@ -0,0 +1,13 @@ +import * as ns from "./other-wrapped.js"; + +let y = typeof module !== "undefined" ? module : {}; + +export function returnThis() { + if (y != null) { + return [this === undefined, this === ns]; + } else { + throw new Error(); + } +} + +export default returnThis; diff --git a/packages/core/integration-tests/test/integration/js-import-this/other.js b/packages/core/integration-tests/test/integration/js-import-this/other.js new file mode 100644 index 00000000000..cf6924b8f63 --- /dev/null +++ b/packages/core/integration-tests/test/integration/js-import-this/other.js @@ -0,0 +1,7 @@ +import * as ns from "./other.js"; + +export function returnThis() { + return [this === undefined, this === ns]; +} + +export default returnThis; diff --git a/packages/core/integration-tests/test/javascript.js b/packages/core/integration-tests/test/javascript.js index 592a4d4d008..35905b82b8d 100644 --- a/packages/core/integration-tests/test/javascript.js +++ b/packages/core/integration-tests/test/javascript.js @@ -5267,6 +5267,21 @@ describe('javascript', function () { assert.deepEqual(res.default, 'x: 123'); }); + it('should call named imports without this context', async function () { + let b = await bundle( + path.join(__dirname, 'integration/js-import-this/index.js'), + ); + let res = await run(b, {output: null}, {strict: true}); + assert.deepEqual(res.default, { + unwrappedNamed: [true, false], + unwrappedDefault: [true, false], + unwrappedNamespace: [false, true], + wrappedNamed: [true, false], + wrappedDefault: [true, false], + wrappedNamespace: [false, true], + }); + }); + it('should only replace free references to require', async () => { let b = await bundle( path.join(__dirname, 'integration/js-require-free/index.js'), diff --git a/packages/core/integration-tests/test/output-formats.js b/packages/core/integration-tests/test/output-formats.js index 7b71ef26b90..5929b90e5c7 100644 --- a/packages/core/integration-tests/test/output-formats.js +++ b/packages/core/integration-tests/test/output-formats.js @@ -191,7 +191,7 @@ describe('output formats', function () { let dist = await outputFS.readFile(b.getBundles()[0].filePath, 'utf8'); assert(dist.includes('= require("lodash")')); - assert(dist.includes('= ($parcel$interopDefault(')); + assert(dist.includes('= (0, ($parcel$interopDefault(')); assert(/var {add: \s*\$.+?\$add\s*} = lodash/); assert.equal((await run(b)).bar, 6); }); diff --git a/packages/core/integration-tests/test/scope-hoisting.js b/packages/core/integration-tests/test/scope-hoisting.js index 5ff9f13fb24..f6022da5d64 100644 --- a/packages/core/integration-tests/test/scope-hoisting.js +++ b/packages/core/integration-tests/test/scope-hoisting.js @@ -5284,6 +5284,23 @@ describe('scope hoisting', function () { assert.deepEqual(res, 'x: 123'); }); + it('should call named imports without this context', async function () { + let b = await bundle( + path.join(__dirname, 'integration/js-import-this/index.js'), + ); + let res = await run(b, {output: null}, {strict: true}); + assert.deepEqual(res, { + unwrappedNamed: [true, false], + unwrappedDefault: [true, false], + // TODO: unwrappedNamespace should actually be `[false, true]` but we optimize + // the `ns.foo` expression into a named import, so that namespace isn't available anymore. + unwrappedNamespace: [true, false], + wrappedNamed: [true, false], + wrappedDefault: [true, false], + wrappedNamespace: [false, true], + }); + }); + it('should insert the prelude for sibling bundles referenced in HTML', async function () { let b = await bundle( path.join( diff --git a/packages/core/integration-tests/test/transpilation.js b/packages/core/integration-tests/test/transpilation.js index fba8e37a738..6dd003dcfdc 100644 --- a/packages/core/integration-tests/test/transpilation.js +++ b/packages/core/integration-tests/test/transpilation.js @@ -121,7 +121,9 @@ describe('transpilation', function () { path.join(distDir, 'pure-comment.js'), 'utf8', ); - assert(file.includes('/*#__PURE__*/ _reactDefault.default.createElement')); + assert( + file.includes('/*#__PURE__*/ (0, _reactDefault.default).createElement'), + ); let res = await run(b); assert(res.Foo()); @@ -190,7 +192,7 @@ describe('transpilation', function () { let file = await outputFS.readFile(b.getBundles()[0].filePath, 'utf8'); assert(file.includes('react/jsx-dev-runtime')); - assert(file.includes('_jsxDevRuntime.jsxDEV("div"')); + assert(file.includes('(0, _jsxDevRuntime.jsxDEV)("div"')); }); it('should support the automatic JSX runtime with preact >= 10.5', async function () { @@ -200,7 +202,7 @@ describe('transpilation', function () { let file = await outputFS.readFile(b.getBundles()[0].filePath, 'utf8'); assert(file.includes('preact/jsx-dev-runtime')); - assert(file.includes('_jsxDevRuntime.jsxDEV("div"')); + assert(file.includes('(0, _jsxDevRuntime.jsxDEV)("div"')); }); it('should support the automatic JSX runtime with React ^16.14.0', async function () { @@ -210,7 +212,7 @@ describe('transpilation', function () { let file = await outputFS.readFile(b.getBundles()[0].filePath, 'utf8'); assert(file.includes('react/jsx-dev-runtime')); - assert(file.includes('_jsxDevRuntime.jsxDEV("div"')); + assert(file.includes('(0, _jsxDevRuntime.jsxDEV)("div"')); }); it('should support the automatic JSX runtime with React 18 prereleases', async function () { @@ -220,7 +222,7 @@ describe('transpilation', function () { let file = await outputFS.readFile(b.getBundles()[0].filePath, 'utf8'); assert(file.includes('react/jsx-dev-runtime')); - assert(file.includes('_jsxDevRuntime.jsxDEV("div"')); + assert(file.includes('(0, _jsxDevRuntime.jsxDEV)("div"')); }); it('should support the automatic JSX runtime with experimental React versions', async function () { @@ -230,7 +232,7 @@ describe('transpilation', function () { let file = await outputFS.readFile(b.getBundles()[0].filePath, 'utf8'); assert(file.includes('react/jsx-dev-runtime')); - assert(file.includes('_jsxDevRuntime.jsxDEV("div"')); + assert(file.includes('(0, _jsxDevRuntime.jsxDEV)("div"')); }); it('should support the automatic JSX runtime with preact with alias', async function () { @@ -243,7 +245,7 @@ describe('transpilation', function () { let file = await outputFS.readFile(b.getBundles()[0].filePath, 'utf8'); assert(/\Wreact\/jsx-dev-runtime\W/.test(file)); - assert(file.includes('_jsxDevRuntime.jsxDEV("div"')); + assert(file.includes('(0, _jsxDevRuntime.jsxDEV)("div"')); }); it('should support the automatic JSX runtime with explicit tsconfig.json', async function () { @@ -253,7 +255,7 @@ describe('transpilation', function () { let file = await outputFS.readFile(b.getBundles()[0].filePath, 'utf8'); assert(file.includes('preact/jsx-dev-runtime')); - assert(file.includes('_jsxDevRuntime.jsxDEV("div"')); + assert(file.includes('(0, _jsxDevRuntime.jsxDEV)("div"')); }); it('should support explicit JSX pragma in tsconfig.json', async function () { diff --git a/packages/transformers/js/core/src/hoist.rs b/packages/transformers/js/core/src/hoist.rs index 59f7f10101c..c9702dba018 100644 --- a/packages/transformers/js/core/src/hoist.rs +++ b/packages/transformers/js/core/src/hoist.rs @@ -668,6 +668,17 @@ impl<'a> Fold for Hoist<'a> { } } } + Expr::Ident(ident) => { + if let Some(Import { specifier, .. }) = self.collect.imports.get(&id!(ident)) { + if specifier != "*" { + return Expr::Seq(SeqExpr { + span: ident.span, + exprs: vec![0.into(), Box::new(Expr::Ident(ident.fold_with(self)))], + }); + } + } + return Expr::Ident(ident.fold_with(self)); + } _ => {} } diff --git a/packages/transformers/js/core/src/modules.rs b/packages/transformers/js/core/src/modules.rs index ff8fd8df7e2..2e36bf0cce1 100644 --- a/packages/transformers/js/core/src/modules.rs +++ b/packages/transformers/js/core/src/modules.rs @@ -230,9 +230,15 @@ impl ESMFold { self.get_require_name(source, DUMMY_SP) }; - Expr::Member(MemberExpr { - obj: Box::new(Expr::Ident(obj)), - prop: MemberProp::Ident(Ident::new(imported.clone(), DUMMY_SP)), + Expr::Seq(SeqExpr { + exprs: vec![ + 0.into(), + Box::new(Expr::Member(MemberExpr { + obj: Box::new(Expr::Ident(obj)), + prop: MemberProp::Ident(Ident::new(imported.clone(), DUMMY_SP)), + span, + })), + ], span, }) } From 4e404299feaa23fcfc691dcd3e1302308e2f6377 Mon Sep 17 00:00:00 2001 From: Niklas Mischkulnig <4586894+mischnic@users.noreply.github.com> Date: Tue, 17 May 2022 16:01:58 +0200 Subject: [PATCH 05/15] Bump swc (#8029) --- Cargo.lock | 411 +++++++++--------- packages/core/integration-tests/test/cache.js | 6 +- packages/core/integration-tests/test/fs.js | 2 +- packages/core/integration-tests/test/html.js | 4 +- .../scope-hoisting/es6/rename-helpers/a.js | 4 + .../scope-hoisting/es6/rename-helpers/b.js | 5 + .../scope-hoisting/es6/rename-helpers/c.js | 5 + .../es6/rename-helpers/package.json | 3 + .../es6/rename-helpers/yarn.lock | 0 .../integration/sourcemap-comments/index.js | 2 +- .../core/integration-tests/test/javascript.js | 18 +- .../integration-tests/test/output-formats.js | 4 +- .../integration-tests/test/scope-hoisting.js | 17 + .../core/integration-tests/test/sourcemaps.js | 71 ++- packages/core/integration-tests/test/svg.js | 2 +- packages/optimizers/image/src/lib.rs | 2 +- packages/transformers/js/core/Cargo.toml | 4 +- .../js/core/src/dependency_collector.rs | 1 - .../js/core/src/global_replacer.rs | 217 ++++----- packages/transformers/js/core/src/hoist.rs | 21 +- packages/transformers/js/core/src/lib.rs | 115 +++-- .../transformers/js/core/src/node_replacer.rs | 263 ++++++----- packages/transformers/js/core/src/utils.rs | 35 ++ packages/transformers/js/package.json | 2 +- packages/transformers/js/src/JSTransformer.js | 3 +- yarn.lock | 15 +- 26 files changed, 648 insertions(+), 584 deletions(-) create mode 100644 packages/core/integration-tests/test/integration/scope-hoisting/es6/rename-helpers/a.js create mode 100644 packages/core/integration-tests/test/integration/scope-hoisting/es6/rename-helpers/b.js create mode 100644 packages/core/integration-tests/test/integration/scope-hoisting/es6/rename-helpers/c.js create mode 100644 packages/core/integration-tests/test/integration/scope-hoisting/es6/rename-helpers/package.json create mode 100644 packages/core/integration-tests/test/integration/scope-hoisting/es6/rename-helpers/yarn.lock diff --git a/Cargo.lock b/Cargo.lock index 2c41d14697f..b037f853b86 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -56,9 +56,9 @@ dependencies = [ [[package]] name = "anyhow" -version = "1.0.56" +version = "1.0.57" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4361135be9122e0870de935d7c439aef945b9f9ddd4199a553b5270b49c82a27" +checksum = "08f9b8508dccb7687a1d6c4ce66b2b0ecef467c94667de27d8d7fe1f8d2a9cdc" [[package]] name = "arrayvec" @@ -150,9 +150,9 @@ dependencies = [ [[package]] name = "browserslist-rs" -version = "0.9.0" +version = "0.10.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a0f43be8e0fc9203f6ed7731d2a9a6bf5924cb78907e67e1fe9133617be402be" +checksum = "e55d9cadf66efd56338797ada06140423bd87f290eac200027265d79d621a266" dependencies = [ "ahash", "anyhow", @@ -430,23 +430,13 @@ dependencies = [ [[package]] name = "dashmap" -version = "4.0.2" +version = "5.3.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e77a43b28d0668df09411cb0bc9a8c2adc40f9a048afe863e05fd43251e8e39c" +checksum = "391b56fbd302e585b7a9494fb70e40949567b1cf9003a8e4a6041a1687c26573" dependencies = [ "cfg-if 1.0.0", - "num_cpus", -] - -[[package]] -name = "dashmap" -version = "5.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4c8858831f7781322e539ea39e72449c46b059638250c14344fec8d0aa6e539c" -dependencies = [ - "cfg-if 1.0.0", - "num_cpus", - "parking_lot", + "hashbrown 0.12.1", + "lock_api", ] [[package]] @@ -519,9 +509,9 @@ dependencies = [ [[package]] name = "filetime" -version = "0.2.15" +version = "0.2.16" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "975ccf83d8d9d0d84682850a38c8169027be83368805971cc4f238c2b245bc98" +checksum = "c0408e2626025178a6a7f7ffc05a25bc47103229f19c113755de7bf63816290c" dependencies = [ "cfg-if 1.0.0", "libc", @@ -596,6 +586,12 @@ version = "0.11.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ab5ef0d4909ef3724cc8cce6ccc8572c5c817592e9285f5464f8e86f8bd3726e" +[[package]] +name = "hashbrown" +version = "0.12.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "db0d4cf898abf0081f964436dc980e96670a0f36863e4b83aaacdb65c9d7ccc3" + [[package]] name = "hermit-abi" version = "0.1.19" @@ -650,18 +646,15 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0f647032dfaa1f8b6dc29bd3edb7bbef4861b8b8007ebb118d6db284fd59f6ee" dependencies = [ "autocfg", - "hashbrown", + "hashbrown 0.11.2", "rayon", ] [[package]] name = "indoc" -version = "1.0.4" +version = "1.0.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e7906a9fababaeacb774f72410e497a1d18de916322e33797bb2cd29baa23c9e" -dependencies = [ - "unindent", -] +checksum = "05a0bd019339e5d968b37855180087b7b9d512c5046fbd244cf8c95687927d6e" [[package]] name = "instant" @@ -820,9 +813,9 @@ dependencies = [ [[package]] name = "libc" -version = "0.2.122" +version = "0.2.125" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ec647867e2bf0772e28c8bcde4f0d19a9216916e890543b5a03ed8ef27b8f259" +checksum = "5916d2ae698f6de9bfb891ad7a8d65c09d232dc58cc4ac433c7da3b2fd84bc2b" [[package]] name = "libdeflate-sys" @@ -842,11 +835,21 @@ dependencies = [ "libdeflate-sys", ] +[[package]] +name = "libloading" +version = "0.7.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "efbc0f03f9a775e9f6aed295c6a1ba2253c5757a9e03d55c6caa46a681abcddd" +dependencies = [ + "cfg-if 1.0.0", + "winapi", +] + [[package]] name = "libmimalloc-sys" -version = "0.1.24" +version = "0.1.25" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7705fc40f6ed493f73584abbb324e74f96b358ff60dfe5659a0f8fc12c590a69" +checksum = "11ca136052550448f55df7898c6dbe651c6b574fe38a0d9ea687a9f8088a2e2c" dependencies = [ "cc", ] @@ -863,9 +866,9 @@ dependencies = [ [[package]] name = "log" -version = "0.4.16" +version = "0.4.17" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6389c490849ff5bc16be905ae24bc913a9c8892e19b2341dbc175e14c341c2b8" +checksum = "abb12e687cfb44aa40f41fc3978ef76448f9b6038cad6aef4259d3c095a2382e" dependencies = [ "cfg-if 1.0.0", ] @@ -878,9 +881,9 @@ checksum = "a3e378b66a060d48947b590737b30a1be76706c8dd7b8ba0f2fe3989c68a853f" [[package]] name = "memchr" -version = "2.4.1" +version = "2.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "308cc39be01b73d0d18f82a0e7b2a3df85245f84af96fdddc5d202d27e47b86a" +checksum = "2dffe52ecf27772e601905b7522cb4ef790d2cc203488bbd0e2fe85fcb74566d" [[package]] name = "memoffset" @@ -893,9 +896,9 @@ dependencies = [ [[package]] name = "mimalloc" -version = "0.1.28" +version = "0.1.29" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b0dfa131390c2f6bdb3242f65ff271fcdaca5ff7b6c08f28398be7f2280e3926" +checksum = "2f64ad83c969af2e732e907564deb0d0ed393cec4af80776f77dd77a1a427698" dependencies = [ "libmimalloc-sys", ] @@ -938,16 +941,16 @@ dependencies = [ [[package]] name = "napi" -version = "2.3.3" +version = "2.4.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4c7806930f3d742fade085524e131dd4407c5bd68dff77086cf6b8ef300e0b12" +checksum = "eba1b04555247b935187ea1dddac523ebc470c45806501d7203ed1bec7fa26b2" dependencies = [ "ctor", "lazy_static", "napi-sys", "serde", "serde_json", - "windows", + "thread_local", ] [[package]] @@ -958,9 +961,9 @@ checksum = "ebd4419172727423cf30351406c54f6cc1b354a2cfb4f1dba3e6cd07f6d5522b" [[package]] name = "napi-derive" -version = "2.3.2" +version = "2.4.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "048a9a6127a77b541184324c622ddcbf15ca0af1557076a0993b304932347272" +checksum = "bffed314331505d8a4ce6831dfb5fff9bad37113344ff55824bd398eb3157a1d" dependencies = [ "convert_case", "napi-derive-backend", @@ -971,9 +974,9 @@ dependencies = [ [[package]] name = "napi-derive-backend" -version = "1.0.29" +version = "1.0.32" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5c4e5660e8013eb5027e6d8ece13c2aaec9674b2332c503e658bfff8c90b4acb" +checksum = "a5cab83da14f4202c1f3858dde5b68e1d8c5bb7ee804c5955911cbbe00b835b8" dependencies = [ "convert_case", "once_cell", @@ -985,9 +988,12 @@ dependencies = [ [[package]] name = "napi-sys" -version = "2.1.0" +version = "2.2.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8a385494dac3c52cbcacb393bb3b42669e7db8ab240c7ad5115f549eb061f2cc" +checksum = "529671ebfae679f2ce9630b62dd53c72c56b3eb8b2c852e7e2fa91704ff93d67" +dependencies = [ + "libloading", +] [[package]] name = "nasm-rs" @@ -1037,9 +1043,9 @@ dependencies = [ [[package]] name = "num-integer" -version = "0.1.44" +version = "0.1.45" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d2cc698a63b549a70bc047073d2949cce27cd1c7b0a4a862d08a8031bc2801db" +checksum = "225d3389fb3509a24c93f5c29eb6bde2586b98d9f016636dff58d7c6f7569cd9" dependencies = [ "autocfg", "num-traits", @@ -1047,9 +1053,9 @@ dependencies = [ [[package]] name = "num-iter" -version = "0.1.42" +version = "0.1.43" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b2021c8337a54d21aca0d59a92577a029af9431cb59b909b03252b9c164fad59" +checksum = "7d03e6c028c5dc5cac6e2dec0efda81fc887605bb3d884578bb6d6bf7514e252" dependencies = [ "autocfg", "num-integer", @@ -1069,9 +1075,9 @@ dependencies = [ [[package]] name = "num-traits" -version = "0.2.14" +version = "0.2.15" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9a64b1ec5cda2586e284722486d802acf1f7dbdc623e2bfc57e65ca1cd099290" +checksum = "578ede34cf02f8924ab9447f50c28075b4d3e5b269972345e7e0372b38c6cdcd" dependencies = [ "autocfg", ] @@ -1214,7 +1220,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "87f5ec2493a61ac0506c0f4199f99070cbe83857b0337006a30f3e6719b8ef58" dependencies = [ "lock_api", - "parking_lot_core 0.9.2", + "parking_lot_core 0.9.3", ] [[package]] @@ -1234,9 +1240,9 @@ dependencies = [ [[package]] name = "parking_lot_core" -version = "0.9.2" +version = "0.9.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "995f667a6c822200b0433ac218e05582f0e2efa1b922a3fd2fbaadc5f87bab37" +checksum = "09a279cbf25cb0757810394fbc1e359949b59e348145c643a939a525692e6929" dependencies = [ "cfg-if 1.0.0", "libc", @@ -1315,9 +1321,9 @@ dependencies = [ [[package]] name = "pin-project-lite" -version = "0.2.8" +version = "0.2.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e280fbe77cc62c91527259e9442153f4688736748d24660126286329742b4c6c" +checksum = "e0a7ae3ac2f1173085d398531c705756c94a4c56843785df85a60c1a0afac116" [[package]] name = "pmutil" @@ -1356,17 +1362,17 @@ checksum = "925383efa346730478fb4838dbe9137d2a47675ad789c546d150a6e1dd4ab31c" [[package]] name = "preset_env_base" -version = "0.2.1" +version = "0.2.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "44b10336bf81e96a223c487607acb08a1407d3e208a65e477190e3fe51fc5dea" +checksum = "3ef989b02dabee8f04ce1048e423a55b2a71a1ba68b9df31266170e6220b61ad" dependencies = [ "ahash", "anyhow", "browserslist-rs", - "dashmap 5.2.0", + "dashmap", "from_variant", "once_cell", - "semver 1.0.7", + "semver 1.0.9", "serde", "st-map", ] @@ -1379,18 +1385,18 @@ checksum = "dbf0c48bc1d91375ae5c3cd81e3722dff1abcf81a30960240640d223f59fe0e5" [[package]] name = "proc-macro2" -version = "1.0.37" +version = "1.0.38" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ec757218438d5fda206afc041538b2f6d889286160d649a86a24d37e1235afd1" +checksum = "9027b48e9d4c9175fa2218adf3557f91c1137021739951d4932f5f8268ac48aa" dependencies = [ "unicode-xid", ] [[package]] name = "quote" -version = "1.0.17" +version = "1.0.18" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "632d02bff7f874a36f33ea8bb416cd484b90cc66c1194b1a1110d067a7013f58" +checksum = "a1feb54ed693b93a84e14094943b84b7c4eae204c512b7ccb95ab0c66d278ad1" dependencies = [ "proc-macro2", ] @@ -1427,9 +1433,9 @@ dependencies = [ [[package]] name = "rayon" -version = "1.5.1" +version = "1.5.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c06aca804d41dbc8ba42dfd964f0d01334eceb64314b9ecf7c5fad5188a06d90" +checksum = "bd99e5772ead8baa5215278c9b15bf92087709e9c1b2d1f97cdb5a183c933a7d" dependencies = [ "autocfg", "crossbeam-deque", @@ -1439,14 +1445,13 @@ dependencies = [ [[package]] name = "rayon-core" -version = "1.9.1" +version = "1.9.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d78120e2c850279833f1dd3582f730c4ab53ed95aeaaaa862a2a5c71b1656d8e" +checksum = "258bcdb5ac6dad48491bb2992db6b7cf74878b0384908af124823d118c99683f" dependencies = [ "crossbeam-channel", "crossbeam-deque", "crossbeam-utils", - "lazy_static", "num_cpus", ] @@ -1512,7 +1517,7 @@ version = "0.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "bfa0f585226d2e68097d4f95d113b15b83a82e819ab25717ec0590d9584ef366" dependencies = [ - "semver 1.0.7", + "semver 1.0.9", ] [[package]] @@ -1544,9 +1549,9 @@ dependencies = [ [[package]] name = "semver" -version = "1.0.7" +version = "1.0.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d65bd28f48be7196d222d95b9243287f48d27aca604e08497513019ff0502cc4" +checksum = "8cb243bdfdb5936c8dc3c45762a19d12ab4550cdc753bc247637d4ec35a040fd" dependencies = [ "serde", ] @@ -1559,9 +1564,9 @@ checksum = "388a1df253eca08550bef6c72392cfe7c30914bf41df5269b68cbd6ff8f570a3" [[package]] name = "serde" -version = "1.0.136" +version = "1.0.137" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ce31e24b01e1e524df96f1c2fdd054405f8d7376249a5110886fb4b658484789" +checksum = "61ea8d54c77f8315140a05f4c7237403bf38b72704d031543aa1d16abbf517d1" dependencies = [ "serde_derive", ] @@ -1580,18 +1585,18 @@ dependencies = [ [[package]] name = "serde_bytes" -version = "0.11.5" +version = "0.11.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "16ae07dd2f88a366f15bd0632ba725227018c69a1c8550a927324f8eb8368bb9" +checksum = "212e73464ebcde48d723aa02eb270ba62eff38a9b732df31f33f1b4e145f3a54" dependencies = [ "serde", ] [[package]] name = "serde_derive" -version = "1.0.136" +version = "1.0.137" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "08597e7152fcd306f41838ed3e37be9eaeed2b61c42e2117266a554fab4662f9" +checksum = "1f26faba0c3959972377d3b2d306ee9f71faee9714294e41bb777f83f88578be" dependencies = [ "proc-macro2", "quote", @@ -1600,9 +1605,9 @@ dependencies = [ [[package]] name = "serde_json" -version = "1.0.79" +version = "1.0.81" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8e8d9fa5c3b304765ce1fd9c4c8a3de2c8db365a5b91be52f186efc675681d95" +checksum = "9b7ce2b32a1aed03c558dc61a5cd328f15aff2dbc17daad8fb8af04d2100e15c" dependencies = [ "itoa", "ryu", @@ -1647,9 +1652,9 @@ checksum = "f2dd574626839106c320a323308629dcb1acfc96e32a8cba364ddc61ac23ee83" [[package]] name = "sourcemap" -version = "6.0.1" +version = "6.0.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6e031f2463ecbdd5f34c950f89f5c1e1032f22c0f8e3dc4bdb2e8b6658cf61eb" +checksum = "a2ca89636b276071e7276488131f531dbf43ad1c19bc4bd5a04f6a0ce1ddc138" dependencies = [ "base64 0.11.0", "if_chain", @@ -1771,7 +1776,7 @@ checksum = "84fed4a980e12c737171a7b17c5e0a2f4272899266fa0632ea4e31264ebdfdb5" dependencies = [ "ahash", "anyhow", - "dashmap 5.2.0", + "dashmap", "once_cell", "regex", "serde", @@ -1780,9 +1785,9 @@ dependencies = [ [[package]] name = "swc_common" -version = "0.17.21" +version = "0.18.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "daac2e6fea713c68d37b29ea5fd6342213ca2915a868f38a3fd4aa6750a9b9f8" +checksum = "a14c5d15a47c404bc1e1597f4412643d293aed2c3143c9c4a9c20abe879a934b" dependencies = [ "ahash", "ast_node", @@ -1807,11 +1812,37 @@ dependencies = [ "url", ] +[[package]] +name = "swc_config" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b8bb05ef56c14b95dd7e62e95960153af811b9a447287f1f6ca59f1337fb83d4" +dependencies = [ + "anyhow", + "indexmap", + "serde", + "serde_json", + "swc_config_macro", +] + +[[package]] +name = "swc_config_macro" +version = "0.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fb64bc03d90fd5c90d6ab917bb2b1d7fbd31957df39e31ea24a3f554b4372251" +dependencies = [ + "pmutil", + "proc-macro2", + "quote", + "swc_macros_common", + "syn", +] + [[package]] name = "swc_ecma_ast" -version = "0.75.0" +version = "0.78.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "72961898fbe56591997e667a1ec6a268383582810351c279a15ec710b6177d33" +checksum = "6ed68ad13e4489f309ffed9d302337d7c8bde11d00b8b275b7aa7fda4da035bf" dependencies = [ "is-macro", "num-bigint", @@ -1824,9 +1855,9 @@ dependencies = [ [[package]] name = "swc_ecma_codegen" -version = "0.103.0" +version = "0.108.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "99ca430d8ea2c8791d1341c4035431c90b87330e39479b4a6dabb4fded124e30" +checksum = "897c6f0574ee1280a97d9d45210f50f8841c643a74ddbb09de2ba2d6f9598a33" dependencies = [ "bitflags", "memchr", @@ -1856,16 +1887,17 @@ dependencies = [ [[package]] name = "swc_ecma_loader" -version = "0.29.0" +version = "0.30.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f9ab69df5d4de425833e02de111f14b5544b39ad9c9b82c97e4835fc55c8f1b6" +checksum = "0f7baaa5b99cdf49e830caf54b837891c5c38275ac94c31d555859be95f6479c" dependencies = [ "ahash", "anyhow", - "dashmap 4.0.2", + "dashmap", "normpath", "once_cell", "path-clean", + "pathdiff", "serde", "serde_json", "swc_common", @@ -1874,9 +1906,9 @@ dependencies = [ [[package]] name = "swc_ecma_parser" -version = "0.100.2" +version = "0.104.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "890d967031e3e7330cd7892f27d826b7b4f37c7caa19db85c78a0862e1fe3974" +checksum = "efb97dc6efc95313dedc5158055cc811da77395ef7b54be61948b5ad097a3671" dependencies = [ "either", "enum_kind", @@ -1894,17 +1926,17 @@ dependencies = [ [[package]] name = "swc_ecma_preset_env" -version = "0.117.0" +version = "0.129.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "77a37c95c8e7e47a1fd6bf09ff2744fe55570235e8aba2c9373200213ec2ce25" +checksum = "b5454c4b5a1e9b8278a5f40e3e03e986c70669768630d7a1252665d63cce3e5b" dependencies = [ "ahash", "anyhow", - "dashmap 5.2.0", + "dashmap", "indexmap", "once_cell", "preset_env_base", - "semver 1.0.7", + "semver 1.0.9", "serde", "serde_json", "st-map", @@ -1919,9 +1951,9 @@ dependencies = [ [[package]] name = "swc_ecma_transforms" -version = "0.142.0" +version = "0.154.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f20e5e2d8ab843fa0454e049f73f6d99c444a8c0e2320f77028361ab75e2d18e" +checksum = "2bce21d9e8ff785aaf9b4ac11375d9f5767630fcaf882f72e6af0516224085a6" dependencies = [ "swc_atoms", "swc_common", @@ -1939,13 +1971,14 @@ dependencies = [ [[package]] name = "swc_ecma_transforms_base" -version = "0.75.0" +version = "0.85.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "404c6ea7ca61ceb2ce1f4ed448d1436a38c31b8c572850f04541c0229c966bbf" +checksum = "8262876d5387887776f23c4894fbddff26e5f184edadf2375f3dc19fca2b42a4" dependencies = [ "better_scoped_tls", "once_cell", "phf", + "rustc-hash", "serde", "smallvec", "swc_atoms", @@ -1959,9 +1992,9 @@ dependencies = [ [[package]] name = "swc_ecma_transforms_classes" -version = "0.63.0" +version = "0.73.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "503f2f6bd0f9e6363a93406753bf64675163423774256a267c85a5d9b5b44b08" +checksum = "e74a27c29def9db5ff03db4d3ab3d37701fb6d100951162223b71132908451eb" dependencies = [ "swc_atoms", "swc_common", @@ -1973,9 +2006,9 @@ dependencies = [ [[package]] name = "swc_ecma_transforms_compat" -version = "0.89.0" +version = "0.99.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1d234c84cee8aeeda2ec60087f65acd420e2475bb334a64bbf988b538c21b31d" +checksum = "b8765716f50186e937f79726384cced3c2d4d15293fb0df7f32bd2feb25fb314" dependencies = [ "ahash", "arrayvec", @@ -1987,6 +2020,7 @@ dependencies = [ "smallvec", "swc_atoms", "swc_common", + "swc_config", "swc_ecma_ast", "swc_ecma_transforms_base", "swc_ecma_transforms_classes", @@ -2012,9 +2046,9 @@ dependencies = [ [[package]] name = "swc_ecma_transforms_module" -version = "0.102.0" +version = "0.112.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6c340a0228a9a49240d97a4a4e99a0a61e6613b29b427cc09a60f6ad4dcbf728" +checksum = "48a5415e54a7b7a95e3dd2ede463e377a6254c6a37fae9830b113a2ad45226fe" dependencies = [ "Inflector", "ahash", @@ -2036,14 +2070,15 @@ dependencies = [ [[package]] name = "swc_ecma_transforms_optimization" -version = "0.112.1" +version = "0.124.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "af43d7d92e0bb8ba60d64ce8a7edcab7738f7e858b8e42814fca5c133ba17c19" +checksum = "e27080f65285ccd53bd9ad68e64e62faba2595d57144e4552a1752664525e474" dependencies = [ "ahash", - "dashmap 5.2.0", + "dashmap", "indexmap", "once_cell", + "rustc-hash", "serde_json", "swc_atoms", "swc_common", @@ -2058,9 +2093,9 @@ dependencies = [ [[package]] name = "swc_ecma_transforms_proposal" -version = "0.97.0" +version = "0.107.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "93d08411e517736b0167f3c9784fe9b98cc09308ae12e6072abd2bb2c2236da2" +checksum = "47fc0f3b336764f89adf1899830321c3f5a7e845ede3ad5949eeb7468aa260ab" dependencies = [ "either", "serde", @@ -2077,13 +2112,13 @@ dependencies = [ [[package]] name = "swc_ecma_transforms_react" -version = "0.104.0" +version = "0.114.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "43cda44270dfcc95d61582981baddaf53d96c5233ea7384e81cd6e462816c58e" +checksum = "83e0f5f3cf67dd7d57f23b152c9d55159ceaa10b73b2a32f973398d2304f3363" dependencies = [ "ahash", "base64 0.13.0", - "dashmap 5.2.0", + "dashmap", "indexmap", "once_cell", "regex", @@ -2092,6 +2127,7 @@ dependencies = [ "string_enum", "swc_atoms", "swc_common", + "swc_config", "swc_ecma_ast", "swc_ecma_parser", "swc_ecma_transforms_base", @@ -2102,9 +2138,9 @@ dependencies = [ [[package]] name = "swc_ecma_transforms_typescript" -version = "0.107.0" +version = "0.117.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a09397169ed7ce0751a82cb71655f3a4a1fb00d8863aabd5cca9b46eff3dd5f2" +checksum = "fa8f32954c5a7c6bdead39c8a8a1580127a1759f33ef8b87d00f754882e6090a" dependencies = [ "serde", "swc_atoms", @@ -2118,9 +2154,9 @@ dependencies = [ [[package]] name = "swc_ecma_utils" -version = "0.79.1" +version = "0.85.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "44ee8d60b9977f58214af7102dc30855a6754e742afe6d6e26e5bf13883c7b91" +checksum = "dff9d469b284a48317a695a81346a9609d04ce3a31da4493aac508e0d48a4257" dependencies = [ "indexmap", "once_cell", @@ -2133,9 +2169,9 @@ dependencies = [ [[package]] name = "swc_ecma_visit" -version = "0.61.0" +version = "0.64.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b5ea00a52ba2b971955c62275696d5c59f3cf0cd06db74a66dec378ec9843c78" +checksum = "f2d3783a0dd1e301ae2945ab1241405f913427f9512ec62756d3d2072f7c21bb" dependencies = [ "num-bigint", "swc_atoms", @@ -2147,9 +2183,9 @@ dependencies = [ [[package]] name = "swc_ecmascript" -version = "0.143.0" +version = "0.157.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ebda93aa6422956c184a9eb5fdb0f0f0ff433169fa15e55ef445e5ad0b5e0abe" +checksum = "bd35679e1dc392f776b691b125692d90a7bebd5d23ec96699cfe37d8ae8633b1" dependencies = [ "swc_ecma_ast", "swc_ecma_codegen", @@ -2174,9 +2210,9 @@ dependencies = [ [[package]] name = "swc_macros_common" -version = "0.3.4" +version = "0.3.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "033f8b6e2fc4991a8e422a20b4f52741affcac2267c29357c931508a1a500797" +checksum = "d5dca3f08d02da4684c3373150f7c045128f81ea00f0c434b1b012bc65a6cce3" dependencies = [ "pmutil", "proc-macro2", @@ -2221,9 +2257,9 @@ dependencies = [ [[package]] name = "syn" -version = "1.0.91" +version = "1.0.94" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b683b2b825c8eef438b77c36a06dc262294da3d5a5813fac20da149241dcd44d" +checksum = "a07e33e919ebcd69113d5be0e4d70c5707004ff45188910106854f38b960df4a" dependencies = [ "proc-macro2", "quote", @@ -2250,18 +2286,18 @@ dependencies = [ [[package]] name = "thiserror" -version = "1.0.30" +version = "1.0.31" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "854babe52e4df1653706b98fcfc05843010039b406875930a70e4d9644e5c417" +checksum = "bd829fe32373d27f76265620b5309d0340cb8550f523c1dda251d6298069069a" dependencies = [ "thiserror-impl", ] [[package]] name = "thiserror-impl" -version = "1.0.30" +version = "1.0.31" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "aa32fd3f627f367fe16f893e2597ae3c05020f8bba2666a4e6ea73d377e5714b" +checksum = "0396bc89e626244658bef819e22d0cc459e795a5ebe878e6ec336d1674a8d79a" dependencies = [ "proc-macro2", "quote", @@ -2289,9 +2325,9 @@ dependencies = [ [[package]] name = "tinyvec" -version = "1.5.1" +version = "1.6.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2c1c1d5a42b6245520c249549ec267180beaffcc0615401ac8e31853d4b6d8d2" +checksum = "87cc5ceb3875bb20c2890005a4e226a4651264a5c75edb2421b52861a0a0cb50" dependencies = [ "tinyvec_macros", ] @@ -2304,9 +2340,9 @@ checksum = "cda74da7e1a664f795bb1f8a87ec406fb89a02522cf6e50620d016add6dbbf5c" [[package]] name = "tracing" -version = "0.1.33" +version = "0.1.34" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "80b9fa4360528139bc96100c160b7ae879f5567f49f1782b0b02035b0358ebf3" +checksum = "5d0ecdcb44a79f0fe9844f0c4f33a342cbcbb5117de8001e6ba0dc2351327d09" dependencies = [ "cfg-if 1.0.0", "pin-project-lite", @@ -2316,9 +2352,9 @@ dependencies = [ [[package]] name = "tracing-attributes" -version = "0.1.20" +version = "0.1.21" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2e65ce065b4b5c53e73bb28912318cb8c9e9ad3921f1d669eb0e68b4c8143a2b" +checksum = "cc6b8ad3567499f98a1db7a752b07a7c8c7c7c34c332ec00effb2b0027974b7c" dependencies = [ "proc-macro2", "quote", @@ -2327,9 +2363,9 @@ dependencies = [ [[package]] name = "tracing-core" -version = "0.1.24" +version = "0.1.26" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "90442985ee2f57c9e1b548ee72ae842f4a9a20e3f417cc38dbc5dc684d9bb4ee" +checksum = "f54c8ca710e81886d498c2fd3331b56c93aa248d49de2222ad2742247c60072f" dependencies = [ "lazy_static", ] @@ -2354,9 +2390,9 @@ checksum = "dcf81ac59edc17cc8697ff311e8f5ef2d99fcbd9817b34cec66f90b6c3dfd987" [[package]] name = "unicode-bidi" -version = "0.3.7" +version = "0.3.8" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1a01404663e3db436ed2746d9fefef640d868edae3cceb81c3b8d5732fda678f" +checksum = "099b7128301d285f79ddd55b9a83d5e6b9e97c92e0ea0daebee7263e932de992" [[package]] name = "unicode-id" @@ -2381,15 +2417,9 @@ checksum = "3ed742d4ea2bd1176e236172c8429aaf54486e7ac098db29ffe6529e0ce50973" [[package]] name = "unicode-xid" -version = "0.2.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8ccb82d61f80a663efe1f787a51b16b5a51e3314d6ac365b08639f52387b33f3" - -[[package]] -name = "unindent" -version = "0.1.8" +version = "0.2.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "514672a55d7380da379785a4d70ca8386c8883ff7eaae877be4d2081cebe73d8" +checksum = "957e51f3646910546462e67d5f7599b9e4fb8acdd304b087a6494730f9eebf04" [[package]] name = "unreachable" @@ -2532,97 +2562,54 @@ version = "0.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f" -[[package]] -name = "windows" -version = "0.36.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "36e5436ab30c3d1422272fc6f7b5e7d46e93c94bfca83be808404df9ea5bea76" -dependencies = [ - "windows_aarch64_msvc 0.36.0", - "windows_i686_gnu 0.36.0", - "windows_i686_msvc 0.36.0", - "windows_x86_64_gnu 0.36.0", - "windows_x86_64_msvc 0.36.0", -] - [[package]] name = "windows-sys" -version = "0.34.0" +version = "0.36.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5acdd78cb4ba54c0045ac14f62d8f94a03d10047904ae2a40afa1e99d8f70825" +checksum = "ea04155a16a59f9eab786fe12a4a450e75cdb175f9e0d80da1e17db09f55b8d2" dependencies = [ - "windows_aarch64_msvc 0.34.0", - "windows_i686_gnu 0.34.0", - "windows_i686_msvc 0.34.0", - "windows_x86_64_gnu 0.34.0", - "windows_x86_64_msvc 0.34.0", + "windows_aarch64_msvc", + "windows_i686_gnu", + "windows_i686_msvc", + "windows_x86_64_gnu", + "windows_x86_64_msvc", ] [[package]] name = "windows_aarch64_msvc" -version = "0.34.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "17cffbe740121affb56fad0fc0e421804adf0ae00891205213b5cecd30db881d" - -[[package]] -name = "windows_aarch64_msvc" -version = "0.36.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4bee8cd327bbef19bf86d30bd66379f57905166d3103b0e2eff4a491b85e421d" - -[[package]] -name = "windows_i686_gnu" -version = "0.34.0" +version = "0.36.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2564fde759adb79129d9b4f54be42b32c89970c18ebf93124ca8870a498688ed" +checksum = "9bb8c3fd39ade2d67e9874ac4f3db21f0d710bee00fe7cab16949ec184eeaa47" [[package]] name = "windows_i686_gnu" -version = "0.36.0" +version = "0.36.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3b759cc6e3d97970c98cffe461739e89ab6d424ba5e2e7d3b9b05a2d56116057" +checksum = "180e6ccf01daf4c426b846dfc66db1fc518f074baa793aa7d9b9aaeffad6a3b6" [[package]] name = "windows_i686_msvc" -version = "0.34.0" +version = "0.36.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9cd9d32ba70453522332c14d38814bceeb747d80b3958676007acadd7e166956" - -[[package]] -name = "windows_i686_msvc" -version = "0.36.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7a0cee91bff283876711f91e7db0aa234438bc663a9d8304596df00b0a6fd6ef" - -[[package]] -name = "windows_x86_64_gnu" -version = "0.34.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cfce6deae227ee8d356d19effc141a509cc503dfd1f850622ec4b0f84428e1f4" +checksum = "e2e7917148b2812d1eeafaeb22a97e4813dfa60a3f8f78ebe204bcc88f12f024" [[package]] name = "windows_x86_64_gnu" -version = "0.36.0" +version = "0.36.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "51e8c6f778aa4383b033ff785191aea0f1ebeceedc160c2c92f944ef7e191476" +checksum = "4dcd171b8776c41b97521e5da127a2d86ad280114807d0b2ab1e462bc764d9e1" [[package]] name = "windows_x86_64_msvc" -version = "0.34.0" +version = "0.36.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d19538ccc21819d01deaf88d6a17eae6596a12e9aafdbb97916fb49896d89de9" - -[[package]] -name = "windows_x86_64_msvc" -version = "0.36.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1dd6a8b0b1ea4331e4db47192729fce42ac8a110fd22bb3abac555d8d7700f29" +checksum = "c811ca4a8c853ef420abd8592ba53ddbbac90410fab6903b3e79972a631f7680" [[package]] name = "xxhash-rust" -version = "0.8.4" +version = "0.8.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "83a16b7b403377d61184bb601d8349a4ff2c4cec08a305d004f710b7eaafef24" +checksum = "074914ea4eec286eb8d1fd745768504f420a1f7b7919185682a4a267bed7d2e7" [[package]] name = "zopfli" diff --git a/packages/core/integration-tests/test/cache.js b/packages/core/integration-tests/test/cache.js index b03c13689e8..b72cc66eefd 100644 --- a/packages/core/integration-tests/test/cache.js +++ b/packages/core/integration-tests/test/cache.js @@ -4901,17 +4901,17 @@ describe('cache', function () { }, async update(b) { let res = await run(b.bundleGraph); - assert(res.includes("let a = 'a'")); + assert(res.includes(`let a = "a"`)); await overlayFS.writeFile( path.join(inputDir, 'src/entries/a.js'), - "export let a = 'b';", + `export let a = "b";`, ); }, }); let res = await run(b.bundleGraph); - assert(res.includes("let a = 'b'")); + assert(res.includes(`let a = "b"`)); }); it('should invalidate when switching to a different packager for an inline bundle', async function () { diff --git a/packages/core/integration-tests/test/fs.js b/packages/core/integration-tests/test/fs.js index d25c3dd44bb..800432aca0d 100644 --- a/packages/core/integration-tests/test/fs.js +++ b/packages/core/integration-tests/test/fs.js @@ -198,7 +198,7 @@ describe('fs', function () { path.join(distDir, 'index.js'), 'utf8', ); - assert(contents.includes("require('fs')")); + assert(contents.includes(`require("fs")`)); assert(contents.includes('readFileSync')); await outputFS.writeFile( diff --git a/packages/core/integration-tests/test/html.js b/packages/core/integration-tests/test/html.js index b8b20d51191..21436020961 100644 --- a/packages/core/integration-tests/test/html.js +++ b/packages/core/integration-tests/test/html.js @@ -2549,7 +2549,7 @@ describe('html', function () { await getNextBuild(b); let html = await outputFS.readFile('/dist/index.html', 'utf8'); - assert(html.includes("console.log('test')")); + assert(html.includes(`console.log("test")`)); await overlayFS.writeFile( path.join(__dirname, '/html-inline-js-require/test.js'), @@ -2558,7 +2558,7 @@ describe('html', function () { await getNextBuild(b); html = await outputFS.readFile(path.join(distDir, '/index.html'), 'utf8'); - assert(html.includes("console.log('foo')")); + assert(html.includes(`console.log("foo")`)); }); it('should invalidate parent bundle when nested inline bundles change', async function () { diff --git a/packages/core/integration-tests/test/integration/scope-hoisting/es6/rename-helpers/a.js b/packages/core/integration-tests/test/integration/scope-hoisting/es6/rename-helpers/a.js new file mode 100644 index 00000000000..da98e4e5420 --- /dev/null +++ b/packages/core/integration-tests/test/integration/scope-hoisting/es6/rename-helpers/a.js @@ -0,0 +1,4 @@ +import {B} from './b.js'; +import {C} from './c.js'; + +output = [new B()[Symbol.toStringTag], new C()[Symbol.toStringTag]]; diff --git a/packages/core/integration-tests/test/integration/scope-hoisting/es6/rename-helpers/b.js b/packages/core/integration-tests/test/integration/scope-hoisting/es6/rename-helpers/b.js new file mode 100644 index 00000000000..b55a15508b7 --- /dev/null +++ b/packages/core/integration-tests/test/integration/scope-hoisting/es6/rename-helpers/b.js @@ -0,0 +1,5 @@ +export class B { + get [Symbol.toStringTag]() { + return '1'; + } +} diff --git a/packages/core/integration-tests/test/integration/scope-hoisting/es6/rename-helpers/c.js b/packages/core/integration-tests/test/integration/scope-hoisting/es6/rename-helpers/c.js new file mode 100644 index 00000000000..3f9efc572e8 --- /dev/null +++ b/packages/core/integration-tests/test/integration/scope-hoisting/es6/rename-helpers/c.js @@ -0,0 +1,5 @@ +export class C { + get [Symbol.toStringTag]() { + return '2'; + } +} diff --git a/packages/core/integration-tests/test/integration/scope-hoisting/es6/rename-helpers/package.json b/packages/core/integration-tests/test/integration/scope-hoisting/es6/rename-helpers/package.json new file mode 100644 index 00000000000..601436668c0 --- /dev/null +++ b/packages/core/integration-tests/test/integration/scope-hoisting/es6/rename-helpers/package.json @@ -0,0 +1,3 @@ +{ + "browserslist": "Chrome 50" +} diff --git a/packages/core/integration-tests/test/integration/scope-hoisting/es6/rename-helpers/yarn.lock b/packages/core/integration-tests/test/integration/scope-hoisting/es6/rename-helpers/yarn.lock new file mode 100644 index 00000000000..e69de29bb2d diff --git a/packages/core/integration-tests/test/integration/sourcemap-comments/index.js b/packages/core/integration-tests/test/integration/sourcemap-comments/index.js index 370f721276c..c764d6be5fa 100644 --- a/packages/core/integration-tests/test/integration/sourcemap-comments/index.js +++ b/packages/core/integration-tests/test/integration/sourcemap-comments/index.js @@ -4,6 +4,6 @@ console.log('bar'); /* block comment line */ console.log('baz'); /* multi line - block comment + block comment */ console.log('idhf'); diff --git a/packages/core/integration-tests/test/javascript.js b/packages/core/integration-tests/test/javascript.js index 35905b82b8d..c0c0c6d50f3 100644 --- a/packages/core/integration-tests/test/javascript.js +++ b/packages/core/integration-tests/test/javascript.js @@ -1084,8 +1084,8 @@ describe('javascript', function () { let main = await outputFS.readFile(b.getBundles()[0].filePath, 'utf8'); dedicated = await outputFS.readFile(dedicated.filePath, 'utf8'); shared = await outputFS.readFile(shared.filePath, 'utf8'); - assert(/new Worker(.*?, {[\n\s]+type: 'module'[\n\s]+})/.test(main)); - assert(/new SharedWorker(.*?, {[\n\s]+type: 'module'[\n\s]+})/.test(main)); + assert(/new Worker(.*?, {[\n\s]+type: "module"[\n\s]+})/.test(main)); + assert(/new SharedWorker(.*?, {[\n\s]+type: "module"[\n\s]+})/.test(main)); }); for (let shouldScopeHoist of [true, false]) { @@ -1238,8 +1238,8 @@ describe('javascript', function () { ); let main = await outputFS.readFile(b.getBundles()[0].filePath, 'utf8'); - assert(/new Worker(.*?, {[\n\s]+name: 'worker'[\n\s]+})/.test(main)); - assert(/new SharedWorker(.*?, {[\n\s]+name: 'shared'[\n\s]+})/.test(main)); + assert(/new Worker(.*?, {[\n\s]+name: "worker"[\n\s]+})/.test(main)); + assert(/new SharedWorker(.*?, {[\n\s]+name: "shared"[\n\s]+})/.test(main)); }); it('should error if importing in a worker without type: module', async function () { @@ -1438,7 +1438,7 @@ describe('javascript', function () { ]); let res = await outputFS.readFile(b.getBundles()[0].filePath, 'utf8'); - assert(res.includes("importScripts('imported.js')")); + assert(res.includes(`importScripts("imported.js")`)); }); it('should ignore importScripts in script workers when not passed a string literal', async function () { @@ -1484,7 +1484,7 @@ describe('javascript', function () { ]); let res = await outputFS.readFile(b.getBundles()[1].filePath, 'utf8'); - assert(res.includes("importScripts('https://unpkg.com/parcel')")); + assert(res.includes(`importScripts("https://unpkg.com/parcel")`)); }); it('should support bundling service-workers', async function () { @@ -1559,7 +1559,7 @@ describe('javascript', function () { let main = bundles.find(b => !b.env.isWorker()); let mainContents = await outputFS.readFile(main.filePath, 'utf8'); assert( - /navigator.serviceWorker.register\(.*?, {[\n\s]*scope: 'foo'[\n\s]*}\)/.test( + /navigator.serviceWorker.register\(.*?, {[\n\s]*scope: "foo"[\n\s]*}\)/.test( mainContents, ), ); @@ -4384,7 +4384,7 @@ describe('javascript', function () { let res = await run(b); assert.equal( res.default, - "

test

\n\n", + `

test

\n\n`, ); }); @@ -5556,7 +5556,7 @@ describe('javascript', function () { }, end: { line: 1, - column: 0, + column: 1, }, }, ], diff --git a/packages/core/integration-tests/test/output-formats.js b/packages/core/integration-tests/test/output-formats.js index 5929b90e5c7..01c20793e13 100644 --- a/packages/core/integration-tests/test/output-formats.js +++ b/packages/core/integration-tests/test/output-formats.js @@ -987,7 +987,7 @@ describe('output formats', function () { assert.equal(await res.output, 4); }); - it('should support use an import polyfill for older browsers', async function () { + it('should support using an import polyfill for older browsers', async function () { let b = await bundle( path.join(__dirname, '/integration/formats/esm-browser/index.html'), { @@ -1024,7 +1024,7 @@ describe('output formats', function () { .find(bundle => bundle.name.startsWith('async')); assert( new RegExp( - "getBundleURL\\('[a-zA-Z0-9]+'\\) \\+ \"" + + `getBundleURL\\("[a-zA-Z0-9]+"\\) \\+ "` + path.basename(asyncBundle.filePath) + '"', ).test(entry), diff --git a/packages/core/integration-tests/test/scope-hoisting.js b/packages/core/integration-tests/test/scope-hoisting.js index f6022da5d64..cb669087c7a 100644 --- a/packages/core/integration-tests/test/scope-hoisting.js +++ b/packages/core/integration-tests/test/scope-hoisting.js @@ -169,6 +169,23 @@ describe('scope hoisting', function () { assert.equal(output, 2); }); + it('supports renaming helpers inserted during transpiling', async function () { + let b = await bundle( + path.join( + __dirname, + '/integration/scope-hoisting/es6/rename-helpers/a.js', + ), + ); + let contents = await outputFS.readFile( + b.getBundles()[0].filePath, + 'utf8', + ); + assert(/let \S* = Symbol.toStringTag;/.test(contents)); + + let output = await run(b); + assert.deepEqual(output, ['1', '2']); + }); + it('supports renaming imports', async function () { let b = await bundle( path.join( diff --git a/packages/core/integration-tests/test/sourcemaps.js b/packages/core/integration-tests/test/sourcemaps.js index 3594231d2c4..42de11f19ca 100644 --- a/packages/core/integration-tests/test/sourcemaps.js +++ b/packages/core/integration-tests/test/sourcemaps.js @@ -1,6 +1,9 @@ +// @flow import assert from 'assert'; +import invariant from 'assert'; import path from 'path'; import SourceMap from '@parcel/source-map'; +import type {InitialParcelOptions} from '@parcel/types'; import { bundle as _bundle, inputFS, @@ -11,11 +14,11 @@ import { mergeParcelOptions, } from '@parcel/test-utils'; import {loadSourceMapUrl} from '@parcel/utils'; +import nullthrows from 'nullthrows'; -const bundle = (name, opts = {}) => { +const bundle = (name, opts?: InitialParcelOptions) => { return _bundle( name, - // $FlowFixMe mergeParcelOptions( { defaultTargetOptions: { @@ -43,7 +46,15 @@ function checkSourceMapping({ generatedStr = str, sourcePath, msg = '', -}) { +}: {| + map: SourceMap, + source: string, + generated: string, + str: string, + generatedStr?: string, + sourcePath: string, + msg?: string, +|}) { assert( generated.indexOf(generatedStr) !== -1, "'" + generatedStr + "' not found in generated code", @@ -90,13 +101,14 @@ function checkSourceMapping({ mapping = map.indexedMappingToStringMapping(mappings[closestIndex]); } - assert(mapping, "no mapping for '" + str + "'" + msg); + invariant(mapping, "no mapping for '" + str + "'" + msg); let generatedDiff = { line: generatedPosition.line - mapping.generated.line, column: generatedPosition.column - mapping.generated.column, }; + invariant(mapping.original); let computedSourcePosition = { line: mapping.original.line + generatedDiff.line, column: mapping.original.column + generatedDiff.column, @@ -610,7 +622,9 @@ describe('sourcemaps', function () { '/integration/sourcemap-css/style.css', ); - await bundle(inputFilePath, {minify}); + await bundle(inputFilePath, { + defaultTargetOptions: {shouldOptimize: minify}, + }); let distDir = path.join(__dirname, '../dist/'); let filename = path.join(distDir, 'style.css'); let raw = await outputFS.readFile(filename, 'utf8'); @@ -656,7 +670,9 @@ describe('sourcemaps', function () { '/integration/sourcemap-css-import/style.css', ); - await bundle(inputFilePath, {minify}); + await bundle(inputFilePath, { + defaultTargetOptions: {shouldOptimize: minify}, + }); let distDir = path.join(__dirname, '../dist/'); let filename = path.join(distDir, 'style.css'); let raw = await outputFS.readFile(filename, 'utf8'); @@ -673,22 +689,33 @@ describe('sourcemaps', function () { sourceMap.addVLQMap(map); let mapData = sourceMap.getMap(); - assert.deepEqual(mapData.sources, [ - 'other-style.css', - 'another-style.css', - 'style.css', - ]); + let sources = minify + ? ['style.css', 'other-style.css', 'another-style.css'] + : ['other-style.css', 'another-style.css', 'style.css']; + assert.deepEqual(mapData.sources, sources); let otherStyle = await inputFS.readFile( - path.join(path.dirname(filename), map.sourceRoot, map.sources[0]), + path.join( + path.dirname(filename), + map.sourceRoot, + map.sources[sources.indexOf('other-style.css')], + ), 'utf-8', ); let anotherStyle = await inputFS.readFile( - path.join(path.dirname(filename), map.sourceRoot, map.sources[1]), + path.join( + path.dirname(filename), + map.sourceRoot, + map.sources[sources.indexOf('another-style.css')], + ), 'utf-8', ); let style = await inputFS.readFile( - path.join(path.dirname(filename), map.sourceRoot, map.sources[2]), + path.join( + path.dirname(filename), + map.sourceRoot, + map.sources[sources.indexOf('style.css')], + ), 'utf8', ); @@ -1123,7 +1150,9 @@ describe('sourcemaps', function () { __dirname, '/integration/sourcemap-css-existing/style.css', ); - let b = await bundle(sourceFilename, {minify}); + let b = await bundle(sourceFilename, { + defaultTargetOptions: {shouldOptimize: minify}, + }); let filename = b.getBundles()[0].filePath; let raw = await outputFS.readFile(filename, 'utf8'); @@ -1228,6 +1257,7 @@ describe('sourcemaps', function () { source: input, generated: raw, str: "console.log('foo')", + generatedStr: `console.log("foo")`, sourcePath, }); @@ -1236,6 +1266,7 @@ describe('sourcemaps', function () { source: input, generated: raw, str: "console.log('bar')", + generatedStr: `console.log("bar")`, sourcePath, }); @@ -1244,6 +1275,7 @@ describe('sourcemaps', function () { source: input, generated: raw, str: "console.log('baz')", + generatedStr: `console.log("baz")`, sourcePath, }); @@ -1252,6 +1284,7 @@ describe('sourcemaps', function () { source: input, generated: raw, str: "console.log('idhf')", + generatedStr: `console.log("idhf")`, sourcePath, }); }); @@ -1281,7 +1314,7 @@ describe('sourcemaps', function () { let sourceMap = new SourceMap('/'); sourceMap.addVLQMap(map); let sourcePath = 'index.js'; - let sourceContent = sourceMap.getSourceContent(sourcePath); + let sourceContent = nullthrows(sourceMap.getSourceContent(sourcePath)); checkSourceMapping({ map: sourceMap, @@ -1326,7 +1359,7 @@ describe('sourcemaps', function () { let sourceMap = new SourceMap('/'); sourceMap.addVLQMap(map); let sourcePath = 'index.tsx'; - let sourceContent = sourceMap.getSourceContent(sourcePath); + let sourceContent = nullthrows(sourceMap.getSourceContent(sourcePath)); checkSourceMapping({ map: sourceMap, @@ -1390,8 +1423,8 @@ describe('sourcemaps', function () { map: sourceMap, source: sourceContent, generated: raw, - str: "foo = 'Lorem ipsum", - generatedStr: "foo = 'Lorem ipsum", + str: `foo = 'Lorem ipsum`, + generatedStr: `foo = "Lorem ipsum`, sourcePath, }); }); diff --git a/packages/core/integration-tests/test/svg.js b/packages/core/integration-tests/test/svg.js index dd44e8dd6ec..f8e2d06ad5f 100644 --- a/packages/core/integration-tests/test/svg.js +++ b/packages/core/integration-tests/test/svg.js @@ -195,7 +195,7 @@ describe('svg', function () { ), ); assert(svg.includes('