@atlaspack/core 2.12.1-canary.3354

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (215) hide show
  1. package/LICENSE +201 -0
  2. package/index.d.ts +22 -0
  3. package/lib/AssetGraph.js +518 -0
  4. package/lib/Atlaspack.js +587 -0
  5. package/lib/AtlaspackConfig.js +298 -0
  6. package/lib/AtlaspackConfig.schema.js +125 -0
  7. package/lib/BundleGraph.js +1445 -0
  8. package/lib/CommittedAsset.js +133 -0
  9. package/lib/Dependency.js +88 -0
  10. package/lib/Environment.js +128 -0
  11. package/lib/InternalConfig.js +48 -0
  12. package/lib/PackagerRunner.js +519 -0
  13. package/lib/ReporterRunner.js +151 -0
  14. package/lib/RequestTracker.js +1089 -0
  15. package/lib/SymbolPropagation.js +625 -0
  16. package/lib/TargetDescriptor.schema.js +115 -0
  17. package/lib/Transformation.js +536 -0
  18. package/lib/UncommittedAsset.js +342 -0
  19. package/lib/Validation.js +215 -0
  20. package/lib/applyRuntimes.js +279 -0
  21. package/lib/assetUtils.js +189 -0
  22. package/lib/atlaspack-v3/AtlaspackV3.js +74 -0
  23. package/lib/atlaspack-v3/fs.js +30 -0
  24. package/lib/atlaspack-v3/index.js +19 -0
  25. package/lib/atlaspack-v3/jsCallable.js +15 -0
  26. package/lib/atlaspack-v3/plugins/Resolver.js +12 -0
  27. package/lib/atlaspack-v3/plugins/index.js +16 -0
  28. package/lib/atlaspack-v3/worker/index.js +3 -0
  29. package/lib/atlaspack-v3/worker/worker.js +30 -0
  30. package/lib/buildCache.js +18 -0
  31. package/lib/constants.js +21 -0
  32. package/lib/dumpGraphToGraphViz.js +206 -0
  33. package/lib/index.js +106 -0
  34. package/lib/loadAtlaspackPlugin.js +148 -0
  35. package/lib/loadDotEnv.js +54 -0
  36. package/lib/projectPath.js +86 -0
  37. package/lib/public/Asset.js +259 -0
  38. package/lib/public/Bundle.js +231 -0
  39. package/lib/public/BundleGraph.js +193 -0
  40. package/lib/public/BundleGroup.js +44 -0
  41. package/lib/public/Config.js +202 -0
  42. package/lib/public/Dependency.js +131 -0
  43. package/lib/public/Environment.js +244 -0
  44. package/lib/public/MutableBundleGraph.js +184 -0
  45. package/lib/public/PluginOptions.js +71 -0
  46. package/lib/public/Symbols.js +247 -0
  47. package/lib/public/Target.js +64 -0
  48. package/lib/registerCoreWithSerializer.js +45 -0
  49. package/lib/requests/AssetGraphRequest.js +427 -0
  50. package/lib/requests/AssetGraphRequestRust.js +187 -0
  51. package/lib/requests/AssetRequest.js +137 -0
  52. package/lib/requests/AtlaspackBuildRequest.js +78 -0
  53. package/lib/requests/AtlaspackConfigRequest.js +473 -0
  54. package/lib/requests/BundleGraphRequest.js +419 -0
  55. package/lib/requests/ConfigRequest.js +198 -0
  56. package/lib/requests/DevDepRequest.js +166 -0
  57. package/lib/requests/EntryRequest.js +295 -0
  58. package/lib/requests/PackageRequest.js +88 -0
  59. package/lib/requests/PathRequest.js +349 -0
  60. package/lib/requests/TargetRequest.js +1177 -0
  61. package/lib/requests/ValidationRequest.js +66 -0
  62. package/lib/requests/WriteBundleRequest.js +252 -0
  63. package/lib/requests/WriteBundlesRequest.js +153 -0
  64. package/lib/resolveOptions.js +234 -0
  65. package/lib/serializer.js +216 -0
  66. package/lib/serializerCore.browser.js +29 -0
  67. package/lib/serializerCore.js +16 -0
  68. package/lib/summarizeRequest.js +55 -0
  69. package/lib/types.js +35 -0
  70. package/lib/utils.js +160 -0
  71. package/lib/worker.js +170 -0
  72. package/package.json +59 -0
  73. package/src/AssetGraph.js +646 -0
  74. package/src/Atlaspack.js +632 -0
  75. package/src/AtlaspackConfig.js +490 -0
  76. package/src/AtlaspackConfig.schema.js +141 -0
  77. package/src/BundleGraph.js +2193 -0
  78. package/src/CommittedAsset.js +143 -0
  79. package/src/Dependency.js +142 -0
  80. package/src/Environment.js +151 -0
  81. package/src/InternalConfig.js +72 -0
  82. package/src/PackagerRunner.js +790 -0
  83. package/src/ReporterRunner.js +158 -0
  84. package/src/RequestTracker.js +1697 -0
  85. package/src/SymbolPropagation.js +794 -0
  86. package/src/TargetDescriptor.schema.js +136 -0
  87. package/src/Transformation.js +752 -0
  88. package/src/UncommittedAsset.js +426 -0
  89. package/src/Validation.js +223 -0
  90. package/src/applyRuntimes.js +341 -0
  91. package/src/assetUtils.js +254 -0
  92. package/src/atlaspack-v3/AtlaspackV3.js +73 -0
  93. package/src/atlaspack-v3/fs.js +36 -0
  94. package/src/atlaspack-v3/index.js +5 -0
  95. package/src/atlaspack-v3/jsCallable.js +13 -0
  96. package/src/atlaspack-v3/plugins/Resolver.js +9 -0
  97. package/src/atlaspack-v3/plugins/index.js +3 -0
  98. package/src/atlaspack-v3/worker/index.js +8 -0
  99. package/src/atlaspack-v3/worker/worker.js +14 -0
  100. package/src/buildCache.js +15 -0
  101. package/src/constants.js +22 -0
  102. package/src/dumpGraphToGraphViz.js +244 -0
  103. package/src/index.js +22 -0
  104. package/src/loadAtlaspackPlugin.js +239 -0
  105. package/src/loadDotEnv.js +56 -0
  106. package/src/projectPath.js +87 -0
  107. package/src/public/Asset.js +359 -0
  108. package/src/public/Bundle.js +337 -0
  109. package/src/public/BundleGraph.js +335 -0
  110. package/src/public/BundleGroup.js +55 -0
  111. package/src/public/Config.js +261 -0
  112. package/src/public/Dependency.js +176 -0
  113. package/src/public/Environment.js +316 -0
  114. package/src/public/MutableBundleGraph.js +320 -0
  115. package/src/public/PluginOptions.js +99 -0
  116. package/src/public/Symbols.js +315 -0
  117. package/src/public/Target.js +71 -0
  118. package/src/registerCoreWithSerializer.js +34 -0
  119. package/src/requests/AssetGraphRequest.js +577 -0
  120. package/src/requests/AssetGraphRequestRust.js +222 -0
  121. package/src/requests/AssetRequest.js +179 -0
  122. package/src/requests/AtlaspackBuildRequest.js +109 -0
  123. package/src/requests/AtlaspackConfigRequest.js +709 -0
  124. package/src/requests/BundleGraphRequest.js +547 -0
  125. package/src/requests/ConfigRequest.js +287 -0
  126. package/src/requests/DevDepRequest.js +246 -0
  127. package/src/requests/EntryRequest.js +385 -0
  128. package/src/requests/PackageRequest.js +105 -0
  129. package/src/requests/PathRequest.js +454 -0
  130. package/src/requests/TargetRequest.js +1632 -0
  131. package/src/requests/ValidationRequest.js +79 -0
  132. package/src/requests/WriteBundleRequest.js +362 -0
  133. package/src/requests/WriteBundlesRequest.js +209 -0
  134. package/src/resolveOptions.js +278 -0
  135. package/src/serializer.js +255 -0
  136. package/src/serializerCore.browser.js +8 -0
  137. package/src/serializerCore.js +5 -0
  138. package/src/summarizeRequest.js +47 -0
  139. package/src/types.js +581 -0
  140. package/src/utils.js +211 -0
  141. package/src/worker.js +189 -0
  142. package/test/AssetGraph.test.js +679 -0
  143. package/test/Atlaspack.test.js +142 -0
  144. package/test/AtlaspackConfig.test.js +405 -0
  145. package/test/AtlaspackConfigRequest.test.js +993 -0
  146. package/test/BundleGraph.test.js +121 -0
  147. package/test/EntryRequest.test.js +215 -0
  148. package/test/Environment.test.js +99 -0
  149. package/test/InternalAsset.test.js +76 -0
  150. package/test/PackagerRunner.test.js +27 -0
  151. package/test/PublicAsset.test.js +40 -0
  152. package/test/PublicBundle.test.js +68 -0
  153. package/test/PublicDependency.test.js +22 -0
  154. package/test/PublicEnvironment.test.js +27 -0
  155. package/test/PublicMutableBundleGraph.test.js +192 -0
  156. package/test/RequestTracker.test.js +448 -0
  157. package/test/SymbolPropagation.test.js +716 -0
  158. package/test/TargetRequest.test.js +1715 -0
  159. package/test/fixtures/application-targets/package.json +3 -0
  160. package/test/fixtures/atlaspack/index.js +1 -0
  161. package/test/fixtures/atlaspack/other.js +3 -0
  162. package/test/fixtures/atlaspack/package.json +1 -0
  163. package/test/fixtures/atlaspack/yarn.lock +0 -0
  164. package/test/fixtures/bundle.js +10 -0
  165. package/test/fixtures/common-targets/package.json +24 -0
  166. package/test/fixtures/common-targets-ignore/package.json +13 -0
  167. package/test/fixtures/config/.atlaspackrc +6 -0
  168. package/test/fixtures/config/subfolder/.atlaspackrc +6 -0
  169. package/test/fixtures/config-extends-not-found/.atlaspackrc +3 -0
  170. package/test/fixtures/config-extends-not-found/.atlaspackrc-json5 +3 -0
  171. package/test/fixtures/config-extends-not-found/.atlaspackrc-multiple +3 -0
  172. package/test/fixtures/config-extends-not-found/.atlaspackrc-node-modules +3 -0
  173. package/test/fixtures/config-malformed/.atlaspackrc +3 -0
  174. package/test/fixtures/config-node-pipeline/.atlaspackrc +6 -0
  175. package/test/fixtures/config-plugin-not-found/.atlaspackrc +6 -0
  176. package/test/fixtures/context/package.json +8 -0
  177. package/test/fixtures/custom-format-infer-ext/package.json +6 -0
  178. package/test/fixtures/custom-format-infer-type/package.json +7 -0
  179. package/test/fixtures/custom-format-mismatch/package.json +8 -0
  180. package/test/fixtures/custom-targets/package.json +20 -0
  181. package/test/fixtures/custom-targets-distdir/package.json +11 -0
  182. package/test/fixtures/duplicate-targets/package.json +4 -0
  183. package/test/fixtures/glob-like/[entry].js +0 -0
  184. package/test/fixtures/invalid-distpath/package.json +11 -0
  185. package/test/fixtures/invalid-engines/package.json +12 -0
  186. package/test/fixtures/invalid-source-missing/package.json +5 -0
  187. package/test/fixtures/invalid-source-not-file/package.json +5 -0
  188. package/test/fixtures/invalid-source-not-file/src/index.js +1 -0
  189. package/test/fixtures/invalid-target-source-missing/package.json +9 -0
  190. package/test/fixtures/invalid-target-source-not-file/package.json +9 -0
  191. package/test/fixtures/invalid-target-source-not-file/src/index.js +1 -0
  192. package/test/fixtures/invalid-targets/package.json +19 -0
  193. package/test/fixtures/library-custom-scopehoist/package.json +9 -0
  194. package/test/fixtures/library-scopehoist/package.json +8 -0
  195. package/test/fixtures/local-plugin-config-pkg/.atlaspackrc +3 -0
  196. package/test/fixtures/local-plugin-config-pkg/node_modules/atlaspack-config-local/index.json +8 -0
  197. package/test/fixtures/local-plugin-config-pkg/node_modules/atlaspack-config-local/local-plugin.js +7 -0
  198. package/test/fixtures/local-plugin-config-pkg/node_modules/atlaspack-config-local/package.json +7 -0
  199. package/test/fixtures/main-format-mismatch/package.json +8 -0
  200. package/test/fixtures/main-global/package.json +8 -0
  201. package/test/fixtures/main-mjs/package.json +8 -0
  202. package/test/fixtures/module-a.js +1 -0
  203. package/test/fixtures/module-b.js +1 -0
  204. package/test/fixtures/plugins/local-plugin.js +7 -0
  205. package/test/fixtures/plugins/node_modules/atlaspack-transformer-bad-engines/index.js +7 -0
  206. package/test/fixtures/plugins/node_modules/atlaspack-transformer-bad-engines/package.json +7 -0
  207. package/test/fixtures/plugins/node_modules/atlaspack-transformer-no-engines/index.js +7 -0
  208. package/test/fixtures/plugins/node_modules/atlaspack-transformer-no-engines/package.json +4 -0
  209. package/test/fixtures/targets-default-distdir-none/package.json +5 -0
  210. package/test/fixtures/targets-default-distdir-one/package.json +8 -0
  211. package/test/fixtures/targets-default-distdir-two/package.json +18 -0
  212. package/test/requests/ConfigRequest.test.js +254 -0
  213. package/test/serializer.test.js +302 -0
  214. package/test/test-utils.js +80 -0
  215. package/test/utils.test.js +43 -0
