@jsenv/core 36.3.1 → 37.0.0

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 (64) hide show
  1. package/dist/js/autoreload.js +6 -5
  2. package/dist/js/import_meta_hot.js +4 -4
  3. package/dist/js/server_events_client.js +422 -304
  4. package/dist/jsenv_core.js +3819 -3256
  5. package/package.json +16 -16
  6. package/src/build/build.js +342 -658
  7. package/src/build/build_urls_generator.js +8 -8
  8. package/src/build/build_versions_manager.js +495 -0
  9. package/src/build/version_mappings_injection.js +27 -16
  10. package/src/dev/file_service.js +80 -91
  11. package/src/dev/start_dev_server.js +5 -3
  12. package/src/kitchen/errors.js +16 -16
  13. package/src/kitchen/fetched_content_compliance.js +4 -8
  14. package/src/kitchen/kitchen.js +367 -939
  15. package/src/kitchen/prepend_content.js +13 -35
  16. package/src/kitchen/url_graph/references.js +713 -0
  17. package/src/kitchen/url_graph/sort_by_dependencies.js +2 -2
  18. package/src/kitchen/url_graph/url_content.js +96 -0
  19. package/src/kitchen/url_graph/url_graph.js +439 -0
  20. package/src/kitchen/url_graph/url_graph_report.js +6 -4
  21. package/src/kitchen/url_graph/url_graph_visitor.js +14 -12
  22. package/src/kitchen/url_graph/url_info_transformations.js +180 -184
  23. package/src/plugins/autoreload/client/autoreload.js +1 -0
  24. package/src/plugins/autoreload/client/reload.js +6 -6
  25. package/src/plugins/autoreload/jsenv_plugin_autoreload.js +2 -2
  26. package/src/plugins/autoreload/jsenv_plugin_autoreload_client.js +2 -2
  27. package/src/plugins/autoreload/jsenv_plugin_autoreload_server.js +84 -78
  28. package/src/plugins/autoreload/jsenv_plugin_hot_search_param.js +52 -0
  29. package/src/plugins/cache_control/jsenv_plugin_cache_control.js +1 -1
  30. package/src/plugins/commonjs_globals/jsenv_plugin_commonjs_globals.js +2 -2
  31. package/src/plugins/global_scenarios/jsenv_plugin_global_scenarios.js +3 -3
  32. package/src/plugins/import_meta_hot/client/import_meta_hot.js +4 -4
  33. package/src/plugins/import_meta_hot/jsenv_plugin_import_meta_hot.js +18 -20
  34. package/src/plugins/import_meta_scenarios/jsenv_plugin_import_meta_scenarios.js +2 -2
  35. package/src/plugins/importmap/jsenv_plugin_importmap.js +35 -37
  36. package/src/plugins/inlining/jsenv_plugin_inlining.js +1 -17
  37. package/src/plugins/inlining/jsenv_plugin_inlining_as_data_url.js +70 -50
  38. package/src/plugins/inlining/jsenv_plugin_inlining_into_html.js +72 -54
  39. package/src/plugins/plugin_controller.js +92 -27
  40. package/src/plugins/protocol_file/jsenv_plugin_protocol_file.js +18 -20
  41. package/src/plugins/reference_analysis/css/jsenv_plugin_css_reference_analysis.js +4 -5
  42. package/src/plugins/reference_analysis/data_urls/jsenv_plugin_data_urls_analysis.js +18 -16
  43. package/src/plugins/reference_analysis/directory/jsenv_plugin_directory_reference_analysis.js +13 -20
  44. package/src/plugins/reference_analysis/html/jsenv_plugin_html_reference_analysis.js +55 -72
  45. package/src/plugins/reference_analysis/js/jsenv_plugin_js_reference_analysis.js +33 -42
  46. package/src/plugins/reference_analysis/jsenv_plugin_reference_analysis.js +16 -7
  47. package/src/plugins/reference_analysis/webmanifest/jsenv_plugin_webmanifest_reference_analysis.js +4 -3
  48. package/src/plugins/resolution_node_esm/jsenv_plugin_node_esm_resolution.js +16 -6
  49. package/src/plugins/resolution_node_esm/node_esm_resolver.js +30 -24
  50. package/src/plugins/resolution_web/jsenv_plugin_web_resolution.js +8 -5
  51. package/src/plugins/ribbon/jsenv_plugin_ribbon.js +3 -3
  52. package/src/plugins/server_events/client/server_events_client.js +460 -15
  53. package/src/plugins/server_events/jsenv_plugin_server_events_client_injection.js +13 -29
  54. package/src/plugins/version_search_param/jsenv_plugin_version_search_param.js +1 -1
  55. package/src/build/version_generator.js +0 -19
  56. package/src/kitchen/url_graph/url_graph_loader.js +0 -77
  57. package/src/kitchen/url_graph.js +0 -322
  58. package/src/plugins/autoreload/jsenv_plugin_hmr.js +0 -42
  59. package/src/plugins/resolution_node_esm/url_type_from_reference.js +0 -13
  60. package/src/plugins/server_events/client/connection_manager.js +0 -170
  61. package/src/plugins/server_events/client/event_source_connection.js +0 -83
  62. package/src/plugins/server_events/client/events_manager.js +0 -75
  63. package/src/plugins/server_events/client/web_socket_connection.js +0 -81
  64. /package/src/kitchen/{url_specifier_encoding.js → url_graph/url_specifier_encoding.js} +0 -0
