web: reload on chunk load errors after a deploy
web / ci (push) Successful in 1m49s

This commit is contained in:
2026-09-08 01:55:35 +02:00
parent 57743e6640
commit 5555a241b5
3 changed files with 54 additions and 1 deletions
+15 -1
View File
@@ -1,8 +1,22 @@
"use client";
import { useEffect } from "react";
import { PageHeader } from "@/components/general/PageHeader";
import { isChunkLoadError } from "@/lib/chunkError";
const RELOAD_KEY = "chunk-error-reload";
const RELOAD_COOLDOWN_MS = 10_000;
function ErrorPage({ error }: { error: Error & { digest?: string } }) {
useEffect(() => {
if (!isChunkLoadError(error)) return;
// No reload loop if the chunk is gone for good
const last = Number(sessionStorage.getItem(RELOAD_KEY) ?? 0);
if (Date.now() - last < RELOAD_COOLDOWN_MS) return;
sessionStorage.setItem(RELOAD_KEY, String(Date.now()));
window.location.reload();
}, [error]);
function ErrorPage() {
return (
<main className="site-main" id="main">
<div>
+30
View File
@@ -0,0 +1,30 @@
import { describe, expect, it } from "vitest";
import { isChunkLoadError } from "./chunkError.ts";
describe("isChunkLoadError", () => {
it("matches the turbopack chunk loader error", () => {
const error = new Error(
"Failed to load chunk /_next/static/chunks/0xd_vh2ud8yl-.js from module 64893"
);
error.name = "ChunkLoadError";
expect(isChunkLoadError(error)).toBe(true);
});
it("matches by message when the name is generic", () => {
expect(isChunkLoadError(new Error("Loading chunk 123 failed."))).toBe(true);
expect(
isChunkLoadError(
new TypeError("Failed to fetch dynamically imported module: https://neuf.no/x.js")
)
).toBe(true);
expect(isChunkLoadError(new TypeError("Importing a module script failed."))).toBe(true);
});
it("ignores other errors", () => {
expect(isChunkLoadError(new Error("boom"))).toBe(false);
expect(
isChunkLoadError(new TypeError("Cannot read properties of undefined (reading 'slug')"))
).toBe(false);
});
});
+9
View File
@@ -0,0 +1,9 @@
// A tab opened before a deploy may reference chunks the new build no longer ships
export function isChunkLoadError(error: Error): boolean {
return (
error.name === "ChunkLoadError" ||
/failed to load chunk|loading chunk .* failed|dynamically imported module|importing a module script failed/i.test(
error.message
)
);
}