@@ -0,0 +1,1445 @@
1
+ "use strict";
2
+
3
+ Object.defineProperty(exports, "__esModule", {
4
+ value: true
5
+ });
6
+ exports.default = exports.bundleGraphEdgeTypes = void 0;
7
+ function _assert() {
8
+ const data = _interopRequireDefault(require("assert"));
9
+ _assert = function () {
10
+ return data;
11
+ };
12
+ return data;
13
+ }
14
+ function _nullthrows() {
15
+ const data = _interopRequireDefault(require("nullthrows"));
16
+ _nullthrows = function () {
17
+ return data;
18
+ };
19
+ return data;
20
+ }
21
+ function _graph() {
22
+ const data = require("@atlaspack/graph");
23
+ _graph = function () {
24
+ return data;
25
+ };
26
+ return data;
27
+ }
28
+ function _rust() {
29
+ const data = require("@atlaspack/rust");
30
+ _rust = function () {
31
+ return data;
32
+ };
33
+ return data;
34
+ }
35
+ function _utils() {
36
+ const data = require("@atlaspack/utils");
37
+ _utils = function () {
38
+ return data;
39
+ };
40
+ return data;
41
+ }
42
+ var _types = require("./types");
43
+ var _utils2 = require("./utils");
44
+ var _Environment = require("./public/Environment");
45
+ var _projectPath = require("./projectPath");
46
+ var _constants = require("./constants");
47
+ function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
48
+ const bundleGraphEdgeTypes = exports.bundleGraphEdgeTypes = {
49
+ // A lack of an edge type indicates to follow the edge while traversing
50
+ // the bundle's contents, e.g. `bundle.traverse()` during packaging.
51
+ null: 1,
52
+ // Used for constant-time checks of presence of a dependency or asset in a bundle,
53
+ // avoiding bundle traversal in cases like `isAssetInAncestors`
54
+ contains: 2,
55
+ // Connections between bundles and bundle groups, for quick traversal of the
56
+ // bundle hierarchy.
57
+ bundle: 3,
58
+ // When dependency -> asset: Indicates that the asset a dependency references
59
+ // is contained in another bundle.
60
+ // When dependency -> bundle: Indicates the bundle is necessary for any bundles
61
+ // with the dependency.
62
+ // When bundle -> bundle: Indicates the target bundle is necessary for the
63
+ // source bundle.
64
+ // This type prevents referenced assets from being traversed from dependencies
65
+ // along the untyped edge, and enables traversal to referenced bundles that are
66
+ // not directly connected to bundle group nodes.
67
+ references: 4,
68
+ // Signals that the dependency is internally resolvable via the bundle's ancestry,
69
+ // and that the bundle connected to the dependency is not necessary for the source bundle.
70
+ internal_async: 5
71
+ };
72
+ function makeReadOnlySet(set) {
73
+ return new Proxy(set, {
74
+ get(target, property) {
75
+ if (property === 'delete' || property === 'add' || property === 'clear') {
76
+ return undefined;
77
+ } else {
78
+ // $FlowFixMe[incompatible-type]
79
+ let value = target[property];
80
+ return typeof value === 'function' ? value.bind(target) : value;
81
+ }
82
+ }
83
+ });
84
+ }
85
+
86
+ /**
87
+ * Stores assets, dependencies, bundle groups, bundles, and the relationships between them.
88
+ * The BundleGraph is passed to the bundler plugin wrapped in a MutableBundleGraph,
89
+ * and is passed to packagers and optimizers wrapped in the public BundleGraph object, both
90
+ * of which implement public api for this structure. This is the internal structure.
91
+ */
92
+ class BundleGraph {
93
+ /** A set of all existing concise asset ids present in the BundleGraph */
94
+
95
+ /** Maps full asset ids (currently 32-character strings) to concise ids (minimum of 5 character strings) */
96
+
97
+ /**
98
+ * A cache of bundle hashes by bundle id.
99
+ *
100
+ * TODO: These hashes are being invalidated in mutative methods, but this._graph is not a private
101
+ * property so it is possible to reach in and mutate the graph without invalidating these hashes.
102
+ * It needs to be exposed in BundlerRunner for now based on how applying runtimes works and the
103
+ * BundlerRunner takes care of invalidating hashes when runtimes are applied, but this is not ideal.
104
+ */
105
+
106
+ _targetEntryRoots = new Map();
107
+ /** The internal core Graph structure */
108
+
109
+ _bundlePublicIds /*: Set<string> */ = new Set();
110
+ constructor({
111
+ graph,
112
+ publicIdByAssetId,
113
+ assetPublicIds,
114
+ bundleContentHashes
115
+ }) {
116
+ this._graph = graph;
117
+ this._assetPublicIds = assetPublicIds;
118
+ this._publicIdByAssetId = publicIdByAssetId;
119
+ this._bundleContentHashes = bundleContentHashes;
120
+ }
121
+
122
+ /**
123
+ * Produce a BundleGraph from an AssetGraph by removing asset groups and retargeting dependencies
124
+ * based on the symbol data (resolving side-effect free reexports).
125
+ */
126
+ static fromAssetGraph(assetGraph, isProduction, publicIdByAssetId = new Map(), assetPublicIds = new Set()) {
127
+ let graph = new (_graph().ContentGraph)();
128
+ let assetGroupIds = new Map();
129
+ let dependencies = new Map();
130
+ let assetGraphNodeIdToBundleGraphNodeId = new Map();
131
+ let assetGraphRootNode = assetGraph.rootNodeId != null ? assetGraph.getNode(assetGraph.rootNodeId) : null;
132
+ (0, _assert().default)(assetGraphRootNode != null && assetGraphRootNode.type === 'root');
133
+ assetGraph.dfsFast(nodeId => {
134
+ let node = assetGraph.getNode(nodeId);
135
+ if (node != null && node.type === 'asset') {
136
+ let {
137
+ id: assetId
138
+ } = node.value;
139
+ // Generate a new, short public id for this asset to use.
140
+ // If one already exists, use it.
141
+ let publicId = publicIdByAssetId.get(assetId);
142
+ if (publicId == null) {
143
+ publicId = (0, _utils2.getPublicId)(assetId, existing => assetPublicIds.has(existing));
144
+ publicIdByAssetId.set(assetId, publicId);
145
+ assetPublicIds.add(publicId);
146
+ }
147
+ } else if (node != null && node.type === 'asset_group') {
148
+ assetGroupIds.set(nodeId, assetGraph.getNodeIdsConnectedFrom(nodeId));
149
+ }
150
+ });
151
+ let walkVisited = new Set();
152
+ function walk(nodeId) {
153
+ if (walkVisited.has(nodeId)) return;
154
+ walkVisited.add(nodeId);
155
+ let node = (0, _nullthrows().default)(assetGraph.getNode(nodeId));
156
+ if (node.type === 'dependency' && node.value.symbols != null && node.value.env.shouldScopeHoist &&
157
+ // Disable in dev mode because this feature is at odds with safeToIncrementallyBundle
158
+ isProduction) {
159
+ let nodeValueSymbols = node.value.symbols;
160
+
161
+ // asset -> symbols that should be imported directly from that asset
162
+ let targets = new (_utils().DefaultMap)(() => new Map());
163
+ let externalSymbols = new Set();
164
+ let hasAmbiguousSymbols = false;
165
+ for (let [symbol, resolvedSymbol] of node.usedSymbolsUp) {
166
+ if (resolvedSymbol) {
167
+ targets.get(resolvedSymbol.asset).set(symbol, resolvedSymbol.symbol ?? symbol);
168
+ } else if (resolvedSymbol === null) {
169
+ externalSymbols.add(symbol);
170
+ } else if (resolvedSymbol === undefined) {
171
+ hasAmbiguousSymbols = true;
172
+ break;
173
+ }
174
+ }
175
+ if (
176
+ // Only perform retargeting when there is an imported symbol
177
+ // - If the target is side-effect-free, the symbols point to the actual target and removing
178
+ // the original dependency resolution is fine
179
+ // - Otherwise, keep this dependency unchanged for its potential side effects
180
+ node.usedSymbolsUp.size > 0 &&
181
+ // Only perform retargeting if the dependency only points to a single asset (e.g. CSS modules)
182
+ !hasAmbiguousSymbols &&
183
+ // It doesn't make sense to retarget dependencies where `*` is used, because the
184
+ // retargeting won't enable any benefits in that case (apart from potentially even more
185
+ // code being generated).
186
+ !node.usedSymbolsUp.has('*') &&
187
+ // TODO We currently can't rename imports in async imports, e.g. from
188
+ // (atlaspackRequire("...")).then(({ a }) => a);
189
+ // to
190
+ // (atlaspackRequire("...")).then(({ a: b }) => a);
191
+ // or
192
+ // (atlaspackRequire("...")).then((a)=>a);
193
+ // if the reexporting asset did `export {a as b}` or `export * as a`
194
+ node.value.priority === _types.Priority.sync &&
195
+ // For every asset, no symbol is imported multiple times (with a different local name).
196
+ // Don't retarget because this cannot be resolved without also changing the asset symbols
197
+ // (and the asset content itself).
198
+ [...targets].every(([, t]) => new Set([...t.values()]).size === t.size)) {
199
+ var _nodeValueSymbols$get;
200
+ let isReexportAll = ((_nodeValueSymbols$get = nodeValueSymbols.get('*')) === null || _nodeValueSymbols$get === void 0 ? void 0 : _nodeValueSymbols$get.local) === '*';
201
+ let reexportAllLoc = isReexportAll ? (0, _nullthrows().default)(nodeValueSymbols.get('*')).loc : undefined;
202
+
203
+ // TODO adjust sourceAssetIdNode.value.dependencies ?
204
+ let deps = [
205
+ // Keep the original dependency
206
+ {
207
+ asset: null,
208
+ dep: graph.addNodeByContentKey(node.id, {
209
+ ...node,
210
+ value: {
211
+ ...node.value,
212
+ symbols: new Map([...nodeValueSymbols].filter(([k]) => externalSymbols.has(k)))
213
+ },
214
+ usedSymbolsUp: new Map([...node.usedSymbolsUp].filter(([k]) => externalSymbols.has(k))),
215
+ usedSymbolsDown: new Set(),
216
+ excluded: externalSymbols.size === 0
217
+ })
218
+ }, ...[...targets].map(([asset, target]) => {
219
+ let newNodeId = (0, _rust().hashString)(node.id + [...target.keys()].join(','));
220
+ let symbols = new Map();
221
+ for (let [as, from] of target) {
222
+ let existing = nodeValueSymbols.get(as);
223
+ if (existing) {
224
+ symbols.set(from, existing);
225
+ } else {
226
+ (0, _assert().default)(isReexportAll);
227
+ if (as === from) {
228
+ // Keep the export-all for non-renamed reexports, this still correctly models
229
+ // ambiguous resolution with multiple export-alls.
230
+ symbols.set('*', {
231
+ isWeak: true,
232
+ local: '*',
233
+ loc: reexportAllLoc
234
+ });
235
+ } else {
236
+ let local = `${node.value.id}$rewrite$${asset}$${from}`;
237
+ symbols.set(from, {
238
+ isWeak: true,
239
+ local,
240
+ loc: reexportAllLoc
241
+ });
242
+ if (node.value.sourceAssetId != null) {
243
+ let sourceAssetId = (0, _nullthrows().default)(assetGraphNodeIdToBundleGraphNodeId.get(assetGraph.getNodeIdByContentKey(node.value.sourceAssetId)));
244
+ let sourceAsset = (0, _nullthrows().default)(graph.getNode(sourceAssetId));
245
+ (0, _assert().default)(sourceAsset.type === 'asset');
246
+ let sourceAssetSymbols = sourceAsset.value.symbols;
247
+ if (sourceAssetSymbols) {
248
+ // The `as == from` case above should handle multiple export-alls causing
249
+ // ambiguous resolution. So the current symbol is unambiguous and shouldn't
250
+ // already exist on the importer.
251
+ (0, _assert().default)(!sourceAssetSymbols.has(as));
252
+ sourceAssetSymbols.set(as, {
253
+ loc: reexportAllLoc,
254
+ local: local
255
+ });
256
+ }
257
+ }
258
+ }
259
+ }
260
+ }
261
+ let usedSymbolsUp = new Map([...node.usedSymbolsUp].filter(([k]) => target.has(k) || k === '*').map(([k, v]) => [target.get(k) ?? k, v]));
262
+ return {
263
+ asset,
264
+ dep: graph.addNodeByContentKey(newNodeId, {
265
+ ...node,
266
+ id: newNodeId,
267
+ value: {
268
+ ...node.value,
269
+ id: newNodeId,
270
+ symbols
271
+ },
272
+ usedSymbolsUp,
273
+ // This is only a temporary helper needed during symbol propagation and is never
274
+ // read afterwards (and also not exposed through the public API).
275
+ usedSymbolsDown: new Set()
276
+ })
277
+ };
278
+ })];
279
+ dependencies.set(nodeId, deps);
280
+
281
+ // Jump to the dependencies that are used in this dependency
282
+ for (let id of targets.keys()) {
283
+ walk(assetGraph.getNodeIdByContentKey(id));
284
+ }
285
+ return;
286
+ } else {
287
+ // No special handling
288
+ let bundleGraphNodeId = graph.addNodeByContentKey(node.id, node);
289
+ assetGraphNodeIdToBundleGraphNodeId.set(nodeId, bundleGraphNodeId);
290
+ }
291
+ }
292
+ // Don't copy over asset groups into the bundle graph.
293
+ else if (node.type !== 'asset_group') {
294
+ let nodeToAdd = node.type === 'asset' ? {
295
+ ...node,
296
+ value: {
297
+ ...node.value,
298
+ symbols: new Map(node.value.symbols)
299
+ }
300
+ } : node;
301
+ let bundleGraphNodeId = graph.addNodeByContentKey(node.id, nodeToAdd);
302
+ if (node.id === (assetGraphRootNode === null || assetGraphRootNode === void 0 ? void 0 : assetGraphRootNode.id)) {
303
+ graph.setRootNodeId(bundleGraphNodeId);
304
+ }
305
+ assetGraphNodeIdToBundleGraphNodeId.set(nodeId, bundleGraphNodeId);
306
+ }
307
+ for (let id of assetGraph.getNodeIdsConnectedFrom(nodeId)) {
308
+ walk(id);
309
+ }
310
+ }
311
+ walk((0, _nullthrows().default)(assetGraph.rootNodeId));
312
+ for (let edge of assetGraph.getAllEdges()) {
313
+ var _dependencies$get, _assetGroupIds$get;
314
+ if (assetGroupIds.has(edge.from)) {
315
+ continue;
316
+ }
317
+ if (dependencies.has(edge.from)) {
318
+ // Discard previous edge, insert outgoing edges for all split dependencies
319
+ for (let {
320
+ asset,
321
+ dep
322
+ } of (0, _nullthrows().default)(dependencies.get(edge.from))) {
323
+ if (asset != null) {
324
+ graph.addEdge(dep, (0, _nullthrows().default)(assetGraphNodeIdToBundleGraphNodeId.get(assetGraph.getNodeIdByContentKey(asset))));
325
+ }
326
+ }
327
+ continue;
328
+ }
329
+ if (!assetGraphNodeIdToBundleGraphNodeId.has(edge.from)) {
330
+ continue;
331
+ }
332
+ let to = ((_dependencies$get = dependencies.get(edge.to)) === null || _dependencies$get === void 0 ? void 0 : _dependencies$get.map(v => v.dep)) ?? ((_assetGroupIds$get = assetGroupIds.get(edge.to)) === null || _assetGroupIds$get === void 0 ? void 0 : _assetGroupIds$get.map(id => (0, _nullthrows().default)(assetGraphNodeIdToBundleGraphNodeId.get(id)))) ?? [(0, _nullthrows().default)(assetGraphNodeIdToBundleGraphNodeId.get(edge.to))];
333
+ for (let t of to) {
334
+ graph.addEdge((0, _nullthrows().default)(assetGraphNodeIdToBundleGraphNodeId.get(edge.from)), t);
335
+ }
336
+ }
337
+ return new BundleGraph({
338
+ graph,
339
+ assetPublicIds,
340
+ bundleContentHashes: new Map(),
341
+ publicIdByAssetId
342
+ });
343
+ }
344
+ serialize() {
345
+ return {
346
+ $$raw: true,
347
+ graph: this._graph.serialize(),
348
+ assetPublicIds: this._assetPublicIds,
349
+ bundleContentHashes: this._bundleContentHashes,
350
+ publicIdByAssetId: this._publicIdByAssetId
351
+ };
352
+ }
353
+ static deserialize(serialized) {
354
+ return new BundleGraph({
355
+ graph: _graph().ContentGraph.deserialize(serialized.graph),
356
+ assetPublicIds: serialized.assetPublicIds,
357
+ bundleContentHashes: serialized.bundleContentHashes,
358
+ publicIdByAssetId: serialized.publicIdByAssetId
359
+ });
360
+ }
361
+ createBundle(opts) {
362
+ let {
363
+ entryAsset,
364
+ target
365
+ } = opts;
366
+ let bundleId = (0, _rust().hashString)('bundle:' + (opts.entryAsset ? opts.entryAsset.id : opts.uniqueKey) + (0, _projectPath.fromProjectPathRelative)(target.distDir) + (opts.bundleBehavior ?? ''));
367
+ let existing = this._graph.getNodeByContentKey(bundleId);
368
+ if (existing != null) {
369
+ (0, _assert().default)(existing.type === 'bundle');
370
+ return existing.value;
371
+ }
372
+ let publicId = (0, _utils2.getPublicId)(bundleId, existing => this._bundlePublicIds.has(existing));
373
+ this._bundlePublicIds.add(publicId);
374
+ let isPlaceholder = false;
375
+ if (entryAsset) {
376
+ let entryAssetNode = this._graph.getNodeByContentKey(entryAsset.id);
377
+ (0, _assert().default)((entryAssetNode === null || entryAssetNode === void 0 ? void 0 : entryAssetNode.type) === 'asset', 'Entry asset does not exist');
378
+ isPlaceholder = entryAssetNode.requested === false;
379
+ }
380
+ let bundleNode = {
381
+ type: 'bundle',
382
+ id: bundleId,
383
+ value: {
384
+ id: bundleId,
385
+ hashReference: opts.shouldContentHash ? _constants.HASH_REF_PREFIX + bundleId : bundleId.slice(-8),
386
+ type: opts.entryAsset ? opts.entryAsset.type : opts.type,
387
+ env: opts.env,
388
+ entryAssetIds: entryAsset ? [entryAsset.id] : [],
389
+ mainEntryId: entryAsset === null || entryAsset === void 0 ? void 0 : entryAsset.id,
390
+ pipeline: opts.entryAsset ? opts.entryAsset.pipeline : opts.pipeline,
391
+ needsStableName: opts.needsStableName,
392
+ bundleBehavior: opts.bundleBehavior != null ? _types.BundleBehavior[opts.bundleBehavior] : null,
393
+ isSplittable: opts.entryAsset ? opts.entryAsset.isBundleSplittable : opts.isSplittable,
394
+ isPlaceholder,
395
+ target,
396
+ name: null,
397
+ displayName: null,
398
+ publicId
399
+ }
400
+ };
401
+ let bundleNodeId = this._graph.addNodeByContentKey(bundleId, bundleNode);
402
+ if (opts.entryAsset) {
403
+ this._graph.addEdge(bundleNodeId, this._graph.getNodeIdByContentKey(opts.entryAsset.id));
404
+ }
405
+ _assert().default;
406
+ return bundleNode.value;
407
+ }
408
+ addAssetToBundle(asset, bundle) {
409
+ let bundleNodeId = this._graph.getNodeIdByContentKey(bundle.id);
410
+ this._graph.addEdge(bundleNodeId, this._graph.getNodeIdByContentKey(asset.id), bundleGraphEdgeTypes.contains);
411
+ this._graph.addEdge(bundleNodeId, this._graph.getNodeIdByContentKey(asset.id));
412
+ let dependencies = this.getDependencies(asset);
413
+ for (let dependency of dependencies) {
414
+ let dependencyNodeId = this._graph.getNodeIdByContentKey(dependency.id);
415
+ this._graph.addEdge(bundleNodeId, dependencyNodeId, bundleGraphEdgeTypes.contains);
416
+ for (let [bundleGroupNodeId, bundleGroupNode] of this._graph.getNodeIdsConnectedFrom(dependencyNodeId).map(id => [id, (0, _nullthrows().default)(this._graph.getNode(id))]).filter(([, node]) => node.type === 'bundle_group')) {
417
+ (0, _assert().default)(bundleGroupNode.type === 'bundle_group');
418
+ this._graph.addEdge(bundleNodeId, bundleGroupNodeId, bundleGraphEdgeTypes.bundle);
419
+ }
420
+ // If the dependency references a target bundle, add a reference edge from
421
+ // the source bundle to the dependency for easy traversal.
422
+ // TODO: Consider bundle being created from dependency
423
+ if (this._graph.getNodeIdsConnectedFrom(dependencyNodeId, bundleGraphEdgeTypes.references).map(id => (0, _nullthrows().default)(this._graph.getNode(id))).some(node => node.type === 'bundle')) {
424
+ this._graph.addEdge(bundleNodeId, dependencyNodeId, bundleGraphEdgeTypes.references);
425
+ }
426
+ }
427
+ }
428
+ addAssetGraphToBundle(asset, bundle, shouldSkipDependency = d => this.isDependencySkipped(d)) {
429
+ let assetNodeId = this._graph.getNodeIdByContentKey(asset.id);
430
+ let bundleNodeId = this._graph.getNodeIdByContentKey(bundle.id);
431
+
432
+ // The root asset should be reached directly from the bundle in traversal.
433
+ // Its children will be traversed from there.
434
+ this._graph.addEdge(bundleNodeId, assetNodeId);
435
+ this._graph.traverse((nodeId, _, actions) => {
436
+ let node = (0, _nullthrows().default)(this._graph.getNode(nodeId));
437
+ if (node.type === 'bundle_group') {
438
+ actions.skipChildren();
439
+ return;
440
+ }
441
+ if (node.type === 'dependency' && shouldSkipDependency(node.value)) {
442
+ actions.skipChildren();
443
+ return;
444
+ }
445
+ if (node.type === 'asset' || node.type === 'dependency') {
446
+ this._graph.addEdge(bundleNodeId, nodeId, bundleGraphEdgeTypes.contains);
447
+ }
448
+ if (node.type === 'dependency') {
449
+ for (let [bundleGroupNodeId, bundleGroupNode] of this._graph.getNodeIdsConnectedFrom(nodeId).map(id => [id, (0, _nullthrows().default)(this._graph.getNode(id))]).filter(([, node]) => node.type === 'bundle_group')) {
450
+ (0, _assert().default)(bundleGroupNode.type === 'bundle_group');
451
+ this._graph.addEdge(bundleNodeId, bundleGroupNodeId, bundleGraphEdgeTypes.bundle);
452
+ }
453
+
454
+ // If the dependency references a target bundle, add a reference edge from
455
+ // the source bundle to the dependency for easy traversal.
456
+ if (this._graph.getNodeIdsConnectedFrom(nodeId, bundleGraphEdgeTypes.references).map(id => (0, _nullthrows().default)(this._graph.getNode(id))).some(node => node.type === 'bundle')) {
457
+ this._graph.addEdge(bundleNodeId, nodeId, bundleGraphEdgeTypes.references);
458
+ this.markDependencyReferenceable(node.value);
459
+ //all bundles that have this dependency need to have an edge from bundle to that dependency
460
+ }
461
+ }
462
+ }, assetNodeId);
463
+ this._bundleContentHashes.delete(bundle.id);
464
+ }
465
+ markDependencyReferenceable(dependency) {
466
+ for (let bundle of this.getBundlesWithDependency(dependency)) {
467
+ this._graph.addEdge(this._graph.getNodeIdByContentKey(bundle.id), this._graph.getNodeIdByContentKey(dependency.id), bundleGraphEdgeTypes.references);
468
+ }
469
+ }
470
+ addEntryToBundle(asset, bundle, shouldSkipDependency) {
471
+ this.addAssetGraphToBundle(asset, bundle, shouldSkipDependency);
472
+ if (!bundle.entryAssetIds.includes(asset.id)) {
473
+ bundle.entryAssetIds.push(asset.id);
474
+ }
475
+ }
476
+ internalizeAsyncDependency(bundle, dependency) {
477
+ if (dependency.priority === _types.Priority.sync) {
478
+ throw new Error('Expected an async dependency');
479
+ }
480
+
481
+ // It's possible for internalized async dependencies to not have
482
+ // reference edges and still have untyped edges.
483
+ // TODO: Maybe don't use internalized async edges at all?
484
+ let dependencyNodeId = this._graph.getNodeIdByContentKey(dependency.id);
485
+ let resolved = this.getResolvedAsset(dependency);
486
+ if (resolved) {
487
+ let resolvedNodeId = this._graph.getNodeIdByContentKey(resolved.id);
488
+ if (!this._graph.hasEdge(dependencyNodeId, resolvedNodeId, bundleGraphEdgeTypes.references)) {
489
+ this._graph.addEdge(dependencyNodeId, resolvedNodeId, bundleGraphEdgeTypes.references);
490
+ this._graph.removeEdge(dependencyNodeId, resolvedNodeId);
491
+ }
492
+ }
493
+ this._graph.addEdge(this._graph.getNodeIdByContentKey(bundle.id), this._graph.getNodeIdByContentKey(dependency.id), bundleGraphEdgeTypes.internal_async);
494
+ this._removeExternalDependency(bundle, dependency);
495
+ }
496
+ isDependencySkipped(dependency) {
497
+ let node = this._graph.getNodeByContentKey(dependency.id);
498
+ (0, _assert().default)(node && node.type === 'dependency');
499
+ return !!node.hasDeferred || node.excluded;
500
+ }
501
+ getParentBundlesOfBundleGroup(bundleGroup) {
502
+ return this._graph.getNodeIdsConnectedTo(this._graph.getNodeIdByContentKey((0, _utils2.getBundleGroupId)(bundleGroup)), bundleGraphEdgeTypes.bundle).map(id => (0, _nullthrows().default)(this._graph.getNode(id))).filter(node => node.type === 'bundle').map(node => {
503
+ (0, _assert().default)(node.type === 'bundle');
504
+ return node.value;
505
+ });
506
+ }
507
+ resolveAsyncDependency(dependency, bundle) {
508
+ let depNodeId = this._graph.getNodeIdByContentKey(dependency.id);
509
+ let bundleNodeId = bundle != null ? this._graph.getNodeIdByContentKey(bundle.id) : null;
510
+ if (bundleNodeId != null && this._graph.hasEdge(bundleNodeId, depNodeId, bundleGraphEdgeTypes.internal_async)) {
511
+ let referencedAssetNodeIds = this._graph.getNodeIdsConnectedFrom(depNodeId, bundleGraphEdgeTypes.references);
512
+ let resolved;
513
+ if (referencedAssetNodeIds.length === 0) {
514
+ resolved = this.getResolvedAsset(dependency, bundle);
515
+ } else if (referencedAssetNodeIds.length === 1) {
516
+ let referencedAssetNode = this._graph.getNode(referencedAssetNodeIds[0]);
517
+ // If a referenced asset already exists, resolve this dependency to it.
518
+ (0, _assert().default)((referencedAssetNode === null || referencedAssetNode === void 0 ? void 0 : referencedAssetNode.type) === 'asset');
519
+ resolved = referencedAssetNode.value;
520
+ } else {
521
+ throw new Error('Dependencies can only reference one asset');
522
+ }
523
+ if (resolved == null) {
524
+ return;
525
+ } else {
526
+ return {
527
+ type: 'asset',
528
+ value: resolved
529
+ };
530
+ }
531
+ }
532
+ let node = this._graph.getNodeIdsConnectedFrom(this._graph.getNodeIdByContentKey(dependency.id)).map(id => (0, _nullthrows().default)(this._graph.getNode(id))).find(node => node.type === 'bundle_group');
533
+ if (node == null) {
534
+ return;
535
+ }
536
+ (0, _assert().default)(node.type === 'bundle_group');
537
+ return {
538
+ type: 'bundle_group',
539
+ value: node.value
540
+ };
541
+ }
542
+
543
+ // eslint-disable-next-line no-unused-vars
544
+ getReferencedBundle(dependency, fromBundle) {
545
+ let dependencyNodeId = this._graph.getNodeIdByContentKey(dependency.id);
546
+
547
+ // Find an attached bundle via a reference edge (e.g. from createAssetReference).
548
+ let bundleNodes = this._graph.getNodeIdsConnectedFrom(dependencyNodeId, bundleGraphEdgeTypes.references).map(id => (0, _nullthrows().default)(this._graph.getNode(id))).filter(node => node.type === 'bundle');
549
+ if (bundleNodes.length) {
550
+ let bundleNode = bundleNodes.find(b => b.type === 'bundle' && b.value.type === fromBundle.type) || bundleNodes[0];
551
+ (0, _assert().default)(bundleNode.type === 'bundle');
552
+ return bundleNode.value;
553
+ }
554
+
555
+ // If this dependency is async, there will be a bundle group attached to it.
556
+ let node = this._graph.getNodeIdsConnectedFrom(dependencyNodeId).map(id => (0, _nullthrows().default)(this._graph.getNode(id))).find(node => node.type === 'bundle_group');
557
+ if (node != null) {
558
+ (0, _assert().default)(node.type === 'bundle_group');
559
+ return this.getBundlesInBundleGroup(node.value, {
560
+ includeInline: true
561
+ }).find(b => {
562
+ let mainEntryId = b.entryAssetIds[b.entryAssetIds.length - 1];
563
+ return mainEntryId != null && node.value.entryAssetId === mainEntryId;
564
+ });
565
+ }
566
+ }
567
+ removeAssetGraphFromBundle(asset, bundle) {
568
+ let bundleNodeId = this._graph.getNodeIdByContentKey(bundle.id);
569
+ let assetNodeId = this._graph.getNodeIdByContentKey(asset.id);
570
+
571
+ // Remove all contains edges from the bundle to the nodes in the asset's
572
+ // subgraph.
573
+ this._graph.traverse((nodeId, context, actions) => {
574
+ let node = (0, _nullthrows().default)(this._graph.getNode(nodeId));
575
+ if (node.type === 'bundle_group') {
576
+ actions.skipChildren();
577
+ return;
578
+ }
579
+ if (node.type !== 'dependency' && node.type !== 'asset') {
580
+ return;
581
+ }
582
+ if (this._graph.hasEdge(bundleNodeId, nodeId, bundleGraphEdgeTypes.contains)) {
583
+ this._graph.removeEdge(bundleNodeId, nodeId, bundleGraphEdgeTypes.contains,
584
+ // Removing this contains edge should not orphan the connected node. This
585
+ // is disabled for performance reasons as these edges are removed as part
586
+ // of a traversal, and checking for orphans becomes quite expensive in
587
+ // aggregate.
588
+ false /* removeOrphans */);
589
+ } else {
590
+ actions.skipChildren();
591
+ }
592
+ if (node.type === 'asset' && this._graph.hasEdge(bundleNodeId, nodeId)) {
593
+ // Remove the untyped edge from the bundle to the node (it's an entry)
594
+ this._graph.removeEdge(bundleNodeId, nodeId);
595
+ let entryIndex = bundle.entryAssetIds.indexOf(node.value.id);
596
+ if (entryIndex >= 0) {
597
+ // Shared bundles have untyped edges to their asset graphs but don't
598
+ // have entry assets. For those that have entry asset ids, remove them.
599
+ bundle.entryAssetIds.splice(entryIndex, 1);
600
+ }
601
+ }
602
+ if (node.type === 'dependency') {
603
+ this._removeExternalDependency(bundle, node.value);
604
+ if (this._graph.hasEdge(bundleNodeId, nodeId, bundleGraphEdgeTypes.references)) {
605
+ this._graph.addEdge(bundleNodeId, nodeId, bundleGraphEdgeTypes.references);
606
+ this.markDependencyReferenceable(node.value);
607
+ }
608
+ if (this._graph.hasEdge(bundleNodeId, nodeId, bundleGraphEdgeTypes.internal_async)) {
609
+ this._graph.removeEdge(bundleNodeId, nodeId, bundleGraphEdgeTypes.internal_async);
610
+ }
611
+ }
612
+ }, assetNodeId);
613
+
614
+ // Remove bundle node if it no longer has any entry assets
615
+ if (this._graph.getNodeIdsConnectedFrom(bundleNodeId).length === 0) {
616
+ this.removeBundle(bundle);
617
+ }
618
+ this._bundleContentHashes.delete(bundle.id);
619
+ }
620
+
621
+ /**
622
+ * Remove a bundle from the bundle graph. Remove its bundle group if it is
623
+ * the only bundle in the group.
624
+ */
625
+ removeBundle(bundle) {
626
+ // Remove bundle node if it no longer has any entry assets
627
+ let bundleNodeId = this._graph.getNodeIdByContentKey(bundle.id);
628
+ let bundleGroupNodeIds = this._graph.getNodeIdsConnectedTo(bundleNodeId, bundleGraphEdgeTypes.bundle);
629
+ this._graph.removeNode(bundleNodeId);
630
+ let removedBundleGroups = new Set();
631
+ // Remove bundle group node if it no longer has any bundles
632
+ for (let bundleGroupNodeId of bundleGroupNodeIds) {
633
+ let bundleGroupNode = (0, _nullthrows().default)(this._graph.getNode(bundleGroupNodeId));
634
+ (0, _assert().default)(bundleGroupNode.type === 'bundle_group');
635
+ let bundleGroup = bundleGroupNode.value;
636
+ if (
637
+ // If the bundle group's entry asset belongs to this bundle, the group
638
+ // was created because of this bundle. Remove the group.
639
+ bundle.entryAssetIds.includes(bundleGroup.entryAssetId) ||
640
+ // If the bundle group is now empty, remove it.
641
+ this.getBundlesInBundleGroup(bundleGroup, {
642
+ includeInline: true
643
+ }).length === 0) {
644
+ removedBundleGroups.add(bundleGroup);
645
+ this.removeBundleGroup(bundleGroup);
646
+ }
647
+ }
648
+ this._bundleContentHashes.delete(bundle.id);
649
+ return removedBundleGroups;
650
+ }
651
+ removeBundleGroup(bundleGroup) {
652
+ let bundleGroupNode = (0, _nullthrows().default)(this._graph.getNodeByContentKey((0, _utils2.getBundleGroupId)(bundleGroup)));
653
+ (0, _assert().default)(bundleGroupNode.type === 'bundle_group');
654
+ let bundlesInGroup = this.getBundlesInBundleGroup(bundleGroupNode.value, {
655
+ includeInline: true
656
+ });
657
+ for (let bundle of bundlesInGroup) {
658
+ if (this.getBundleGroupsContainingBundle(bundle).length === 1) {
659
+ let removedBundleGroups = this.removeBundle(bundle);
660
+ if (removedBundleGroups.has(bundleGroup)) {
661
+ // This function can be reentered through removeBundle above. In the case this
662
+ // bundle group has already been removed, stop.
663
+ return;
664
+ }
665
+ }
666
+ }
667
+
668
+ // This function can be reentered through removeBundle above. In this case,
669
+ // the node may already been removed.
670
+ if (this._graph.hasContentKey(bundleGroupNode.id)) {
671
+ this._graph.removeNode(this._graph.getNodeIdByContentKey(bundleGroupNode.id));
672
+ }
673
+ (0, _assert().default)(bundlesInGroup.every(bundle => this.getBundleGroupsContainingBundle(bundle).length > 0));
674
+ }
675
+ _removeExternalDependency(bundle, dependency) {
676
+ let bundleNodeId = this._graph.getNodeIdByContentKey(bundle.id);
677
+ for (let bundleGroupNode of this._graph.getNodeIdsConnectedFrom(this._graph.getNodeIdByContentKey(dependency.id)).map(id => (0, _nullthrows().default)(this._graph.getNode(id))).filter(node => node.type === 'bundle_group')) {
678
+ let bundleGroupNodeId = this._graph.getNodeIdByContentKey(bundleGroupNode.id);
679
+ if (!this._graph.hasEdge(bundleNodeId, bundleGroupNodeId, bundleGraphEdgeTypes.bundle)) {
680
+ continue;
681
+ }
682
+ let inboundDependencies = this._graph.getNodeIdsConnectedTo(bundleGroupNodeId).map(id => (0, _nullthrows().default)(this._graph.getNode(id))).filter(node => node.type === 'dependency').map(node => {
683
+ (0, _assert().default)(node.type === 'dependency');
684
+ return node.value;
685
+ });
686
+
687
+ // If every inbound dependency to this bundle group does not belong to this bundle,
688
+ // or the dependency is internal to the bundle, then the connection between
689
+ // this bundle and the group is safe to remove.
690
+ if (inboundDependencies.every(dependency => dependency.specifierType !== _types.SpecifierType.url && (!this.bundleHasDependency(bundle, dependency) || this._graph.hasEdge(bundleNodeId, this._graph.getNodeIdByContentKey(dependency.id), bundleGraphEdgeTypes.internal_async)))) {
691
+ this._graph.removeEdge(bundleNodeId, bundleGroupNodeId, bundleGraphEdgeTypes.bundle);
692
+ }
693
+ }
694
+ }
695
+ createAssetReference(dependency, asset, bundle) {
696
+ let dependencyId = this._graph.getNodeIdByContentKey(dependency.id);
697
+ let assetId = this._graph.getNodeIdByContentKey(asset.id);
698
+ let bundleId = this._graph.getNodeIdByContentKey(bundle.id);
699
+ this._graph.addEdge(dependencyId, assetId, bundleGraphEdgeTypes.references);
700
+ this._graph.addEdge(dependencyId, bundleId, bundleGraphEdgeTypes.references);
701
+ this.markDependencyReferenceable(dependency);
702
+ if (this._graph.hasEdge(dependencyId, assetId)) {
703
+ this._graph.removeEdge(dependencyId, assetId);
704
+ }
705
+ }
706
+ createBundleReference(from, to) {
707
+ this._graph.addEdge(this._graph.getNodeIdByContentKey(from.id), this._graph.getNodeIdByContentKey(to.id), bundleGraphEdgeTypes.references);
708
+ }
709
+ getBundlesWithAsset(asset) {
710
+ return this._graph.getNodeIdsConnectedTo(this._graph.getNodeIdByContentKey(asset.id), bundleGraphEdgeTypes.contains).map(id => (0, _nullthrows().default)(this._graph.getNode(id))).filter(node => node.type === 'bundle').map(node => {
711
+ (0, _assert().default)(node.type === 'bundle');
712
+ return node.value;
713
+ });
714
+ }
715
+ getBundlesWithDependency(dependency) {
716
+ return this._graph.getNodeIdsConnectedTo((0, _nullthrows().default)(this._graph.getNodeIdByContentKey(dependency.id)), bundleGraphEdgeTypes.contains).map(id => (0, _nullthrows().default)(this._graph.getNode(id))).filter(node => node.type === 'bundle').map(node => {
717
+ (0, _assert().default)(node.type === 'bundle');
718
+ return node.value;
719
+ });
720
+ }
721
+ getDependencyAssets(dependency) {
722
+ return this._graph.getNodeIdsConnectedFrom(this._graph.getNodeIdByContentKey(dependency.id)).map(id => (0, _nullthrows().default)(this._graph.getNode(id))).filter(node => node.type === 'asset').map(node => {
723
+ (0, _assert().default)(node.type === 'asset');
724
+ return node.value;
725
+ });
726
+ }
727
+ getResolvedAsset(dep, bundle) {
728
+ let assets = this.getDependencyAssets(dep);
729
+ let firstAsset = assets[0];
730
+ let resolved =
731
+ // If no bundle is specified, use the first concrete asset.
732
+ bundle == null ? firstAsset :
733
+ // Otherwise, find the first asset that belongs to this bundle.
734
+ assets.find(asset => this.bundleHasAsset(bundle, asset)) || assets.find(a => a.type === bundle.type) || firstAsset;
735
+
736
+ // If a resolution still hasn't been found, return the first referenced asset.
737
+ if (resolved == null) {
738
+ let potential = [];
739
+ this._graph.traverse((nodeId, _, traversal) => {
740
+ let node = (0, _nullthrows().default)(this._graph.getNode(nodeId));
741
+ if (node.type === 'asset') {
742
+ potential.push(node.value);
743
+ } else if (node.id !== dep.id) {
744
+ traversal.skipChildren();
745
+ }
746
+ }, this._graph.getNodeIdByContentKey(dep.id), bundleGraphEdgeTypes.references);
747
+ if (bundle) {
748
+ resolved = potential.find(a => a.type === bundle.type);
749
+ }
750
+ resolved ||= potential[0];
751
+ }
752
+ return resolved;
753
+ }
754
+ getDependencies(asset) {
755
+ let nodeId = this._graph.getNodeIdByContentKey(asset.id);
756
+ return this._graph.getNodeIdsConnectedFrom(nodeId).map(id => {
757
+ let node = (0, _nullthrows().default)(this._graph.getNode(id));
758
+ (0, _assert().default)(node.type === 'dependency');
759
+ return node.value;
760
+ });
761
+ }
762
+ traverseAssets(bundle, visit, startAsset) {
763
+ return this.traverseBundle(bundle, (0, _graph().mapVisitor)(node => node.type === 'asset' ? node.value : null, visit), startAsset);
764
+ }
765
+ isAssetReferenced(bundle, asset) {
766
+ // If the asset is available in multiple bundles in the same target, it's referenced.
767
+ if (this.getBundlesWithAsset(asset).filter(b => b.target.distDir === bundle.target.distDir).length > 1) {
768
+ return true;
769
+ }
770
+ let assetNodeId = (0, _nullthrows().default)(this._graph.getNodeIdByContentKey(asset.id));
771
+ if (this._graph.getNodeIdsConnectedTo(assetNodeId, bundleGraphEdgeTypes.references).map(id => this._graph.getNode(id)).some(node => (node === null || node === void 0 ? void 0 : node.type) === 'dependency' && node.value.priority === _types.Priority.lazy && node.value.specifierType !== _types.SpecifierType.url)) {
772
+ // If this asset is referenced by any async dependency, it's referenced.
773
+ return true;
774
+ }
775
+ let dependencies = this._graph.getNodeIdsConnectedTo(assetNodeId).map(id => (0, _nullthrows().default)(this._graph.getNode(id))).filter(node => node.type === 'dependency').map(node => {
776
+ (0, _assert().default)(node.type === 'dependency');
777
+ return node.value;
778
+ });
779
+ const bundleHasReference = bundle => {
780
+ return !this.bundleHasAsset(bundle, asset) && dependencies.some(dependency => this.bundleHasDependency(bundle, dependency));
781
+ };
782
+ let visitedBundles = new Set();
783
+ let siblingBundles = new Set(this.getBundleGroupsContainingBundle(bundle).flatMap(bundleGroup => this.getBundlesInBundleGroup(bundleGroup, {
784
+ includeInline: true
785
+ })));
786
+
787
+ // Check if any of this bundle's descendants, referencers, bundles referenced
788
+ // by referencers, or descendants of its referencers use the asset without
789
+ // an explicit reference edge. This can happen if e.g. the asset has been
790
+ // deduplicated.
791
+ return [...siblingBundles].some(referencer => {
792
+ let isReferenced = false;
793
+ this.traverseBundles((descendant, _, actions) => {
794
+ if (descendant.id === bundle.id) {
795
+ return;
796
+ }
797
+ if (visitedBundles.has(descendant)) {
798
+ actions.skipChildren();
799
+ return;
800
+ }
801
+ visitedBundles.add(descendant);
802
+ if (descendant.type !== bundle.type || descendant.env.context !== bundle.env.context) {
803
+ actions.skipChildren();
804
+ return;
805
+ }
806
+ if (bundleHasReference(descendant)) {
807
+ isReferenced = true;
808
+ actions.stop();
809
+ }
810
+ }, referencer);
811
+ return isReferenced;
812
+ });
813
+ }
814
+ hasParentBundleOfType(bundle, type) {
815
+ let parents = this.getParentBundles(bundle);
816
+ return parents.length > 0 && parents.every(parent => parent.type === type);
817
+ }
818
+ getParentBundles(bundle) {
819
+ let parentBundles = new Set();
820
+ for (let bundleGroup of this.getBundleGroupsContainingBundle(bundle)) {
821
+ for (let parentBundle of this.getParentBundlesOfBundleGroup(bundleGroup)) {
822
+ parentBundles.add(parentBundle);
823
+ }
824
+ }
825
+ return [...parentBundles];
826
+ }
827
+ isAssetReachableFromBundle(asset, bundle) {
828
+ // If a bundle's environment is isolated, it can't access assets present
829
+ // in any ancestor bundles. Don't consider any assets reachable.
830
+ if (_Environment.ISOLATED_ENVS.has(bundle.env.context) || !bundle.isSplittable || bundle.bundleBehavior === _types.BundleBehavior.isolated || bundle.bundleBehavior === _types.BundleBehavior.inline) {
831
+ return false;
832
+ }
833
+
834
+ // For an asset to be reachable from a bundle, it must either exist in a sibling bundle,
835
+ // or in an ancestor bundle group reachable from all parent bundles.
836
+ let bundleGroups = this.getBundleGroupsContainingBundle(bundle);
837
+ return bundleGroups.every(bundleGroup => {
838
+ // If the asset is in any sibling bundles of the original bundle, it is reachable.
839
+ let bundles = this.getBundlesInBundleGroup(bundleGroup);
840
+ if (bundles.some(b => b.id !== bundle.id && b.bundleBehavior !== _types.BundleBehavior.isolated && b.bundleBehavior !== _types.BundleBehavior.inline && this.bundleHasAsset(b, asset))) {
841
+ return true;
842
+ }
843
+
844
+ // Get a list of parent bundle nodes pointing to the bundle group
845
+ let parentBundleNodes = this._graph.getNodeIdsConnectedTo(this._graph.getNodeIdByContentKey((0, _utils2.getBundleGroupId)(bundleGroup)), bundleGraphEdgeTypes.bundle);
846
+
847
+ // Check that every parent bundle has a bundle group in its ancestry that contains the asset.
848
+ return parentBundleNodes.every(bundleNodeId => {
849
+ let bundleNode = (0, _nullthrows().default)(this._graph.getNode(bundleNodeId));
850
+ if (bundleNode.type !== 'bundle' || bundleNode.value.bundleBehavior === _types.BundleBehavior.isolated || bundleNode.value.bundleBehavior === _types.BundleBehavior.inline) {
851
+ return false;
852
+ }
853
+ let isReachable = true;
854
+ this._graph.traverseAncestors(bundleNodeId, (nodeId, ctx, actions) => {
855
+ let node = (0, _nullthrows().default)(this._graph.getNode(nodeId));
856
+ // If we've reached the root or a context change without
857
+ // finding this asset in the ancestry, it is not reachable.
858
+ if (node.type === 'root' || node.type === 'bundle' && (node.value.id === bundle.id || node.value.env.context !== bundle.env.context)) {
859
+ isReachable = false;
860
+ actions.stop();
861
+ return;
862
+ }
863
+ if (node.type === 'bundle_group') {
864
+ let childBundles = this.getBundlesInBundleGroup(node.value);
865
+ if (childBundles.some(b => b.id !== bundle.id && b.bundleBehavior !== _types.BundleBehavior.isolated && b.bundleBehavior !== _types.BundleBehavior.inline && this.bundleHasAsset(b, asset))) {
866
+ actions.skipChildren();
867
+ }
868
+ }
869
+ }, [bundleGraphEdgeTypes.references, bundleGraphEdgeTypes.bundle]);
870
+ return isReachable;
871
+ });
872
+ });
873
+ }
874
+
875
+ /**
876
+ * TODO: Document why this works like this & why visitor order matters
877
+ * on these use-cases.
878
+ */
879
+ traverseBundle(bundle, visit, startAsset) {
880
+ let entries = !startAsset;
881
+ let bundleNodeId = this._graph.getNodeIdByContentKey(bundle.id);
882
+
883
+ // A modified DFS traversal which traverses entry assets in the same order
884
+ // as their ids appear in `bundle.entryAssetIds`.
885
+ return this._graph.dfs({
886
+ visit: (0, _graph().mapVisitor)((nodeId, actions) => {
887
+ let node = (0, _nullthrows().default)(this._graph.getNode(nodeId));
888
+ if (nodeId === bundleNodeId) {
889
+ return;
890
+ }
891
+ if (node.type === 'dependency' || node.type === 'asset') {
892
+ if (this._graph.hasEdge(bundleNodeId, nodeId, bundleGraphEdgeTypes.contains)) {
893
+ return node;
894
+ }
895
+ }
896
+ actions.skipChildren();
897
+ }, visit),
898
+ startNodeId: startAsset ? this._graph.getNodeIdByContentKey(startAsset.id) : bundleNodeId,
899
+ getChildren: nodeId => {
900
+ let children = this._graph.getNodeIdsConnectedFrom(nodeId).map(id => [id, (0, _nullthrows().default)(this._graph.getNode(id))]);
901
+ let sorted = entries && bundle.entryAssetIds.length > 0 ? children.sort(([, a], [, b]) => {
902
+ let aIndex = bundle.entryAssetIds.indexOf(a.id);
903
+ let bIndex = bundle.entryAssetIds.indexOf(b.id);
904
+ if (aIndex === bIndex) {
905
+ // If both don't exist in the entry asset list, or
906
+ // otherwise have the same index.
907
+ return 0;
908
+ } else if (aIndex === -1) {
909
+ return 1;
910
+ } else if (bIndex === -1) {
911
+ return -1;
912
+ }
913
+ return aIndex - bIndex;
914
+ }) : children;
915
+ entries = false;
916
+ return sorted.map(([id]) => id);
917
+ }
918
+ });
919
+ }
920
+ traverse(visit, start) {
921
+ return this._graph.filteredTraverse(nodeId => {
922
+ let node = (0, _nullthrows().default)(this._graph.getNode(nodeId));
923
+ if (node.type === 'asset' || node.type === 'dependency') {
924
+ return node;
925
+ }
926
+ }, visit, start ? this._graph.getNodeIdByContentKey(start.id) : undefined,
927
+ // start with root
928
+ _graph().ALL_EDGE_TYPES);
929
+ }
930
+ getChildBundles(bundle) {
931
+ let siblings = new Set(this.getReferencedBundles(bundle));
932
+ let bundles = [];
933
+ this.traverseBundles((b, _, actions) => {
934
+ if (bundle.id === b.id) {
935
+ return;
936
+ }
937
+ if (!siblings.has(b)) {
938
+ bundles.push(b);
939
+ }
940
+ actions.skipChildren();
941
+ }, bundle);
942
+ return bundles;
943
+ }
944
+ traverseBundles(visit, startBundle) {
945
+ return this._graph.filteredTraverse(nodeId => {
946
+ let node = (0, _nullthrows().default)(this._graph.getNode(nodeId));
947
+ return node.type === 'bundle' ? node.value : null;
948
+ }, visit, startBundle ? this._graph.getNodeIdByContentKey(startBundle.id) : null, [bundleGraphEdgeTypes.bundle, bundleGraphEdgeTypes.references]);
949
+ }
950
+ getBundles(opts) {
951
+ let bundles = [];
952
+ this.traverseBundles(bundle => {
953
+ if (opts !== null && opts !== void 0 && opts.includeInline || bundle.bundleBehavior !== _types.BundleBehavior.inline) {
954
+ bundles.push(bundle);
955
+ }
956
+ });
957
+ return bundles;
958
+ }
959
+ getTotalSize(asset) {
960
+ let size = 0;
961
+ this._graph.traverse((nodeId, _, actions) => {
962
+ let node = (0, _nullthrows().default)(this._graph.getNode(nodeId));
963
+ if (node.type === 'bundle_group') {
964
+ actions.skipChildren();
965
+ return;
966
+ }
967
+ if (node.type === 'asset') {
968
+ size += node.value.stats.size;
969
+ }
970
+ }, this._graph.getNodeIdByContentKey(asset.id));
971
+ return size;
972
+ }
973
+ getReferencingBundles(bundle) {
974
+ let referencingBundles = new Set();
975
+ this._graph.traverseAncestors(this._graph.getNodeIdByContentKey(bundle.id), nodeId => {
976
+ let node = (0, _nullthrows().default)(this._graph.getNode(nodeId));
977
+ if (node.type === 'bundle' && node.value.id !== bundle.id) {
978
+ referencingBundles.add(node.value);
979
+ }
980
+ }, bundleGraphEdgeTypes.references);
981
+ return [...referencingBundles];
982
+ }
983
+ getBundleGroupsContainingBundle(bundle) {
984
+ let bundleGroups = new Set();
985
+ for (let currentBundle of [bundle, ...this.getReferencingBundles(bundle)]) {
986
+ for (let bundleGroup of this.getDirectParentBundleGroups(currentBundle)) {
987
+ bundleGroups.add(bundleGroup);
988
+ }
989
+ }
990
+ return [...bundleGroups];
991
+ }
992
+ getDirectParentBundleGroups(bundle) {
993
+ return this._graph.getNodeIdsConnectedTo((0, _nullthrows().default)(this._graph.getNodeIdByContentKey(bundle.id)), bundleGraphEdgeTypes.bundle).map(id => (0, _nullthrows().default)(this._graph.getNode(id))).filter(node => node.type === 'bundle_group').map(node => {
994
+ (0, _assert().default)(node.type === 'bundle_group');
995
+ return node.value;
996
+ });
997
+ }
998
+ getBundlesInBundleGroup(bundleGroup, opts) {
999
+ let bundles = new Set();
1000
+ for (let bundleNodeId of this._graph.getNodeIdsConnectedFrom(this._graph.getNodeIdByContentKey((0, _utils2.getBundleGroupId)(bundleGroup)), bundleGraphEdgeTypes.bundle)) {
1001
+ let bundleNode = (0, _nullthrows().default)(this._graph.getNode(bundleNodeId));
1002
+ (0, _assert().default)(bundleNode.type === 'bundle');
1003
+ let bundle = bundleNode.value;
1004
+ if (opts !== null && opts !== void 0 && opts.includeInline || bundle.bundleBehavior !== _types.BundleBehavior.inline) {
1005
+ bundles.add(bundle);
1006
+ }
1007
+ for (let referencedBundle of this.getReferencedBundles(bundle, {
1008
+ includeInline: opts === null || opts === void 0 ? void 0 : opts.includeInline
1009
+ })) {
1010
+ bundles.add(referencedBundle);
1011
+ }
1012
+ }
1013
+ return [...bundles];
1014
+ }
1015
+ getReferencedBundles(bundle, opts) {
1016
+ let recursive = (opts === null || opts === void 0 ? void 0 : opts.recursive) ?? true;
1017
+ let includeInline = (opts === null || opts === void 0 ? void 0 : opts.includeInline) ?? false;
1018
+ let referencedBundles = new Set();
1019
+ this._graph.dfs({
1020
+ visit: (nodeId, _, actions) => {
1021
+ let node = (0, _nullthrows().default)(this._graph.getNode(nodeId));
1022
+ if (node.type !== 'bundle') {
1023
+ return;
1024
+ }
1025
+ if (node.value.id === bundle.id) {
1026
+ return;
1027
+ }
1028
+ if (includeInline || node.value.bundleBehavior !== _types.BundleBehavior.inline) {
1029
+ referencedBundles.add(node.value);
1030
+ }
1031
+ if (!recursive) {
1032
+ actions.skipChildren();
1033
+ }
1034
+ },
1035
+ startNodeId: this._graph.getNodeIdByContentKey(bundle.id),
1036
+ getChildren: nodeId =>
1037
+ // Shared bundles seem to depend on being used in the opposite order
1038
+ // they were added.
1039
+ // TODO: Should this be the case?
1040
+ this._graph.getNodeIdsConnectedFrom(nodeId, bundleGraphEdgeTypes.references)
1041
+ });
1042
+ return [...referencedBundles];
1043
+ }
1044
+ getIncomingDependencies(asset) {
1045
+ if (!this._graph.hasContentKey(asset.id)) {
1046
+ return [];
1047
+ }
1048
+ // Dependencies can be a a parent node via an untyped edge (like in the AssetGraph but without AssetGroups)
1049
+ // or they can be parent nodes via a 'references' edge
1050
+ return this._graph.getNodeIdsConnectedTo(this._graph.getNodeIdByContentKey(asset.id), _graph().ALL_EDGE_TYPES).map(id => (0, _nullthrows().default)(this._graph.getNode(id))).filter(n => n.type === 'dependency').map(n => {
1051
+ (0, _assert().default)(n.type === 'dependency');
1052
+ return n.value;
1053
+ });
1054
+ }
1055
+ getAssetWithDependency(dep) {
1056
+ if (!this._graph.hasContentKey(dep.id)) {
1057
+ return null;
1058
+ }
1059
+ let res = this._graph.getNodeIdsConnectedTo(this._graph.getNodeIdByContentKey(dep.id));
1060
+ (0, _assert().default)(res.length <= 1, 'Expected a single asset to be connected to a dependency');
1061
+ let resNode = this._graph.getNode(res[0]);
1062
+ if ((resNode === null || resNode === void 0 ? void 0 : resNode.type) === 'asset') {
1063
+ return resNode.value;
1064
+ }
1065
+ }
1066
+ bundleHasAsset(bundle, asset) {
1067
+ let bundleNodeId = this._graph.getNodeIdByContentKey(bundle.id);
1068
+ let assetNodeId = this._graph.getNodeIdByContentKey(asset.id);
1069
+ return this._graph.hasEdge(bundleNodeId, assetNodeId, bundleGraphEdgeTypes.contains);
1070
+ }
1071
+ bundleHasDependency(bundle, dependency) {
1072
+ let bundleNodeId = this._graph.getNodeIdByContentKey(bundle.id);
1073
+ let dependencyNodeId = this._graph.getNodeIdByContentKey(dependency.id);
1074
+ return this._graph.hasEdge(bundleNodeId, dependencyNodeId, bundleGraphEdgeTypes.contains);
1075
+ }
1076
+ filteredTraverse(bundleNodeId, filter, visit) {
1077
+ return this._graph.filteredTraverse(filter, visit, bundleNodeId);
1078
+ }
1079
+ getSymbolResolution(asset, symbol, boundary) {
1080
+ var _asset$symbols;
1081
+ let assetOutside = boundary && !this.bundleHasAsset(boundary, asset);
1082
+ let identifier = (_asset$symbols = asset.symbols) === null || _asset$symbols === void 0 || (_asset$symbols = _asset$symbols.get(symbol)) === null || _asset$symbols === void 0 ? void 0 : _asset$symbols.local;
1083
+ if (symbol === '*') {
1084
+ var _asset$symbols2;
1085
+ return {
1086
+ asset,
1087
+ exportSymbol: '*',
1088
+ symbol: identifier ?? null,
1089
+ loc: (_asset$symbols2 = asset.symbols) === null || _asset$symbols2 === void 0 || (_asset$symbols2 = _asset$symbols2.get(symbol)) === null || _asset$symbols2 === void 0 ? void 0 : _asset$symbols2.loc
1090
+ };
1091
+ }
1092
+ let found = false;
1093
+ let nonStaticDependency = false;
1094
+ let skipped = false;
1095
+ let deps = this.getDependencies(asset).reverse();
1096
+ let potentialResults = [];
1097
+ for (let dep of deps) {
1098
+ var _depSymbols$get;
1099
+ let depSymbols = dep.symbols;
1100
+ if (!depSymbols) {
1101
+ nonStaticDependency = true;
1102
+ continue;
1103
+ }
1104
+ // If this is a re-export, find the original module.
1105
+ let symbolLookup = new Map([...depSymbols].map(([key, val]) => [val.local, key]));
1106
+ let depSymbol = symbolLookup.get(identifier);
1107
+ if (depSymbol != null) {
1108
+ let resolved = this.getResolvedAsset(dep, boundary);
1109
+ if (!resolved || resolved.id === asset.id) {
1110
+ var _asset$symbols3;
1111
+ // External module or self-reference
1112
+ return {
1113
+ asset,
1114
+ exportSymbol: symbol,
1115
+ symbol: identifier,
1116
+ loc: (_asset$symbols3 = asset.symbols) === null || _asset$symbols3 === void 0 || (_asset$symbols3 = _asset$symbols3.get(symbol)) === null || _asset$symbols3 === void 0 ? void 0 : _asset$symbols3.loc
1117
+ };
1118
+ }
1119
+ if (assetOutside) {
1120
+ // We found the symbol, but `asset` is outside, return `asset` and the original symbol
1121
+ found = true;
1122
+ break;
1123
+ }
1124
+ if (this.isDependencySkipped(dep)) {
1125
+ // We found the symbol and `dep` was skipped
1126
+ skipped = true;
1127
+ break;
1128
+ }
1129
+ let {
1130
+ asset: resolvedAsset,
1131
+ symbol: resolvedSymbol,
1132
+ exportSymbol,
1133
+ loc
1134
+ } = this.getSymbolResolution(resolved, depSymbol, boundary);
1135
+ if (!loc) {
1136
+ var _asset$symbols4;
1137
+ // Remember how we got there
1138
+ loc = (_asset$symbols4 = asset.symbols) === null || _asset$symbols4 === void 0 || (_asset$symbols4 = _asset$symbols4.get(symbol)) === null || _asset$symbols4 === void 0 ? void 0 : _asset$symbols4.loc;
1139
+ }
1140
+ return {
1141
+ asset: resolvedAsset,
1142
+ symbol: resolvedSymbol,
1143
+ exportSymbol,
1144
+ loc
1145
+ };
1146
+ }
1147
+ // If this module exports wildcards, resolve the original module.
1148
+ // Default exports are excluded from wildcard exports.
1149
+ // Wildcard reexports are never listed in the reexporting asset's symbols.
1150
+ if (identifier == null && ((_depSymbols$get = depSymbols.get('*')) === null || _depSymbols$get === void 0 ? void 0 : _depSymbols$get.local) === '*' && symbol !== 'default') {
1151
+ let resolved = this.getResolvedAsset(dep, boundary);
1152
+ if (!resolved) {
1153
+ continue;
1154
+ }
1155
+ let result = this.getSymbolResolution(resolved, symbol, boundary);
1156
+
1157
+ // We found the symbol
1158
+ if (result.symbol != undefined) {
1159
+ var _resolved$symbols;
1160
+ if (assetOutside) {
1161
+ // ..., but `asset` is outside, return `asset` and the original symbol
1162
+ found = true;
1163
+ break;
1164
+ }
1165
+ if (this.isDependencySkipped(dep)) {
1166
+ // We found the symbol and `dep` was skipped
1167
+ skipped = true;
1168
+ break;
1169
+ }
1170
+ return {
1171
+ asset: result.asset,
1172
+ symbol: result.symbol,
1173
+ exportSymbol: result.exportSymbol,
1174
+ loc: (_resolved$symbols = resolved.symbols) === null || _resolved$symbols === void 0 || (_resolved$symbols = _resolved$symbols.get(symbol)) === null || _resolved$symbols === void 0 ? void 0 : _resolved$symbols.loc
1175
+ };
1176
+ }
1177
+ if (result.symbol === null) {
1178
+ found = true;
1179
+ if (boundary && !this.bundleHasAsset(boundary, result.asset)) {
1180
+ // If the returned asset is outside (and it's the first asset that is outside), return it.
1181
+ if (!assetOutside) {
1182
+ var _resolved$symbols2;
1183
+ return {
1184
+ asset: result.asset,
1185
+ symbol: result.symbol,
1186
+ exportSymbol: result.exportSymbol,
1187
+ loc: (_resolved$symbols2 = resolved.symbols) === null || _resolved$symbols2 === void 0 || (_resolved$symbols2 = _resolved$symbols2.get(symbol)) === null || _resolved$symbols2 === void 0 ? void 0 : _resolved$symbols2.loc
1188
+ };
1189
+ } else {
1190
+ // Otherwise the original asset will be returned at the end.
1191
+ break;
1192
+ }
1193
+ } else {
1194
+ var _resolved$symbols3;
1195
+ // We didn't find it in this dependency, but it might still be there: bailout.
1196
+ // Continue searching though, with the assumption that there are no conficting reexports
1197
+ // and there might be a another (re)export (where we might statically find the symbol).
1198
+ potentialResults.push({
1199
+ asset: result.asset,
1200
+ symbol: result.symbol,
1201
+ exportSymbol: result.exportSymbol,
1202
+ loc: (_resolved$symbols3 = resolved.symbols) === null || _resolved$symbols3 === void 0 || (_resolved$symbols3 = _resolved$symbols3.get(symbol)) === null || _resolved$symbols3 === void 0 ? void 0 : _resolved$symbols3.loc
1203
+ });
1204
+ }
1205
+ }
1206
+ }
1207
+ }
1208
+
1209
+ // We didn't find the exact symbol...
1210
+ if (potentialResults.length == 1) {
1211
+ // ..., but if it does exist, it has to be behind this one reexport.
1212
+ return potentialResults[0];
1213
+ } else {
1214
+ var _asset$symbols6;
1215
+ let result = identifier;
1216
+ if (skipped) {
1217
+ // ... and it was excluded (by symbol propagation) or deferred.
1218
+ result = false;
1219
+ } else {
1220
+ // ... and there is no single reexport, but it might still be exported:
1221
+ if (found) {
1222
+ // Fallback to namespace access, because of a bundle boundary.
1223
+ result = null;
1224
+ } else if (result === undefined) {
1225
+ var _asset$symbols5;
1226
+ // If not exported explicitly by the asset (= would have to be in * or a reexport-all) ...
1227
+ if (nonStaticDependency || (_asset$symbols5 = asset.symbols) !== null && _asset$symbols5 !== void 0 && _asset$symbols5.has('*')) {
1228
+ // ... and if there are non-statically analyzable dependencies or it's a CJS asset,
1229
+ // fallback to namespace access.
1230
+ result = null;
1231
+ }
1232
+ // (It shouldn't be possible for the symbol to be in a reexport-all and to end up here).
1233
+ // Otherwise return undefined to report that the symbol wasn't found.
1234
+ }
1235
+ }
1236
+
1237
+ return {
1238
+ asset,
1239
+ exportSymbol: symbol,
1240
+ symbol: result,
1241
+ loc: (_asset$symbols6 = asset.symbols) === null || _asset$symbols6 === void 0 || (_asset$symbols6 = _asset$symbols6.get(symbol)) === null || _asset$symbols6 === void 0 ? void 0 : _asset$symbols6.loc
1242
+ };
1243
+ }
1244
+ }
1245
+ getAssetById(contentKey) {
1246
+ let node = this._graph.getNodeByContentKey(contentKey);
1247
+ if (node == null) {
1248
+ throw new Error('Node not found');
1249
+ } else if (node.type !== 'asset') {
1250
+ throw new Error('Node was not an asset');
1251
+ }
1252
+ return node.value;
1253
+ }
1254
+ getAssetPublicId(asset) {
1255
+ let publicId = this._publicIdByAssetId.get(asset.id);
1256
+ if (publicId == null) {
1257
+ throw new Error("Asset or it's public id not found");
1258
+ }
1259
+ return publicId;
1260
+ }
1261
+ getExportedSymbols(asset, boundary) {
1262
+ if (!asset.symbols) {
1263
+ return [];
1264
+ }
1265
+ let symbols = [];
1266
+ for (let symbol of asset.symbols.keys()) {
1267
+ symbols.push({
1268
+ ...this.getSymbolResolution(asset, symbol, boundary),
1269
+ exportAs: symbol
1270
+ });
1271
+ }
1272
+ let deps = this.getDependencies(asset);
1273
+ for (let dep of deps) {
1274
+ var _depSymbols$get2;
1275
+ let depSymbols = dep.symbols;
1276
+ if (!depSymbols) continue;
1277
+ if (((_depSymbols$get2 = depSymbols.get('*')) === null || _depSymbols$get2 === void 0 ? void 0 : _depSymbols$get2.local) === '*') {
1278
+ let resolved = this.getResolvedAsset(dep, boundary);
1279
+ if (!resolved) continue;
1280
+ let exported = this.getExportedSymbols(resolved, boundary).filter(s => s.exportSymbol !== 'default').map(s => s.exportSymbol !== '*' ? {
1281
+ ...s,
1282
+ exportAs: s.exportSymbol
1283
+ } : s);
1284
+ symbols.push(...exported);
1285
+ }
1286
+ }
1287
+ return symbols;
1288
+ }
1289
+ getContentHash(bundle) {
1290
+ let existingHash = this._bundleContentHashes.get(bundle.id);
1291
+ if (existingHash != null) {
1292
+ return existingHash;
1293
+ }
1294
+ let hash = new (_rust().Hash)();
1295
+ // TODO: sort??
1296
+ this.traverseAssets(bundle, asset => {
1297
+ {
1298
+ hash.writeString([this.getAssetPublicId(asset), asset.id, asset.outputHash].join(':'));
1299
+ }
1300
+ });
1301
+ let hashHex = hash.finish();
1302
+ this._bundleContentHashes.set(bundle.id, hashHex);
1303
+ return hashHex;
1304
+ }
1305
+ getInlineBundles(bundle) {
1306
+ let bundles = [];
1307
+ let seen = new Set();
1308
+ let addReferencedBundles = bundle => {
1309
+ if (seen.has(bundle.id)) {
1310
+ return;
1311
+ }
1312
+ seen.add(bundle.id);
1313
+ let referencedBundles = this.getReferencedBundles(bundle, {
1314
+ includeInline: true
1315
+ });
1316
+ for (let referenced of referencedBundles) {
1317
+ if (referenced.bundleBehavior === _types.BundleBehavior.inline) {
1318
+ bundles.push(referenced);
1319
+ addReferencedBundles(referenced);
1320
+ }
1321
+ }
1322
+ };
1323
+ addReferencedBundles(bundle);
1324
+ this.traverseBundles((childBundle, _, traversal) => {
1325
+ if (childBundle.bundleBehavior === _types.BundleBehavior.inline) {
1326
+ bundles.push(childBundle);
1327
+ } else if (childBundle.id !== bundle.id) {
1328
+ traversal.skipChildren();
1329
+ }
1330
+ }, bundle);
1331
+ return bundles;
1332
+ }
1333
+ getHash(bundle) {
1334
+ let hash = new (_rust().Hash)();
1335
+ hash.writeString(bundle.id + JSON.stringify(bundle.target) + this.getContentHash(bundle));
1336
+ if (bundle.isPlaceholder) {
1337
+ hash.writeString('placeholder');
1338
+ }
1339
+ let inlineBundles = this.getInlineBundles(bundle);
1340
+ for (let inlineBundle of inlineBundles) {
1341
+ hash.writeString(this.getContentHash(inlineBundle));
1342
+ }
1343
+ for (let referencedBundle of this.getReferencedBundles(bundle)) {
1344
+ hash.writeString(referencedBundle.id);
1345
+ }
1346
+ hash.writeString(JSON.stringify((0, _utils().objectSortedEntriesDeep)(bundle.env)));
1347
+ return hash.finish();
1348
+ }
1349
+ getBundleGraphHash() {
1350
+ let hashes = '';
1351
+ for (let bundle of this.getBundles()) {
1352
+ hashes += this.getHash(bundle);
1353
+ }
1354
+ return (0, _rust().hashString)(hashes);
1355
+ }
1356
+ addBundleToBundleGroup(bundle, bundleGroup) {
1357
+ let bundleGroupNodeId = this._graph.getNodeIdByContentKey((0, _utils2.getBundleGroupId)(bundleGroup));
1358
+ let bundleNodeId = this._graph.getNodeIdByContentKey(bundle.id);
1359
+ if (this._graph.hasEdge(bundleGroupNodeId, bundleNodeId, bundleGraphEdgeTypes.bundle)) {
1360
+ // Bundle group already has bundle
1361
+ return;
1362
+ }
1363
+ this._graph.addEdge(bundleGroupNodeId, bundleNodeId);
1364
+ this._graph.addEdge(bundleGroupNodeId, bundleNodeId, bundleGraphEdgeTypes.bundle);
1365
+ for (let entryAssetId of bundle.entryAssetIds) {
1366
+ let entryAssetNodeId = this._graph.getNodeIdByContentKey(entryAssetId);
1367
+ if (this._graph.hasEdge(bundleGroupNodeId, entryAssetNodeId)) {
1368
+ this._graph.removeEdge(bundleGroupNodeId, entryAssetNodeId);
1369
+ }
1370
+ }
1371
+ }
1372
+ getUsedSymbolsAsset(asset) {
1373
+ let node = this._graph.getNodeByContentKey(asset.id);
1374
+ (0, _assert().default)(node && node.type === 'asset');
1375
+ return node.value.symbols ? makeReadOnlySet(new Set(node.usedSymbols.keys())) : null;
1376
+ }
1377
+ getUsedSymbolsDependency(dep) {
1378
+ let node = this._graph.getNodeByContentKey(dep.id);
1379
+ (0, _assert().default)(node && node.type === 'dependency');
1380
+ return node.value.symbols ? makeReadOnlySet(new Set(node.usedSymbolsUp.keys())) : null;
1381
+ }
1382
+ merge(other) {
1383
+ let otherGraphIdToThisNodeId = new Map();
1384
+ for (let [otherNodeId, otherNode] of other._graph.nodes.entries()) {
1385
+ if (!otherNode) continue;
1386
+ if (this._graph.hasContentKey(otherNode.id)) {
1387
+ let existingNodeId = this._graph.getNodeIdByContentKey(otherNode.id);
1388
+ otherGraphIdToThisNodeId.set(otherNodeId, existingNodeId);
1389
+ let existingNode = (0, _nullthrows().default)(this._graph.getNode(existingNodeId));
1390
+ // Merge symbols, recompute dep.excluded based on that
1391
+ if (existingNode.type === 'asset') {
1392
+ (0, _assert().default)(otherNode.type === 'asset');
1393
+ existingNode.usedSymbols = new Set([...existingNode.usedSymbols, ...otherNode.usedSymbols]);
1394
+ } else if (existingNode.type === 'dependency') {
1395
+ (0, _assert().default)(otherNode.type === 'dependency');
1396
+ existingNode.usedSymbolsDown = new Set([...existingNode.usedSymbolsDown, ...otherNode.usedSymbolsDown]);
1397
+ existingNode.usedSymbolsUp = new Map([...existingNode.usedSymbolsUp, ...otherNode.usedSymbolsUp]);
1398
+ existingNode.excluded = (existingNode.excluded || Boolean(existingNode.hasDeferred)) && (otherNode.excluded || Boolean(otherNode.hasDeferred));
1399
+ }
1400
+ } else {
1401
+ let updateNodeId = this._graph.addNodeByContentKey(otherNode.id, otherNode);
1402
+ otherGraphIdToThisNodeId.set(otherNodeId, updateNodeId);
1403
+ }
1404
+ }
1405
+ for (let edge of other._graph.getAllEdges()) {
1406
+ this._graph.addEdge((0, _nullthrows().default)(otherGraphIdToThisNodeId.get(edge.from)), (0, _nullthrows().default)(otherGraphIdToThisNodeId.get(edge.to)), edge.type);
1407
+ }
1408
+ }
1409
+ isEntryBundleGroup(bundleGroup) {
1410
+ return this._graph.getNodeIdsConnectedTo((0, _nullthrows().default)(this._graph.getNodeIdByContentKey((0, _utils2.getBundleGroupId)(bundleGroup))), bundleGraphEdgeTypes.bundle).map(id => (0, _nullthrows().default)(this._graph.getNode(id))).some(n => n.type === 'root');
1411
+ }
1412
+
1413
+ /**
1414
+ * Update the asset in a Bundle Graph and clear the associated Bundle hash.
1415
+ */
1416
+ updateAsset(asset) {
1417
+ this._graph.updateNode(this._graph.getNodeIdByContentKey(asset.id), asset);
1418
+ let bundles = this.getBundlesWithAsset(asset.value);
1419
+ for (let bundle of bundles) {
1420
+ // the bundle content will change with a modified asset
1421
+ this._bundleContentHashes.delete(bundle.id);
1422
+ }
1423
+ }
1424
+ getEntryRoot(projectRoot, target) {
1425
+ let cached = this._targetEntryRoots.get(target.distDir);
1426
+ if (cached != null) {
1427
+ return cached;
1428
+ }
1429
+ let entryBundleGroupIds = this._graph.getNodeIdsConnectedFrom((0, _nullthrows().default)(this._graph.rootNodeId), bundleGraphEdgeTypes.bundle);
1430
+ let entries = [];
1431
+ for (let bundleGroupId of entryBundleGroupIds) {
1432
+ let bundleGroupNode = this._graph.getNode(bundleGroupId);
1433
+ (0, _assert().default)((bundleGroupNode === null || bundleGroupNode === void 0 ? void 0 : bundleGroupNode.type) === 'bundle_group');
1434
+ if (bundleGroupNode.value.target.distDir === target.distDir) {
1435
+ let entryAssetNode = this._graph.getNodeByContentKey(bundleGroupNode.value.entryAssetId);
1436
+ (0, _assert().default)((entryAssetNode === null || entryAssetNode === void 0 ? void 0 : entryAssetNode.type) === 'asset');
1437
+ entries.push((0, _projectPath.fromProjectPath)(projectRoot, entryAssetNode.value.filePath));
1438
+ }
1439
+ }
1440
+ let root = (0, _utils().getRootDir)(entries);
1441
+ this._targetEntryRoots.set(target.distDir, root);
1442
+ return root;
1443
+ }
1444
+ }
1445
+ exports.default = BundleGraph;