@@ -1,13 +1,11 @@
1
1
  import { readFileSync } from "node:fs";
2
2
  import { serveDirectory, composeTwoResponses } from "@jsenv/server";
3
3
  import { bufferToEtag } from "@jsenv/filesystem";
4
- import { asUrlWithoutSearch } from "@jsenv/urls";
5
4
  import { URL_META } from "@jsenv/url-meta";
6
5
  import { RUNTIME_COMPAT } from "@jsenv/runtime-compat";
7
6
 
8
7
  import { WEB_URL_CONVERTER } from "../helpers/web_url_converter.js";
9
8
  import { watchSourceFiles } from "../helpers/watch_source_files.js";
10
- import { createUrlGraph } from "../kitchen/url_graph.js";
11
9
  import { createKitchen } from "../kitchen/kitchen.js";
12
10
  import { getCorePlugins } from "../plugins/plugins.js";
13
11
  import { jsenvPluginServerEventsClientInjection } from "../plugins/server_events/jsenv_plugin_server_events_client_injection.js";
@@ -18,7 +16,7 @@ export const createFileService = ({
18
16
  logLevel,
19
17
  serverStopCallbacks,
20
18
  serverEventsDispatcher,
21
- contextCache,
19
+ kitchenCache,
22
20
 
23
21
  sourceDirectoryUrl,
24
22
  sourceMainFilePath,
@@ -35,6 +33,7 @@ export const createFileService = ({
35
33
  transpilation,
36
34
  clientAutoreload,
37
35
  cooldownBetweenFileEvents,
36
+ clientServerEventsConfig,
38
37
  cacheControl,
39
38
  ribbon,
40
39
  sourcemaps,
@@ -59,47 +58,35 @@ export const createFileService = ({
59
58
  );
60
59
  serverStopCallbacks.push(stopWatchingSourceFiles);
61
60
 
62
- const getOrCreateContext = (request) => {
61
+ const getOrCreateKitchen = (request) => {
63
62
  const { runtimeName, runtimeVersion } = parseUserAgentHeader(
64
63
  request.headers["user-agent"] || "",
65
64
  );
66
65
  const runtimeId = `${runtimeName}@${runtimeVersion}`;
67
- const existingContext = contextCache.get(runtimeId);
68
- if (existingContext) {
69
- return existingContext;
66
+ const existing = kitchenCache.get(runtimeId);
67
+ if (existing) {
68
+ return existing;
70
69
  }
71
70
  const watchAssociations = URL_META.resolveAssociations(
72
71
  { watch: stopWatchingSourceFiles.watchPatterns },
73
72
  sourceDirectoryUrl,
74
73
  );
75
- const urlGraph = createUrlGraph({
76
- name: runtimeId,
77
- });
74
+ let kitchen;
78
75
  clientFileChangeCallbackList.push(({ url }) => {
79
- const onUrlInfo = (urlInfo) => {
80
- urlGraph.considerModified(urlInfo);
81
- };
82
- const exactUrlInfo = urlGraph.getUrlInfo(url);
83
- if (exactUrlInfo) {
84
- onUrlInfo(exactUrlInfo);
76
+ const urlInfo = kitchen.graph.getUrlInfo(url);
77
+ if (urlInfo) {
78
+ urlInfo.considerModified();
85
79
  }
86
- urlGraph.urlInfoMap.forEach((urlInfo) => {
87
- if (urlInfo === exactUrlInfo) return;
88
- const urlWithoutSearch = asUrlWithoutSearch(urlInfo.url);
89
- if (urlWithoutSearch !== url) return;
90
- if (exactUrlInfo && exactUrlInfo.dependents.has(urlInfo.url)) return;
91
- onUrlInfo(urlInfo);
92
- });
93
80
  });
94
81
  const clientRuntimeCompat = { [runtimeName]: runtimeVersion };
95
82
 
96
- const kitchen = createKitchen({
83
+ kitchen = createKitchen({
84
+ name: runtimeId,
97
85
  signal,
98
86
  logLevel,
99
87
  rootDirectoryUrl: sourceDirectoryUrl,
100
88
  mainFilePath: sourceMainFilePath,
101
89
  ignore,
102
- urlGraph,
103
90
  dev: true,
104
91
  runtimeCompat,
105
92
  clientRuntimeCompat,
@@ -139,48 +126,54 @@ export const createFileService = ({
139
126
  ? new URL(`${runtimeName}@${runtimeVersion}/`, outDirectoryUrl)
140
127
  : undefined,
141
128
  });
142
- urlGraph.createUrlInfoCallbackRef.current = (urlInfo) => {
129
+ kitchen.graph.createUrlInfoCallbackRef.current = (urlInfo) => {
143
130
  const { watch } = URL_META.applyAssociations({
144
131
  url: urlInfo.url,
145
132
  associations: watchAssociations,
146
133
  });
147
134
  urlInfo.isWatched = watch;
148
- // si une urlInfo dépends de pleins d'autres alors
149
- // on voudrait check chacune de ces url infos (package.json dans mon cas)
135
+ // wehn an url depends on many others, we check all these (like package.json)
150
136
  urlInfo.isValid = () => {
151
137
  if (!urlInfo.url.startsWith("file:")) {
152
138
  return false;
153
139
  }
154
- if (watch && urlInfo.contentEtag === undefined) {
155
- // we trust the watching mecanism
156
- // doing urlInfo.contentEtag = undefined
157
- // when file is modified
140
+ if (urlInfo.content === undefined) {
141
+ // urlInfo content is undefined when:
142
+ // - url info content never fetched
143
+ // - it is considered as modified because undelying file is watched and got saved
144
+ // - it is considered as modified because underlying file content
145
+ // was compared using etag and it has changed
158
146
  return false;
159
147
  }
160
- if (!watch && urlInfo.contentEtag) {
148
+ if (!watch) {
161
149
  // file is not watched, check the filesystem
162
150
  let fileContentAsBuffer;
163
151
  try {
164
152
  fileContentAsBuffer = readFileSync(new URL(urlInfo.url));
165
153
  } catch (e) {
166
154
  if (e.code === "ENOENT") {
167
- // we should consider calling urlGraph.deleteUrlInfo(urlInfo)
168
- urlInfo.originalContentEtag = undefined;
169
- urlInfo.contentEtag = undefined;
155
+ urlInfo.considerModified();
156
+ urlInfo.deleteFromGraph();
170
157
  return false;
171
158
  }
172
159
  return false;
173
160
  }
174
161
  const fileContentEtag = bufferToEtag(fileContentAsBuffer);
175
162
  if (fileContentEtag !== urlInfo.originalContentEtag) {
176
- // we should consider calling urlGraph.considerModified(urlInfo)
177
- urlInfo.originalContentEtag = undefined;
178
- urlInfo.contentEtag = undefined;
163
+ urlInfo.considerModified();
164
+ // restore content to be able to compare it again later
165
+ urlInfo.kitchen.urlInfoTransformer.setContent(
166
+ urlInfo,
167
+ String(fileContentAsBuffer),
168
+ {
169
+ contentEtag: fileContentEtag,
170
+ },
171
+ );
179
172
  return false;
180
173
  }
181
174
  }
182
- for (const implicitUrl of urlInfo.implicitUrls) {
183
- const implicitUrlInfo = context.urlGraph.getUrlInfo(implicitUrl);
175
+ for (const implicitUrl of urlInfo.implicitUrlSet) {
176
+ const implicitUrlInfo = kitchen.graph.getUrlInfo(implicitUrl);
184
177
  if (implicitUrlInfo && !implicitUrlInfo.isValid()) {
185
178
  return false;
186
179
  }
@@ -188,13 +181,16 @@ export const createFileService = ({
188
181
  return true;
189
182
  };
190
183
  };
191
- urlGraph.prunedUrlInfosCallbackRef.current = (urlInfos, firstUrlInfo) => {
184
+ kitchen.graph.pruneUrlInfoCallbackRef.current = (
185
+ prunedUrlInfo,
186
+ lastReferenceFromOther,
187
+ ) => {
192
188
  clientFilesPruneCallbackList.forEach((callback) => {
193
- callback(urlInfos, firstUrlInfo);
189
+ callback(prunedUrlInfo, lastReferenceFromOther);
194
190
  });
195
191
  };
196
192
  serverStopCallbacks.push(() => {
197
- kitchen.pluginController.callHooks("destroy", kitchen.kitchenContext);
193
+ kitchen.pluginController.callHooks("destroy", kitchen.context);
198
194
  });
199
195
  server_events: {
200
196
  const allServerEvents = {};
@@ -211,44 +207,39 @@ export const createFileService = ({
211
207
  const serverEventNames = Object.keys(allServerEvents);
212
208
  if (serverEventNames.length > 0) {
213
209
  Object.keys(allServerEvents).forEach((serverEventName) => {
214
- allServerEvents[serverEventName]({
215
- rootDirectoryUrl: sourceDirectoryUrl,
216
- urlGraph,
217
- dev: true,
210
+ const serverEventInfo = {
211
+ ...kitchen.context,
218
212
  sendServerEvent: (data) => {
219
213
  serverEventsDispatcher.dispatch({
220
214
  type: serverEventName,
221
215
  data,
222
216
  });
223
217
  },
224
- });
218
+ };
219
+ const serverEventInit = allServerEvents[serverEventName];
220
+ serverEventInit(serverEventInfo);
225
221
  });
226
222
  // "pushPlugin" so that event source client connection can be put as early as possible in html
227
223
  kitchen.pluginController.pushPlugin(
228
- jsenvPluginServerEventsClientInjection(),
224
+ jsenvPluginServerEventsClientInjection(clientServerEventsConfig),
229
225
  );
230
226
  }
231
227
  }
232
228
 
233
- const context = {
234
- rootDirectoryUrl: sourceDirectoryUrl,
235
- dev: true,
236
- runtimeName,
237
- runtimeVersion,
238
- urlGraph,
239
- kitchen,
240
- };
241
- contextCache.set(runtimeId, context);
242
- return context;
229
+ kitchenCache.set(runtimeId, kitchen);
230
+ return kitchen;
243
231
  };
244
232
 
245
233
  return async (request) => {
246
- const { urlGraph, kitchen } = getOrCreateContext(request);
234
+ const kitchen = getOrCreateKitchen(request);
235
+ const serveHookInfo = {
236
+ ...kitchen.context,
237
+ request,
238
+ };
247
239
  const responseFromPlugin =
248
240
  await kitchen.pluginController.callAsyncHooksUntil(
249
241
  "serve",
250
- request,
251
- kitchen.kitchenContext,
242
+ serveHookInfo,
252
243
  );
253
244
  if (responseFromPlugin) {
254
245
  return responseFromPlugin;
@@ -260,20 +251,25 @@ export const createFileService = ({
260
251
  sourceMainFilePath,
261
252
  );
262
253
  if (parentUrl) {
263
- reference = urlGraph.inferReference(request.resource, parentUrl);
254
+ reference = kitchen.graph.inferReference(request.resource, parentUrl);
264
255
  }
265
256
  if (!reference) {
266
- const entryPoint = kitchen.injectReference({
257
+ let parentUrlInfo;
258
+ if (parentUrl) {
259
+ parentUrlInfo = kitchen.graph.getUrlInfo(parentUrl);
260
+ }
261
+ if (!parentUrlInfo) {
262
+ parentUrlInfo = kitchen.graph.rootUrlInfo;
263
+ }
264
+ reference = parentUrlInfo.dependencies.createResolveAndFinalize({
267
265
  trace: { message: parentUrl || sourceDirectoryUrl },
268
- parentUrl: parentUrl || sourceDirectoryUrl,
269
266
  type: "http_request",
270
267
  specifier: request.resource,
271
268
  });
272
- reference = entryPoint[0];
273
269
  }
274
- const urlInfo = urlGraph.reuseOrCreateUrlInfo(reference.url);
270
+ const urlInfo = reference.urlInfo;
275
271
  const ifNoneMatch = request.headers["if-none-match"];
276
- const urlInfoTargetedByCache = urlGraph.getParentIfInline(urlInfo);
272
+ const urlInfoTargetedByCache = urlInfo.findParentIfInline() || urlInfo;
277
273
 
278
274
  try {
279
275
  if (ifNoneMatch) {
@@ -300,26 +296,7 @@ export const createFileService = ({
300
296
  }
301
297
  }
302
298
 
303
- // urlInfo objects are reused, they must be "reset" before cooking them again
304
- if (
305
- (urlInfo.error || urlInfo.contentEtag) &&
306
- !urlInfo.isInline &&
307
- urlInfo.type !== "sourcemap"
308
- ) {
309
- urlInfo.error = null;
310
- urlInfo.sourcemap = null;
311
- urlInfo.sourcemapIsWrong = null;
312
- urlInfo.sourcemapReference = null;
313
- urlInfo.content = null;
314
- urlInfo.originalContent = null;
315
- urlInfo.type = null;
316
- urlInfo.subtype = null;
317
- urlInfo.timing = {};
318
- }
319
- await kitchen.cook(urlInfo, {
320
- request,
321
- reference,
322
- });
299
+ await urlInfo.cook({ request, reference });
323
300
  let { response } = urlInfo;
324
301
  if (response) {
325
302
  return response;
@@ -348,10 +325,14 @@ export const createFileService = ({
348
325
  body: urlInfo.content,
349
326
  timing: urlInfo.timing,
350
327
  };
328
+ const augmentResponseInfo = {
329
+ ...kitchen.context,
330
+ reference,
331
+ urlInfo,
332
+ };
351
333
  kitchen.pluginController.callHooks(
352
334
  "augmentResponse",
353
- { reference, urlInfo },
354
- kitchen.kitchenContext,
335
+ augmentResponseInfo,
355
336
  (returnValue) => {
356
337
  response = composeTwoResponses(response, returnValue);
357
338
  },
@@ -425,6 +406,14 @@ export const createFileService = ({
425
406
  statusText: e.reason,
426
407
  statusMessage: e.stack,
427
408
  };
409
+ } finally {
410
+ // remove http_request when there is other references keeping url info alive
411
+ if (
412
+ reference.type === "http_request" &&
413
+ reference.urlInfo.referenceFromOthersSet.size > 1
414
+ ) {
415
+ reference.remove();
416
+ }
428
417
  }
429
418
  };
430
419
  };
@@ -45,6 +45,7 @@ export const startDevServer = async ({
45
45
  sourceFilesConfig,
46
46
  clientAutoreload = true,
47
47
  cooldownBetweenFileEvents,
48
+ clientServerEventsConfig = {},
48
49
 
49
50
  // runtimeCompat is the runtimeCompat for the build
50
51
  // when specified, dev server use it to warn in case
@@ -121,7 +122,7 @@ export const startDevServer = async ({
121
122
  serverStopCallbacks.push(() => {
122
123
  serverEventsDispatcher.destroy();
123
124
  });
124
- const contextCache = new Map();
125
+ const kitchenCache = new Map();
125
126
  const server = await startServer({
126
127
  signal,
127
128
  stopOnExit: false,
@@ -183,7 +184,7 @@ export const startDevServer = async ({
183
184
  logLevel,
184
185
  serverStopCallbacks,
185
186
  serverEventsDispatcher,
186
- contextCache,
187
+ kitchenCache,
187
188
 
188
189
  sourceDirectoryUrl,
189
190
  sourceMainFilePath,
@@ -200,6 +201,7 @@ export const startDevServer = async ({
200
201
  transpilation,
201
202
  clientAutoreload,
202
203
  cooldownBetweenFileEvents,
204
+ clientServerEventsConfig,
203
205
  cacheControl,
204
206
  ribbon,
205
207
  sourcemaps,
@@ -278,6 +280,6 @@ export const startDevServer = async ({
278
280
  stop: () => {
279
281
  server.stop();
280
282
  },
281
- contextCache,
283
+ kitchenCache,
282
284
  };
283
285
  };
@@ -46,7 +46,6 @@ export const createResolveUrlError = ({
46
46
 
47
47
  export const createFetchUrlContentError = ({
48
48
  pluginController,
49
- reference,
50
49
  urlInfo,
51
50
  error,
52
51
  }) => {
@@ -60,7 +59,7 @@ export const createFetchUrlContentError = ({
60
59
  reason,
61
60
  ...details,
62
61
  "url": urlInfo.url,
63
- "url reference trace": reference.trace.message,
62
+ "url reference trace": urlInfo.firstReference.trace.message,
64
63
  ...detailsFromPluginController(pluginController),
65
64
  }),
66
65
  );
@@ -74,10 +73,10 @@ export const createFetchUrlContentError = ({
74
73
  fetchError.traceColumn = error.traceColumn;
75
74
  fetchError.traceMessage = error.traceMessage;
76
75
  } else {
77
- fetchError.traceUrl = reference.trace.url;
78
- fetchError.traceLine = reference.trace.line;
79
- fetchError.traceColumn = reference.trace.column;
80
- fetchError.traceMessage = reference.trace.message;
76
+ fetchError.traceUrl = urlInfo.firstReference.trace.url;
77
+ fetchError.traceLine = urlInfo.firstReference.trace.line;
78
+ fetchError.traceColumn = urlInfo.firstReference.trace.column;
79
+ fetchError.traceMessage = urlInfo.firstReference.trace.message;
81
80
  }
82
81
  fetchError.asResponse = error.asResponse;
83
82
  return fetchError;
@@ -123,7 +122,6 @@ export const createFetchUrlContentError = ({
123
122
 
124
123
  export const createTransformUrlContentError = ({
125
124
  pluginController,
126
- reference,
127
125
  urlInfo,
128
126
  error,
129
127
  }) => {
@@ -142,7 +140,7 @@ export const createTransformUrlContentError = ({
142
140
  reason,
143
141
  ...details,
144
142
  "url": urlInfo.url,
145
- "url reference trace": reference.trace.message,
143
+ "url reference trace": urlInfo.firstReference.trace.message,
146
144
  ...detailsFromPluginController(pluginController),
147
145
  },
148
146
  ),
@@ -152,16 +150,18 @@ export const createTransformUrlContentError = ({
152
150
  transformError.reason = reason;
153
151
  transformError.stack = error.stack;
154
152
  transformError.url = urlInfo.url;
155
- transformError.traceUrl = reference.trace.url;
156
- transformError.traceLine = reference.trace.line;
157
- transformError.traceColumn = reference.trace.column;
158
- transformError.traceMessage = reference.trace.message;
153
+ transformError.traceUrl = urlInfo.firstReference.trace.url;
154
+ transformError.traceLine = urlInfo.firstReference.trace.line;
155
+ transformError.traceColumn = urlInfo.firstReference.trace.column;
156
+ transformError.traceMessage = urlInfo.firstReference.trace.message;
159
157
  if (code === "PARSE_ERROR") {
160
158
  transformError.reason = `parse error on ${urlInfo.type}`;
161
159
  transformError.cause = error;
162
160
  if (urlInfo.isInline) {
163
- transformError.traceLine = reference.trace.line + error.line - 1;
164
- transformError.traceColumn = reference.trace.column + error.column;
161
+ transformError.traceLine =
162
+ urlInfo.firstReference.trace.line + error.line - 1;
163
+ transformError.traceColumn =
164
+ urlInfo.firstReference.trace.column + error.column;
165
165
  transformError.traceMessage = stringifyUrlSite({
166
166
  url: urlInfo.inlineUrlSite.url,
167
167
  line: transformError.traceLine,
@@ -190,7 +190,7 @@ export const createTransformUrlContentError = ({
190
190
 
191
191
  export const createFinalizeUrlContentError = ({
192
192
  pluginController,
193
- reference,
193
+
194
194
  urlInfo,
195
195
  error,
196
196
  }) => {
@@ -198,7 +198,7 @@ export const createFinalizeUrlContentError = ({
198
198
  createDetailedMessage(`"finalizeUrlContent" error on "${urlInfo.type}"`, {
199
199
  ...detailsFromValueThrown(error),
200
200
  "url": urlInfo.url,
201
- "url reference trace": reference.trace.message,
201
+ "url reference trace": urlInfo.firstReference.trace.message,
202
202
  ...detailsFromPluginController(pluginController),
203
203
  }),
204
204
  );
@@ -1,23 +1,19 @@
1
1
  import { validateResponseIntegrity } from "@jsenv/integrity";
2
2
 
3
- export const assertFetchedContentCompliance = ({
4
- reference,
5
- urlInfo,
6
- content,
7
- }) => {
8
- const { expectedContentType } = reference;
3
+ export const assertFetchedContentCompliance = ({ urlInfo, content }) => {
4
+ const { expectedContentType } = urlInfo.firstReference;
9
5
  if (expectedContentType && urlInfo.contentType !== expectedContentType) {
10
6
  throw new Error(
11
7
  `Unexpected content-type on url: "${expectedContentType}" was expected but got "${urlInfo.contentType}`,
12
8
  );
13
9
  }
14
- const { expectedType } = reference;
10
+ const { expectedType } = urlInfo.firstReference;
15
11
  if (expectedType && urlInfo.type !== expectedType) {
16
12
  throw new Error(
17
13
  `Unexpected type on url: "${expectedType}" was expected but got "${urlInfo.type}"`,
18
14
  );
19
15
  }
20
- const { integrity } = reference;
16
+ const { integrity } = urlInfo.firstReference;
21
17
  if (integrity) {
22
18
  validateResponseIntegrity({
23
19
  url: urlInfo.url,