UNPKG

everything-dev

Version:

A consolidated product package for building Module Federation apps with oRPC APIs.

85 lines (83 loc) • 3.86 kB
import { useSyncExternalStore } from "react"; import { jsx, jsxs } from "react/jsx-runtime"; //#region src/ui/router-error.tsx /** * Generic router error boundary component — shared by the client and SSR * router factories. Dependency-free by design: the framework cannot import * the app's UI kit, so primitives are plain markup + semantic tokens. */ const subscribeToNothing = () => () => {}; /** * Whether the error-details block renders. `undefined` (the default) shows * details once the client is live — SSR HTML is what gets indexed, cached * and logged, so internal messages (RPC endpoints, digests, provider errors) * stay out of it, and the hydration pass renders the same details-free * markup before revealing. `true` always renders the block, `false` never * does. `suppress` is true while rendering on the server or pre-reveal. */ function shouldShowErrorDetails(showErrorDetails, suppress) { if (showErrorDetails === false) return false; if (showErrorDetails === true) return true; return !suppress; } function RouterError({ error, reset, messages, showErrorDetails }) { const showDetails = shouldShowErrorDetails(showErrorDetails, !useSyncExternalStore(subscribeToNothing, () => true, () => false)); return /* @__PURE__ */ jsx("div", { className: "flex min-h-96 flex-1 items-center justify-center bg-background px-4 py-16", role: "alert", "data-testid": "router-error", children: /* @__PURE__ */ jsxs("div", { className: "flex max-w-md flex-col items-center gap-6 text-center", children: [ /* @__PURE__ */ jsx("div", { className: "flex size-14 items-center justify-center rounded-full bg-destructive-muted text-destructive-muted-foreground", children: /* @__PURE__ */ jsx("svg", { className: "size-7", viewBox: "0 0 256 256", fill: "currentColor", "aria-hidden": "true", children: /* @__PURE__ */ jsx("path", { d: "M128 24a104 104 0 1 0 104 104A104.11 104.11 0 0 0 128 24Zm0 192a88 88 0 1 1 88-88 88.1 88.1 0 0 1-88 88Zm-8-80V80a8 8 0 0 1 16 0v56a8 8 0 0 1-16 0Zm20 36a12 12 0 1 1-12-12 12 12 0 0 1 12 12Z" }) }) }), /* @__PURE__ */ jsxs("div", { className: "flex flex-col gap-3", children: [/* @__PURE__ */ jsx("h1", { className: "text-3xl font-semibold text-foreground", children: messages?.title ?? "This page didn’t load" }), /* @__PURE__ */ jsx("p", { className: "text-base text-muted-foreground", children: messages?.body ?? "Something went wrong on our side. Try again, or head back home." })] }), /* @__PURE__ */ jsxs("div", { className: "flex flex-wrap justify-center gap-3", children: [/* @__PURE__ */ jsx("a", { href: "/", "data-testid": "router-error-home", className: "inline-flex h-9 items-center justify-center rounded-md bg-primary px-4 text-sm font-medium text-primary-foreground", children: messages?.home ?? "Back home" }), /* @__PURE__ */ jsx("button", { type: "button", onClick: () => reset ? reset() : window.location.reload(), "data-testid": "router-error-retry", className: "inline-flex h-9 items-center justify-center rounded-md border border-border bg-background px-4 text-sm font-medium text-foreground", children: messages?.retry ?? "Try again" })] }), showDetails && /* @__PURE__ */ jsxs("details", { className: "w-full text-left text-sm text-muted-foreground", children: [/* @__PURE__ */ jsx("summary", { className: "cursor-pointer text-center", children: "Error details" }), /* @__PURE__ */ jsx("pre", { className: "mt-3 overflow-x-auto whitespace-pre-wrap rounded-lg bg-muted p-4 font-mono text-xs", children: error.message })] }) ] }) }); } //#endregion export { RouterError, shouldShowErrorDetails }; //# sourceMappingURL=router-error.mjs.map