veryfront 0.1.72 → 0.1.73
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.
- package/esm/deno.js +1 -1
- package/esm/src/html/html-shell-generator.d.ts.map +1 -1
- package/esm/src/html/html-shell-generator.js +6 -0
- package/esm/src/rendering/orchestrator/pipeline.d.ts.map +1 -1
- package/esm/src/rendering/orchestrator/pipeline.js +116 -105
- package/esm/src/server/dev-server/error-overlay/error-formatter.d.ts +4 -0
- package/esm/src/server/dev-server/error-overlay/error-formatter.d.ts.map +1 -1
- package/esm/src/server/dev-server/error-overlay/error-formatter.js +15 -0
- package/esm/src/server/dev-server/error-overlay/html-template.d.ts +1 -1
- package/esm/src/server/dev-server/error-overlay/html-template.d.ts.map +1 -1
- package/esm/src/server/dev-server/error-overlay/html-template.js +131 -8
- package/esm/src/server/dev-server/error-overlay/index.d.ts +1 -1
- package/esm/src/server/dev-server/error-overlay/index.d.ts.map +1 -1
- package/esm/src/server/dev-server/error-overlay/index.js +1 -1
- package/esm/src/server/dev-server/error-overlay/overlay-renderer.d.ts +1 -1
- package/esm/src/server/dev-server/error-overlay/overlay-renderer.d.ts.map +1 -1
- package/esm/src/server/dev-server/error-overlay/overlay-renderer.js +2 -2
- package/esm/src/server/dev-server/request-handler.d.ts.map +1 -1
- package/esm/src/server/dev-server/request-handler.js +6 -2
- package/esm/src/server/services/rendering/ssr.service.d.ts.map +1 -1
- package/esm/src/server/services/rendering/ssr.service.js +9 -2
- package/esm/src/server/utils/error-html.d.ts.map +1 -1
- package/esm/src/server/utils/error-html.js +26 -6
- package/package.json +1 -1
- package/src/deno.js +1 -1
- package/src/src/html/html-shell-generator.ts +9 -0
- package/src/src/rendering/orchestrator/pipeline.ts +186 -172
- package/src/src/server/dev-server/error-overlay/error-formatter.ts +21 -0
- package/src/src/server/dev-server/error-overlay/html-template.ts +139 -8
- package/src/src/server/dev-server/error-overlay/index.ts +1 -0
- package/src/src/server/dev-server/error-overlay/overlay-renderer.ts +2 -1
- package/src/src/server/dev-server/request-handler.ts +6 -2
- package/src/src/server/services/rendering/ssr.service.ts +9 -2
- package/src/src/server/utils/error-html.ts +29 -6
package/esm/deno.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"html-shell-generator.d.ts","sourceRoot":"","sources":["../../../src/src/html/html-shell-generator.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,cAAc,EAAE,cAAc,EAAE,MAAM,mBAAmB,CAAC;AAmBxE,OAAO,KAAK,EAAE,qBAAqB,EAAE,MAAM,YAAY,CAAC;AA+ExD,wBAAgB,sBAAsB,CACpC,IAAI,EAAE,cAAc,EACpB,OAAO,EAAE,qBAAqB,EAC9B,MAAM,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,EAAE,CAAC,EAC1C,KAAK,CAAC,EAAE,cAAc,EACtB,kBAAkB,CAAC,EAAE,MAAM,GAC1B,OAAO,CAAC;IAAE,KAAK,EAAE,MAAM,CAAC;IAAC,GAAG,EAAE,MAAM,CAAA;CAAE,CAAC,CAWzC;
|
|
1
|
+
{"version":3,"file":"html-shell-generator.d.ts","sourceRoot":"","sources":["../../../src/src/html/html-shell-generator.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,cAAc,EAAE,cAAc,EAAE,MAAM,mBAAmB,CAAC;AAmBxE,OAAO,KAAK,EAAE,qBAAqB,EAAE,MAAM,YAAY,CAAC;AA+ExD,wBAAgB,sBAAsB,CACpC,IAAI,EAAE,cAAc,EACpB,OAAO,EAAE,qBAAqB,EAC9B,MAAM,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,EAAE,CAAC,EAC1C,KAAK,CAAC,EAAE,cAAc,EACtB,kBAAkB,CAAC,EAAE,MAAM,GAC1B,OAAO,CAAC;IAAE,KAAK,EAAE,MAAM,CAAC;IAAC,GAAG,EAAE,MAAM,CAAA;CAAE,CAAC,CAWzC;AA+PD,wBAAgB,eAAe,CAC7B,OAAO,EAAE,MAAM,EACf,IAAI,EAAE,cAAc,EACpB,OAAO,EAAE,qBAAqB,EAC9B,MAAM,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,EAAE,CAAC,EAC1C,KAAK,CAAC,EAAE,cAAc,GACrB,OAAO,CAAC,MAAM,CAAC,CAmBjB"}
|
|
@@ -134,6 +134,11 @@ async function generateHTMLShellPartsImpl(meta, options, params, props, contentF
|
|
|
134
134
|
? `<link rel="modulepreload" href="${jsxRuntimeUrl}">`
|
|
135
135
|
: "";
|
|
136
136
|
const nonceAttr = nonce ? ` nonce="${nonce}"` : "";
|
|
137
|
+
// Expose project slug for runtime error overlay "Fix in Veryfront" button
|
|
138
|
+
const overlaySlug = options.projectId || meta.slug;
|
|
139
|
+
const slugForOverlay = useDevScripts && overlaySlug
|
|
140
|
+
? `<script${nonceAttr}>window.__VF_PROJECT_SLUG__=${JSON.stringify(overlaySlug).replace(/</g, "\\u003c")};</script>`
|
|
141
|
+
: "";
|
|
137
142
|
const hydrationErrorSuppression = useDevScripts ? "" : `<script${nonceAttr}>
|
|
138
143
|
(function(){
|
|
139
144
|
var origError = console.error;
|
|
@@ -222,6 +227,7 @@ async function generateHTMLShellPartsImpl(meta, options, params, props, contentF
|
|
|
222
227
|
${linkTags}
|
|
223
228
|
${styleTags}
|
|
224
229
|
${modeStyles}
|
|
230
|
+
${slugForOverlay}
|
|
225
231
|
</head>
|
|
226
232
|
<body${bodyClass ? ` class="${bodyClass}"` : ""} suppressHydrationWarning>
|
|
227
233
|
<div ${rootAttributes}>`;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"pipeline.d.ts","sourceRoot":"","sources":["../../../../src/src/rendering/orchestrator/pipeline.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;GAcG;AAgBH,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,iCAAiC,CAAC;AAEtE,OAAO,KAAK,EAAE,iBAAiB,EAAE,MAAM,+BAA+B,CAAC;AACvE,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,qBAAqB,CAAC;AACxD,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,6BAA6B,CAAC;AAChE,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,aAAa,CAAC;AACtD,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,uBAAuB,CAAC;AAC7D,OAAO,KAAK,EAAE,gBAAgB,EAAE,aAAa,EAAE,YAAY,EAAE,MAAM,YAAY,CAAC;AA6ChF,OAAO,EAAE,wBAAwB,EAAE,MAAM,gBAAgB,CAAC;AAE1D;;;;GAIG;AACH,MAAM,WAAW,wBAAwB;IACvC,UAAU,CAAC,IAAI,EAAE,MAAM,EAAE,QAAQ,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,iBAAiB,CAAC,CAAC;IACxE,aAAa,CAAC,MAAM,EAAE,YAAY,EAAE,IAAI,EAAE,MAAM,EAAE,QAAQ,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;CACrF;AAED,MAAM,WAAW,oBAAoB;IACnC,YAAY,EAAE,YAAY,CAAC;IAC3B,gBAAgB,EAAE,wBAAwB,CAAC;IAC3C,YAAY,EAAE,YAAY,CAAC;IAC3B,kBAAkB,EAAE,kBAAkB,CAAC;IACvC,eAAe,EAAE,eAAe,CAAC;IACjC,OAAO,EAAE,cAAc,CAAC;IACxB,IAAI,EAAE,aAAa,GAAG,YAAY,CAAC;IACnC,UAAU,EAAE,MAAM,CAAC;IACnB,8EAA8E;IAC9E,iBAAiB,CAAC,EAAE,OAAO,qBAAqB,EAAE,sBAAsB,CAAC;CAC1E;AAQD,qBAAa,cAAc;IACzB,OAAO,CAAC,MAAM,CAAuB;IACrC,OAAO,CAAC,WAAW,CAAc;IACjC,OAAO,CAAC,kBAAkB,CAAqB;gBAEnC,MAAM,EAAE,oBAAoB;IAaxC;;;OAGG;IACH,gBAAgB,IAAI,IAAI;IAKxB,OAAO,CAAC,UAAU;IAIlB,OAAO,CAAC,sBAAsB;YAIhB,0BAA0B;IAaxC;;;;;;;;;OASG;YACW,qBAAqB;IAyDnC;;;OAGG;YACW,mBAAmB;IAqH3B,UAAU,CAAC,IAAI,EAAE,MAAM,EAAE,OAAO,CAAC,EAAE,aAAa,GAAG,OAAO,CAAC,YAAY,CAAC;
|
|
1
|
+
{"version":3,"file":"pipeline.d.ts","sourceRoot":"","sources":["../../../../src/src/rendering/orchestrator/pipeline.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;GAcG;AAgBH,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,iCAAiC,CAAC;AAEtE,OAAO,KAAK,EAAE,iBAAiB,EAAE,MAAM,+BAA+B,CAAC;AACvE,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,qBAAqB,CAAC;AACxD,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,6BAA6B,CAAC;AAChE,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,aAAa,CAAC;AACtD,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,uBAAuB,CAAC;AAC7D,OAAO,KAAK,EAAE,gBAAgB,EAAE,aAAa,EAAE,YAAY,EAAE,MAAM,YAAY,CAAC;AA6ChF,OAAO,EAAE,wBAAwB,EAAE,MAAM,gBAAgB,CAAC;AAE1D;;;;GAIG;AACH,MAAM,WAAW,wBAAwB;IACvC,UAAU,CAAC,IAAI,EAAE,MAAM,EAAE,QAAQ,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,iBAAiB,CAAC,CAAC;IACxE,aAAa,CAAC,MAAM,EAAE,YAAY,EAAE,IAAI,EAAE,MAAM,EAAE,QAAQ,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;CACrF;AAED,MAAM,WAAW,oBAAoB;IACnC,YAAY,EAAE,YAAY,CAAC;IAC3B,gBAAgB,EAAE,wBAAwB,CAAC;IAC3C,YAAY,EAAE,YAAY,CAAC;IAC3B,kBAAkB,EAAE,kBAAkB,CAAC;IACvC,eAAe,EAAE,eAAe,CAAC;IACjC,OAAO,EAAE,cAAc,CAAC;IACxB,IAAI,EAAE,aAAa,GAAG,YAAY,CAAC;IACnC,UAAU,EAAE,MAAM,CAAC;IACnB,8EAA8E;IAC9E,iBAAiB,CAAC,EAAE,OAAO,qBAAqB,EAAE,sBAAsB,CAAC;CAC1E;AAQD,qBAAa,cAAc;IACzB,OAAO,CAAC,MAAM,CAAuB;IACrC,OAAO,CAAC,WAAW,CAAc;IACjC,OAAO,CAAC,kBAAkB,CAAqB;gBAEnC,MAAM,EAAE,oBAAoB;IAaxC;;;OAGG;IACH,gBAAgB,IAAI,IAAI;IAKxB,OAAO,CAAC,UAAU;IAIlB,OAAO,CAAC,sBAAsB;YAIhB,0BAA0B;IAaxC;;;;;;;;;OASG;YACW,qBAAqB;IAyDnC;;;OAGG;YACW,mBAAmB;IAqH3B,UAAU,CAAC,IAAI,EAAE,MAAM,EAAE,OAAO,CAAC,EAAE,aAAa,GAAG,OAAO,CAAC,YAAY,CAAC;IA8P9E,+EAA+E;IACzE,eAAe,CAAC,IAAI,EAAE,MAAM,EAAE,OAAO,CAAC,EAAE,aAAa,GAAG,OAAO,CAAC,gBAAgB,CAAC;IA6LvF;;;;;;OAMG;IACH,OAAO,CAAC,aAAa;CAetB"}
|
|
@@ -247,119 +247,130 @@ export class RenderPipeline {
|
|
|
247
247
|
const pageResolveStart = performance.now();
|
|
248
248
|
const pageInfo = await withSpan("render.resolve_page", () => this.config.pageResolver.resolvePage(slug), { "render.slug": slug });
|
|
249
249
|
timing.pageResolve = Math.round(performance.now() - pageResolveStart);
|
|
250
|
-
const
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
|
|
273
|
-
|
|
274
|
-
|
|
250
|
+
const sourceFile = extractRelativePathShared(pageInfo.entity.path, this.config.projectDir);
|
|
251
|
+
try {
|
|
252
|
+
const skipLayouts = isDotPath(slug, pageInfo.entity.path);
|
|
253
|
+
const layoutCollectStart = performance.now();
|
|
254
|
+
const layoutResult = skipLayouts ? EMPTY_LAYOUT_RESULT : await withSpan("render.collect_layouts", () => this.config.layoutOrchestrator.collectLayouts(pageInfo), { "render.slug": slug });
|
|
255
|
+
timing.layoutCollect = Math.round(performance.now() - layoutCollectStart);
|
|
256
|
+
const layoutPreloadPromise = !skipLayouts && layoutResult.nestedLayouts.length > 0
|
|
257
|
+
? this.config.layoutOrchestrator.preloadLayoutModules(layoutResult.nestedLayouts)
|
|
258
|
+
: Promise.resolve();
|
|
259
|
+
let dataFetchingProps;
|
|
260
|
+
let resolvedParams = options?.params
|
|
261
|
+
? { ...options.params }
|
|
262
|
+
: {};
|
|
263
|
+
let layoutDataMap = new Map();
|
|
264
|
+
const dataFetchStart = performance.now();
|
|
265
|
+
if (options?.request && options?.url) {
|
|
266
|
+
await withSpan("render.data_fetching", async () => {
|
|
267
|
+
try {
|
|
268
|
+
const dataResolution = await this.resolveDataFetching(slug, pageInfo.entity.path, layoutResult.nestedLayouts, options);
|
|
269
|
+
resolvedParams = dataResolution.params;
|
|
270
|
+
dataFetchingProps = Object.keys(dataResolution.pageProps).length > 0
|
|
271
|
+
? dataResolution.pageProps
|
|
272
|
+
: undefined;
|
|
273
|
+
layoutDataMap = dataResolution.layoutProps;
|
|
274
|
+
}
|
|
275
|
+
catch (error) {
|
|
276
|
+
if (error instanceof VeryfrontError)
|
|
277
|
+
throw error;
|
|
278
|
+
renderPageLog.error("Data fetching error", {
|
|
279
|
+
slug,
|
|
280
|
+
error: error instanceof Error ? error.message : String(error),
|
|
281
|
+
});
|
|
275
282
|
throw error;
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
|
|
283
|
+
}
|
|
284
|
+
}, { "render.slug": slug });
|
|
285
|
+
}
|
|
286
|
+
timing.dataFetch = Math.round(performance.now() - dataFetchStart);
|
|
287
|
+
const hasResolvedParams = Object.keys(resolvedParams).length > 0;
|
|
288
|
+
const mergedOptions = (dataFetchingProps || hasResolvedParams)
|
|
289
|
+
? {
|
|
290
|
+
...options,
|
|
291
|
+
...(hasResolvedParams ? { params: resolvedParams } : {}),
|
|
292
|
+
...(dataFetchingProps
|
|
293
|
+
? { props: { ...options?.props, ...dataFetchingProps } }
|
|
294
|
+
: {}),
|
|
281
295
|
}
|
|
282
|
-
|
|
283
|
-
|
|
284
|
-
|
|
285
|
-
|
|
286
|
-
|
|
287
|
-
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
|
|
296
|
+
: options;
|
|
297
|
+
const bundlePrepStart = performance.now();
|
|
298
|
+
const pageBundleResult = await withSpan("render.prepare_bundles", () => this.config.pageRenderer.preparePageBundles(pageInfo, slug, cacheResult?.cachedModule, mergedOptions), { "render.slug": slug });
|
|
299
|
+
timing.bundlePrep = Math.round(performance.now() - bundlePrepStart);
|
|
300
|
+
if (pageBundleResult.scriptResult)
|
|
301
|
+
return pageBundleResult.scriptResult;
|
|
302
|
+
if (!pageBundleResult.pageElement || !pageBundleResult.pageBundle) {
|
|
303
|
+
throw RENDER_ERROR.create({
|
|
304
|
+
detail: "Failed to prepare page bundle",
|
|
305
|
+
context: { slug },
|
|
306
|
+
});
|
|
291
307
|
}
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
|
|
301
|
-
|
|
302
|
-
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
|
|
310
|
-
|
|
311
|
-
|
|
312
|
-
const wrappedElement = await withSpan("render.apply_layouts", () => this.config.layoutOrchestrator.applyLayoutsAndWrappers(pageElement, pageInfo, layoutResult.layoutBundle, layoutResult.nestedLayouts, layoutDataMap, options?.url, mergedFrontmatter, headings, options?.projectSlug), { "render.slug": slug, "render.layout_count": layoutResult.nestedLayouts.length });
|
|
313
|
-
timing.layoutApply = Math.round(performance.now() - layoutApplyStart);
|
|
314
|
-
// Snapshot CSS imports collected during module loading (before SSR rendering).
|
|
315
|
-
// These are passed to the HTML generator to be included in the output.
|
|
316
|
-
const collectedCSSImports = getCSSImports();
|
|
317
|
-
const ssrStart = performance.now();
|
|
318
|
-
const ssrResult = await withSpan("render.ssr", () => withTimeoutThrow(this.config.ssrOrchestrator.performSSRRendering(wrappedElement, {
|
|
319
|
-
pageInfo,
|
|
320
|
-
pageBundle,
|
|
321
|
-
layoutBundle: layoutResult.layoutBundle,
|
|
322
|
-
nestedLayouts: layoutResult.nestedLayouts,
|
|
323
|
-
collectedMetadata: pageBundleResult.collectedMetadata,
|
|
324
|
-
slug,
|
|
325
|
-
cssImports: collectedCSSImports,
|
|
326
|
-
}, mergedOptions), SSR_RENDER_TIMEOUT_MS, `SSR rendering for ${slug}`), { "render.slug": slug, "render.delivery": mergedOptions?.delivery || "full" });
|
|
327
|
-
timing.ssr = Math.round(performance.now() - ssrStart);
|
|
328
|
-
if (collectedCSSImports.length > 0) {
|
|
329
|
-
renderPipelineLog.debug("CSS imports collected for HTML generation", {
|
|
330
|
-
slug,
|
|
331
|
-
count: collectedCSSImports.length,
|
|
332
|
-
paths: collectedCSSImports.map((p) => p.split("/").pop()),
|
|
333
|
-
});
|
|
334
|
-
}
|
|
335
|
-
const pageModule = pageBundleResult.clientModuleCode && pageBundleResult.pageModuleType
|
|
336
|
-
? {
|
|
308
|
+
const { pageElement, pageBundle } = pageBundleResult;
|
|
309
|
+
const mergedFrontmatter = {
|
|
310
|
+
...pageInfo.entity.frontmatter,
|
|
311
|
+
...pageBundle.frontmatter,
|
|
312
|
+
};
|
|
313
|
+
const headings = pageBundle.headings || [];
|
|
314
|
+
await layoutPreloadPromise;
|
|
315
|
+
const layoutApplyStart = performance.now();
|
|
316
|
+
const wrappedElement = await withSpan("render.apply_layouts", () => this.config.layoutOrchestrator.applyLayoutsAndWrappers(pageElement, pageInfo, layoutResult.layoutBundle, layoutResult.nestedLayouts, layoutDataMap, options?.url, mergedFrontmatter, headings, options?.projectSlug), { "render.slug": slug, "render.layout_count": layoutResult.nestedLayouts.length });
|
|
317
|
+
timing.layoutApply = Math.round(performance.now() - layoutApplyStart);
|
|
318
|
+
// Snapshot CSS imports collected during module loading (before SSR rendering).
|
|
319
|
+
// These are passed to the HTML generator to be included in the output.
|
|
320
|
+
const collectedCSSImports = getCSSImports();
|
|
321
|
+
const ssrStart = performance.now();
|
|
322
|
+
const ssrResult = await withSpan("render.ssr", () => withTimeoutThrow(this.config.ssrOrchestrator.performSSRRendering(wrappedElement, {
|
|
323
|
+
pageInfo,
|
|
324
|
+
pageBundle,
|
|
325
|
+
layoutBundle: layoutResult.layoutBundle,
|
|
326
|
+
nestedLayouts: layoutResult.nestedLayouts,
|
|
327
|
+
collectedMetadata: pageBundleResult.collectedMetadata,
|
|
337
328
|
slug,
|
|
338
|
-
|
|
339
|
-
|
|
329
|
+
cssImports: collectedCSSImports,
|
|
330
|
+
}, mergedOptions), SSR_RENDER_TIMEOUT_MS, `SSR rendering for ${slug}`), { "render.slug": slug, "render.delivery": mergedOptions?.delivery || "full" });
|
|
331
|
+
timing.ssr = Math.round(performance.now() - ssrStart);
|
|
332
|
+
if (collectedCSSImports.length > 0) {
|
|
333
|
+
renderPipelineLog.debug("CSS imports collected for HTML generation", {
|
|
334
|
+
slug,
|
|
335
|
+
count: collectedCSSImports.length,
|
|
336
|
+
paths: collectedCSSImports.map((p) => p.split("/").pop()),
|
|
337
|
+
});
|
|
340
338
|
}
|
|
341
|
-
|
|
342
|
-
|
|
343
|
-
html: ssrResult.fullHtml,
|
|
344
|
-
frontmatter: pageBundleResult.pageBundle.frontmatter || {},
|
|
345
|
-
headings: pageBundleResult.pageBundle.headings || [],
|
|
346
|
-
nodeMap: pageBundleResult.pageBundle.nodeMap,
|
|
347
|
-
stream: ssrResult.finalStream,
|
|
348
|
-
ssrHash: ssrResult.ssrHash,
|
|
349
|
-
...(pageModule ? { pageModule } : {}),
|
|
350
|
-
};
|
|
351
|
-
if (shouldCache && !options?.skipCachePersist) {
|
|
352
|
-
void this.config.cacheCoordinator.persistResult(result, slug, cacheKey).catch((error) => {
|
|
353
|
-
renderPipelineLog.error("Cache persist failed", {
|
|
339
|
+
const pageModule = pageBundleResult.clientModuleCode && pageBundleResult.pageModuleType
|
|
340
|
+
? {
|
|
354
341
|
slug,
|
|
355
|
-
|
|
356
|
-
|
|
342
|
+
code: pageBundleResult.clientModuleCode,
|
|
343
|
+
type: pageBundleResult.pageModuleType,
|
|
344
|
+
}
|
|
345
|
+
: undefined;
|
|
346
|
+
const result = {
|
|
347
|
+
html: ssrResult.fullHtml,
|
|
348
|
+
frontmatter: pageBundleResult.pageBundle.frontmatter || {},
|
|
349
|
+
headings: pageBundleResult.pageBundle.headings || [],
|
|
350
|
+
nodeMap: pageBundleResult.pageBundle.nodeMap,
|
|
351
|
+
stream: ssrResult.finalStream,
|
|
352
|
+
ssrHash: ssrResult.ssrHash,
|
|
353
|
+
...(pageModule ? { pageModule } : {}),
|
|
354
|
+
};
|
|
355
|
+
if (shouldCache && !options?.skipCachePersist) {
|
|
356
|
+
void this.config.cacheCoordinator.persistResult(result, slug, cacheKey).catch((error) => {
|
|
357
|
+
renderPipelineLog.error("Cache persist failed", {
|
|
358
|
+
slug,
|
|
359
|
+
error: error instanceof Error ? error.message : String(error),
|
|
360
|
+
stack: error instanceof Error ? error.stack : undefined,
|
|
361
|
+
});
|
|
357
362
|
});
|
|
358
|
-
}
|
|
363
|
+
}
|
|
364
|
+
timing.total = Math.round(performance.now() - pipelineStartTime);
|
|
365
|
+
renderPipelineLog.debug("Complete", { slug, timing });
|
|
366
|
+
return result;
|
|
367
|
+
}
|
|
368
|
+
catch (error) {
|
|
369
|
+
if (error instanceof Error) {
|
|
370
|
+
error.sourceFile = sourceFile;
|
|
371
|
+
}
|
|
372
|
+
throw error;
|
|
359
373
|
}
|
|
360
|
-
timing.total = Math.round(performance.now() - pipelineStartTime);
|
|
361
|
-
renderPipelineLog.debug("Complete", { slug, timing });
|
|
362
|
-
return result;
|
|
363
374
|
});
|
|
364
375
|
return result;
|
|
365
376
|
}, {
|
|
@@ -8,5 +8,9 @@ export interface ErrorInfo {
|
|
|
8
8
|
suggestion?: string;
|
|
9
9
|
}
|
|
10
10
|
export declare function getSuggestion(error: Error): string | undefined;
|
|
11
|
+
export declare function parseErrorLocation(error: Error, file: string): {
|
|
12
|
+
line?: number;
|
|
13
|
+
column?: number;
|
|
14
|
+
};
|
|
11
15
|
export declare function formatErrorType(type: ErrorType): string;
|
|
12
16
|
//# sourceMappingURL=error-formatter.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"error-formatter.d.ts","sourceRoot":"","sources":["../../../../../src/src/server/dev-server/error-overlay/error-formatter.ts"],"names":[],"mappings":"AAAA,MAAM,MAAM,SAAS,GAAG,OAAO,GAAG,SAAS,GAAG,WAAW,CAAC;AAE1D,MAAM,WAAW,SAAS;IACxB,IAAI,EAAE,SAAS,CAAC;IAChB,KAAK,EAAE,KAAK,CAAC;IACb,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,UAAU,CAAC,EAAE,MAAM,CAAC;CACrB;AAkCD,wBAAgB,aAAa,CAAC,KAAK,EAAE,KAAK,GAAG,MAAM,GAAG,SAAS,CAU9D;AAED,wBAAgB,eAAe,CAAC,IAAI,EAAE,SAAS,GAAG,MAAM,CAKvD"}
|
|
1
|
+
{"version":3,"file":"error-formatter.d.ts","sourceRoot":"","sources":["../../../../../src/src/server/dev-server/error-overlay/error-formatter.ts"],"names":[],"mappings":"AAAA,MAAM,MAAM,SAAS,GAAG,OAAO,GAAG,SAAS,GAAG,WAAW,CAAC;AAE1D,MAAM,WAAW,SAAS;IACxB,IAAI,EAAE,SAAS,CAAC;IAChB,KAAK,EAAE,KAAK,CAAC;IACb,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,UAAU,CAAC,EAAE,MAAM,CAAC;CACrB;AAkCD,wBAAgB,aAAa,CAAC,KAAK,EAAE,KAAK,GAAG,MAAM,GAAG,SAAS,CAU9D;AAED,wBAAgB,kBAAkB,CAChC,KAAK,EAAE,KAAK,EACZ,IAAI,EAAE,MAAM,GACX;IAAE,IAAI,CAAC,EAAE,MAAM,CAAC;IAAC,MAAM,CAAC,EAAE,MAAM,CAAA;CAAE,CAgBpC;AAED,wBAAgB,eAAe,CAAC,IAAI,EAAE,SAAS,GAAG,MAAM,CAKvD"}
|
|
@@ -33,6 +33,21 @@ export function getSuggestion(error) {
|
|
|
33
33
|
}
|
|
34
34
|
return undefined;
|
|
35
35
|
}
|
|
36
|
+
export function parseErrorLocation(error, file) {
|
|
37
|
+
if (!error.stack || !file)
|
|
38
|
+
return {};
|
|
39
|
+
const lines = error.stack.split("\n");
|
|
40
|
+
// First try to match the known source file
|
|
41
|
+
for (const stackLine of lines) {
|
|
42
|
+
if (!stackLine.includes(file))
|
|
43
|
+
continue;
|
|
44
|
+
const match = stackLine.match(/:(\d+):(\d+)\)?$/);
|
|
45
|
+
if (match) {
|
|
46
|
+
return { line: Number(match[1]), column: Number(match[2]) };
|
|
47
|
+
}
|
|
48
|
+
}
|
|
49
|
+
return {};
|
|
50
|
+
}
|
|
36
51
|
export function formatErrorType(type) {
|
|
37
52
|
const firstChar = type[0];
|
|
38
53
|
if (!firstChar)
|
|
@@ -1,4 +1,4 @@
|
|
|
1
1
|
import { type ErrorInfo } from "./error-formatter.js";
|
|
2
2
|
export declare function generateRuntimeScript(): string;
|
|
3
|
-
export declare function generateErrorHTML(errorInfo: ErrorInfo, suggestion?: string): string;
|
|
3
|
+
export declare function generateErrorHTML(errorInfo: ErrorInfo, suggestion?: string, projectSlug?: string): string;
|
|
4
4
|
//# sourceMappingURL=html-template.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"html-template.d.ts","sourceRoot":"","sources":["../../../../../src/src/server/dev-server/error-overlay/html-template.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,KAAK,SAAS,EAAmB,MAAM,sBAAsB,CAAC;
|
|
1
|
+
{"version":3,"file":"html-template.d.ts","sourceRoot":"","sources":["../../../../../src/src/server/dev-server/error-overlay/html-template.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,KAAK,SAAS,EAAmB,MAAM,sBAAsB,CAAC;AAmBvE,wBAAgB,qBAAqB,IAAI,MAAM,CA6L9C;AAED,wBAAgB,iBAAiB,CAC/B,SAAS,EAAE,SAAS,EACpB,UAAU,CAAC,EAAE,MAAM,EACnB,WAAW,CAAC,EAAE,MAAM,GACnB,MAAM,CAuOR"}
|
|
@@ -6,6 +6,12 @@ const WS_RECONNECT_BASE_DELAY_MS = 1_000;
|
|
|
6
6
|
const WS_RECONNECT_MAX_DELAY_MS = 5_000;
|
|
7
7
|
/** Maximum number of WebSocket reconnection attempts before giving up */
|
|
8
8
|
const WS_MAX_RECONNECT_ATTEMPTS = 10;
|
|
9
|
+
/** JSON.stringify that escapes `<` to prevent `</script>` breaking inline scripts */
|
|
10
|
+
function jsonForScript(value) {
|
|
11
|
+
const json = JSON.stringify(value);
|
|
12
|
+
// JSON.stringify(undefined) returns undefined (not a string)
|
|
13
|
+
return json === undefined ? "undefined" : json.replace(/</g, "\\u003c");
|
|
14
|
+
}
|
|
9
15
|
export function generateRuntimeScript() {
|
|
10
16
|
return `
|
|
11
17
|
// Veryfront Error Overlay Runtime
|
|
@@ -106,21 +112,76 @@ export function generateRuntimeScript() {
|
|
|
106
112
|
</div>
|
|
107
113
|
|
|
108
114
|
<button type="button" onclick="document.getElementById('veryfront-error-overlay').remove()" style="
|
|
109
|
-
background: #
|
|
110
|
-
border:
|
|
111
|
-
color: #
|
|
112
|
-
padding:
|
|
113
|
-
border-radius:
|
|
115
|
+
background: #fff;
|
|
116
|
+
border: none;
|
|
117
|
+
color: #000;
|
|
118
|
+
padding: 10px 20px;
|
|
119
|
+
border-radius: 9999px;
|
|
114
120
|
cursor: pointer;
|
|
115
121
|
font-family: inherit;
|
|
116
122
|
">
|
|
117
123
|
Dismiss
|
|
118
124
|
</button>
|
|
125
|
+
\${window.__VF_PROJECT_SLUG__ ? \`
|
|
126
|
+
<button type="button" id="vf-fix-btn-runtime" style="
|
|
127
|
+
background: transparent;
|
|
128
|
+
border: 1px solid rgba(255, 255, 255, 0.2);
|
|
129
|
+
color: rgba(255, 255, 255, 0.7);
|
|
130
|
+
padding: 10px 20px;
|
|
131
|
+
border-radius: 9999px;
|
|
132
|
+
cursor: pointer;
|
|
133
|
+
font-family: inherit;
|
|
134
|
+
margin-left: 8px;
|
|
135
|
+
">
|
|
136
|
+
Fix in Veryfront
|
|
137
|
+
</button>
|
|
138
|
+
\` : ''}
|
|
119
139
|
</div>
|
|
120
140
|
</div>
|
|
121
141
|
\`;
|
|
122
142
|
|
|
123
143
|
document.body.appendChild(overlay);
|
|
144
|
+
|
|
145
|
+
// Notify Studio of runtime error
|
|
146
|
+
if (window.parent !== window) {
|
|
147
|
+
try {
|
|
148
|
+
window.parent.postMessage({
|
|
149
|
+
action: 'runtimeError',
|
|
150
|
+
url: window.location.href,
|
|
151
|
+
hasError: true,
|
|
152
|
+
errors: [{
|
|
153
|
+
type: 'error',
|
|
154
|
+
message: (errorInfo.error && errorInfo.error.message) || 'Unknown error',
|
|
155
|
+
file: errorInfo.file ? String(errorInfo.file) : undefined,
|
|
156
|
+
line: errorInfo.line ? Number(errorInfo.line) : undefined,
|
|
157
|
+
column: errorInfo.column ? Number(errorInfo.column) : undefined
|
|
158
|
+
}]
|
|
159
|
+
}, '*');
|
|
160
|
+
} catch (e) { /* postMessage may fail */ }
|
|
161
|
+
}
|
|
162
|
+
|
|
163
|
+
if (window.__VF_PROJECT_SLUG__) {
|
|
164
|
+
var fixBtn = document.getElementById('vf-fix-btn-runtime');
|
|
165
|
+
if (fixBtn) {
|
|
166
|
+
fixBtn.addEventListener('click', function() {
|
|
167
|
+
var rawName = (errorInfo.error && errorInfo.error.name) || 'Error';
|
|
168
|
+
var rawMessage = (errorInfo.error && errorInfo.error.message) || 'Unknown error';
|
|
169
|
+
var rawFile = errorInfo.file ? String(errorInfo.file) : null;
|
|
170
|
+
var rawLine = errorInfo.line ? String(errorInfo.line) : null;
|
|
171
|
+
var rawColumn = errorInfo.column ? String(errorInfo.column) : null;
|
|
172
|
+
var loc = rawFile ? rawFile + (rawLine ? ':' + rawLine : '') + (rawColumn ? ':' + rawColumn : '') : null;
|
|
173
|
+
var bt = String.fromCharCode(96);
|
|
174
|
+
var prompt = 'Find and fix the following error' +
|
|
175
|
+
(loc ? ' in ' + bt + loc + bt : '') +
|
|
176
|
+
'\\n\\n' + bt + rawMessage + bt;
|
|
177
|
+
if (window.parent !== window) {
|
|
178
|
+
window.parent.postMessage({ action: 'chatMessage', prompt: prompt }, '*');
|
|
179
|
+
} else {
|
|
180
|
+
window.open('https://veryfront.com/projects/' + window.__VF_PROJECT_SLUG__ + '?prompt=' + encodeURIComponent(prompt));
|
|
181
|
+
}
|
|
182
|
+
});
|
|
183
|
+
}
|
|
184
|
+
}
|
|
124
185
|
};
|
|
125
186
|
|
|
126
187
|
window.addEventListener('error', (event) => {
|
|
@@ -141,7 +202,7 @@ export function generateRuntimeScript() {
|
|
|
141
202
|
});
|
|
142
203
|
`;
|
|
143
204
|
}
|
|
144
|
-
export function generateErrorHTML(errorInfo, suggestion) {
|
|
205
|
+
export function generateErrorHTML(errorInfo, suggestion, projectSlug) {
|
|
145
206
|
const errorType = escapeHtml(formatErrorType(errorInfo.type));
|
|
146
207
|
const errorName = escapeHtml(errorInfo.error.name);
|
|
147
208
|
const errorMessage = escapeHtml(errorInfo.error.message);
|
|
@@ -173,6 +234,9 @@ export function generateErrorHTML(errorInfo, suggestion) {
|
|
|
173
234
|
</details>
|
|
174
235
|
`
|
|
175
236
|
: "";
|
|
237
|
+
const fixButtonHtml = projectSlug
|
|
238
|
+
? `<button type="button" id="vf-fix-btn" class="btn btn-fix">Fix in Veryfront</button>`
|
|
239
|
+
: "";
|
|
176
240
|
return `
|
|
177
241
|
<!DOCTYPE html>
|
|
178
242
|
<html>
|
|
@@ -244,6 +308,32 @@ export function generateErrorHTML(errorInfo, suggestion) {
|
|
|
244
308
|
overflow-x: auto;
|
|
245
309
|
font-size: 12px;
|
|
246
310
|
}
|
|
311
|
+
.btn {
|
|
312
|
+
padding: 10px 20px;
|
|
313
|
+
border-radius: 9999px;
|
|
314
|
+
cursor: pointer;
|
|
315
|
+
font-family: inherit;
|
|
316
|
+
font-size: 14px;
|
|
317
|
+
border: none;
|
|
318
|
+
}
|
|
319
|
+
.btn-dismiss {
|
|
320
|
+
background: #fff;
|
|
321
|
+
color: #000;
|
|
322
|
+
}
|
|
323
|
+
.btn-dismiss:hover {
|
|
324
|
+
background: #e5e5e5;
|
|
325
|
+
}
|
|
326
|
+
.btn-fix {
|
|
327
|
+
background: transparent;
|
|
328
|
+
color: rgba(255, 255, 255, 0.7);
|
|
329
|
+
border: 1px solid rgba(255, 255, 255, 0.2);
|
|
330
|
+
margin-left: 8px;
|
|
331
|
+
}
|
|
332
|
+
.btn-fix:hover {
|
|
333
|
+
background: rgba(255, 255, 255, 0.1);
|
|
334
|
+
color: #fff;
|
|
335
|
+
border-color: rgba(255, 255, 255, 0.4);
|
|
336
|
+
}
|
|
247
337
|
</style>
|
|
248
338
|
</head>
|
|
249
339
|
<body>
|
|
@@ -258,8 +348,34 @@ export function generateErrorHTML(errorInfo, suggestion) {
|
|
|
258
348
|
${suggestionSection}
|
|
259
349
|
${stackSection}
|
|
260
350
|
</div>
|
|
351
|
+
${fixButtonHtml}
|
|
261
352
|
</div>
|
|
262
|
-
<script
|
|
353
|
+
<script>${projectSlug
|
|
354
|
+
? `
|
|
355
|
+
(function() {
|
|
356
|
+
var slug = ${jsonForScript(projectSlug)};
|
|
357
|
+
var errorName = ${jsonForScript(errorInfo.error.name)};
|
|
358
|
+
var errorMessage = ${jsonForScript(errorInfo.error.message)};
|
|
359
|
+
var errorFile = ${jsonForScript(errorInfo.file ?? null)};
|
|
360
|
+
var errorLine = ${jsonForScript(errorInfo.line ?? null)};
|
|
361
|
+
var errorColumn = ${jsonForScript(errorInfo.column ?? null)};
|
|
362
|
+
var btn = document.getElementById('vf-fix-btn');
|
|
363
|
+
if (btn) {
|
|
364
|
+
btn.addEventListener('click', function() {
|
|
365
|
+
var loc = errorFile ? errorFile + (errorLine ? ':' + errorLine : '') + (errorColumn ? ':' + errorColumn : '') : null;
|
|
366
|
+
var bt = String.fromCharCode(96);
|
|
367
|
+
var prompt = 'Find and fix the following error' +
|
|
368
|
+
(loc ? ' in ' + bt + loc + bt : '') +
|
|
369
|
+
'\\n\\n' + bt + errorMessage + bt;
|
|
370
|
+
if (window.parent !== window) {
|
|
371
|
+
window.parent.postMessage({ action: 'chatMessage', prompt: prompt }, '*');
|
|
372
|
+
} else {
|
|
373
|
+
window.open('https://veryfront.com/projects/' + slug + '?prompt=' + encodeURIComponent(prompt));
|
|
374
|
+
}
|
|
375
|
+
});
|
|
376
|
+
}
|
|
377
|
+
})();`
|
|
378
|
+
: ""}
|
|
263
379
|
// Notify Studio (parent) that page has loaded with an error
|
|
264
380
|
// This hides the loading spinner in Studio's preview iframe
|
|
265
381
|
if (window.parent !== window) {
|
|
@@ -268,7 +384,14 @@ export function generateErrorHTML(errorInfo, suggestion) {
|
|
|
268
384
|
action: 'appUpdated',
|
|
269
385
|
isInitialLoad: true,
|
|
270
386
|
hasError: true,
|
|
271
|
-
url: window.location.href
|
|
387
|
+
url: window.location.href,
|
|
388
|
+
errors: [{
|
|
389
|
+
type: 'error',
|
|
390
|
+
message: ${jsonForScript(errorInfo.error.message)},
|
|
391
|
+
file: ${jsonForScript(errorInfo.file || undefined)},
|
|
392
|
+
line: ${errorInfo.line ? String(errorInfo.line) : "undefined"},
|
|
393
|
+
column: ${errorInfo.column ? String(errorInfo.column) : "undefined"}
|
|
394
|
+
}]
|
|
272
395
|
}, '*');
|
|
273
396
|
} catch (e) { /* postMessage may fail in cross-origin iframes */ }
|
|
274
397
|
}
|
|
@@ -4,7 +4,7 @@
|
|
|
4
4
|
* @module server/dev-server/error-overlay
|
|
5
5
|
*/
|
|
6
6
|
export { ErrorOverlay } from "./overlay-renderer.js";
|
|
7
|
-
export { type ErrorInfo, type ErrorType, formatErrorType, getSuggestion, } from "./error-formatter.js";
|
|
7
|
+
export { type ErrorInfo, type ErrorType, formatErrorType, getSuggestion, parseErrorLocation, } from "./error-formatter.js";
|
|
8
8
|
export { generateErrorHTML, generateRuntimeScript } from "./html-template.js";
|
|
9
9
|
export { formatStackTrace, hasStackTrace, type ParsedStackFrame, parseStackTrace, } from "./stack-parser.js";
|
|
10
10
|
//# sourceMappingURL=index.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../../../src/src/server/dev-server/error-overlay/index.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,EAAE,YAAY,EAAE,MAAM,uBAAuB,CAAC;AACrD,OAAO,EACL,KAAK,SAAS,EACd,KAAK,SAAS,EACd,eAAe,EACf,aAAa,
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../../../src/src/server/dev-server/error-overlay/index.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,EAAE,YAAY,EAAE,MAAM,uBAAuB,CAAC;AACrD,OAAO,EACL,KAAK,SAAS,EACd,KAAK,SAAS,EACd,eAAe,EACf,aAAa,EACb,kBAAkB,GACnB,MAAM,sBAAsB,CAAC;AAC9B,OAAO,EAAE,iBAAiB,EAAE,qBAAqB,EAAE,MAAM,oBAAoB,CAAC;AAC9E,OAAO,EACL,gBAAgB,EAChB,aAAa,EACb,KAAK,gBAAgB,EACrB,eAAe,GAChB,MAAM,mBAAmB,CAAC"}
|
|
@@ -4,6 +4,6 @@
|
|
|
4
4
|
* @module server/dev-server/error-overlay
|
|
5
5
|
*/
|
|
6
6
|
export { ErrorOverlay } from "./overlay-renderer.js";
|
|
7
|
-
export { formatErrorType, getSuggestion, } from "./error-formatter.js";
|
|
7
|
+
export { formatErrorType, getSuggestion, parseErrorLocation, } from "./error-formatter.js";
|
|
8
8
|
export { generateErrorHTML, generateRuntimeScript } from "./html-template.js";
|
|
9
9
|
export { formatStackTrace, hasStackTrace, parseStackTrace, } from "./stack-parser.js";
|
|
@@ -3,6 +3,6 @@ import { generateRuntimeScript } from "./html-template.js";
|
|
|
3
3
|
export declare const ErrorOverlay: {
|
|
4
4
|
getRuntime: typeof generateRuntimeScript;
|
|
5
5
|
getSuggestion: typeof getSuggestion;
|
|
6
|
-
createHTML(errorInfo: ErrorInfo): string;
|
|
6
|
+
createHTML(errorInfo: ErrorInfo, projectSlug?: string): string;
|
|
7
7
|
};
|
|
8
8
|
//# sourceMappingURL=overlay-renderer.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"overlay-renderer.d.ts","sourceRoot":"","sources":["../../../../../src/src/server/dev-server/error-overlay/overlay-renderer.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,KAAK,SAAS,EAAE,aAAa,EAAE,MAAM,sBAAsB,CAAC;AACrE,OAAO,EAAqB,qBAAqB,EAAE,MAAM,oBAAoB,CAAC;AAE9E,eAAO,MAAM,YAAY;;;0BAGD,SAAS,GAAG,MAAM;
|
|
1
|
+
{"version":3,"file":"overlay-renderer.d.ts","sourceRoot":"","sources":["../../../../../src/src/server/dev-server/error-overlay/overlay-renderer.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,KAAK,SAAS,EAAE,aAAa,EAAE,MAAM,sBAAsB,CAAC;AACrE,OAAO,EAAqB,qBAAqB,EAAE,MAAM,oBAAoB,CAAC;AAE9E,eAAO,MAAM,YAAY;;;0BAGD,SAAS,gBAAgB,MAAM,GAAG,MAAM;CAO/D,CAAC"}
|
|
@@ -3,7 +3,7 @@ import { generateErrorHTML, generateRuntimeScript } from "./html-template.js";
|
|
|
3
3
|
export const ErrorOverlay = {
|
|
4
4
|
getRuntime: generateRuntimeScript,
|
|
5
5
|
getSuggestion,
|
|
6
|
-
createHTML(errorInfo) {
|
|
7
|
-
return generateErrorHTML(errorInfo, errorInfo.suggestion ?? getSuggestion(errorInfo.error));
|
|
6
|
+
createHTML(errorInfo, projectSlug) {
|
|
7
|
+
return generateErrorHTML(errorInfo, errorInfo.suggestion ?? getSuggestion(errorInfo.error), projectSlug);
|
|
8
8
|
},
|
|
9
9
|
};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"request-handler.d.ts","sourceRoot":"","sources":["../../../../src/src/server/dev-server/request-handler.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,OAAO,MAAM,wBAAwB,CAAC;AASlD,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,iCAAiC,CAAC;AACtE,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,uBAAuB,CAAC;AAY7D,qBAAa,cAAc;IAIvB,OAAO,CAAC,UAAU;IAClB,OAAO,CAAC,OAAO;IACf,OAAO,CAAC,OAAO;IACf,OAAO,CAAC,OAAO;IACf,OAAO,CAAC,MAAM,CAAC;IACf,OAAO,CAAC,kBAAkB,CAAC;IAC3B,OAAO,CAAC,gBAAgB,CAAC;IACzB,OAAO,CAAC,aAAa,CAAC;IAVxB,OAAO,CAAC,cAAc,CAAC,CAAsD;gBAGnE,UAAU,EAAE,MAAM,EAClB,OAAO,EAAE,cAAc,EACvB,OAAO,EAAE,MAAM,OAAO,EACtB,OAAO,EAAE,MAAM,OAAO,EACtB,MAAM,CAAC,EAAE,eAAe,YAAA,EACxB,kBAAkB,CAAC,EAAE,MAAM,YAAA,EAC3B,gBAAgB,CAAC,EAAE,MAAM,YAAA,EACzB,aAAa,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,YAAA;IAG1C,aAAa,CAAC,GAAG,EAAE,OAAO,CAAC,OAAO,GAAG,OAAO,CAAC,OAAO,CAAC,QAAQ,CAAC;IA0BpE,OAAO,CAAC,UAAU;IAYlB,OAAO,CAAC,iBAAiB;YAiBX,uBAAuB;IASrC,OAAO,CAAC,iBAAiB;IAqBzB,OAAO,CAAC,oBAAoB;YAYd,wBAAwB;IAiBtC,wBAAwB,IAAI,IAAI;IAehC,OAAO,CAAC,iBAAiB;
|
|
1
|
+
{"version":3,"file":"request-handler.d.ts","sourceRoot":"","sources":["../../../../src/src/server/dev-server/request-handler.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,OAAO,MAAM,wBAAwB,CAAC;AASlD,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,iCAAiC,CAAC;AACtE,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,uBAAuB,CAAC;AAY7D,qBAAa,cAAc;IAIvB,OAAO,CAAC,UAAU;IAClB,OAAO,CAAC,OAAO;IACf,OAAO,CAAC,OAAO;IACf,OAAO,CAAC,OAAO;IACf,OAAO,CAAC,MAAM,CAAC;IACf,OAAO,CAAC,kBAAkB,CAAC;IAC3B,OAAO,CAAC,gBAAgB,CAAC;IACzB,OAAO,CAAC,aAAa,CAAC;IAVxB,OAAO,CAAC,cAAc,CAAC,CAAsD;gBAGnE,UAAU,EAAE,MAAM,EAClB,OAAO,EAAE,cAAc,EACvB,OAAO,EAAE,MAAM,OAAO,EACtB,OAAO,EAAE,MAAM,OAAO,EACtB,MAAM,CAAC,EAAE,eAAe,YAAA,EACxB,kBAAkB,CAAC,EAAE,MAAM,YAAA,EAC3B,gBAAgB,CAAC,EAAE,MAAM,YAAA,EACzB,aAAa,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,YAAA;IAG1C,aAAa,CAAC,GAAG,EAAE,OAAO,CAAC,OAAO,GAAG,OAAO,CAAC,OAAO,CAAC,QAAQ,CAAC;IA0BpE,OAAO,CAAC,UAAU;IAYlB,OAAO,CAAC,iBAAiB;YAiBX,uBAAuB;IASrC,OAAO,CAAC,iBAAiB;IAqBzB,OAAO,CAAC,oBAAoB;YAYd,wBAAwB;IAiBtC,wBAAwB,IAAI,IAAI;IAehC,OAAO,CAAC,iBAAiB;CAqB1B"}
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import * as dntShim from "../../../_dnt.shims.js";
|
|
2
2
|
import { DEV_SERVER_ENDPOINTS, HTTP_CONTENT_TYPES, HTTP_OK, HTTP_SERVER_ERROR, HTTP_UNAVAILABLE, serverLogger, } from "../../utils/index.js";
|
|
3
3
|
import { clearConfigCache } from "../../config/index.js";
|
|
4
|
-
import { ErrorOverlay } from "./error-overlay/index.js";
|
|
4
|
+
import { ErrorOverlay, parseErrorLocation } from "./error-overlay/index.js";
|
|
5
5
|
import { createResponseBuilder } from "../../security/index.js";
|
|
6
6
|
import { resetApiHandler } from "../handlers/request/api/pages-api-handler.js";
|
|
7
7
|
import { clearLayoutDiscoveryCache } from "../../rendering/layouts/index.js";
|
|
@@ -147,10 +147,14 @@ export class RequestHandler {
|
|
|
147
147
|
logger.error("Server error:", error);
|
|
148
148
|
const err = error;
|
|
149
149
|
getErrorCollector().addRuntimeError(err.message, err.stack, { source: "request-handler" });
|
|
150
|
+
const sourceFile = err.sourceFile;
|
|
151
|
+
const location = sourceFile ? parseErrorLocation(err, sourceFile) : {};
|
|
150
152
|
return new dntShim.Response(ErrorOverlay.createHTML({
|
|
151
153
|
type: "runtime",
|
|
152
154
|
error: err,
|
|
153
|
-
|
|
155
|
+
...(sourceFile ? { file: sourceFile } : {}),
|
|
156
|
+
...location,
|
|
157
|
+
}, this.defaultProjectSlug), {
|
|
154
158
|
status: HTTP_SERVER_ERROR,
|
|
155
159
|
headers: { "content-type": "text/html; charset=utf-8" },
|
|
156
160
|
});
|