@rpcbase/client 0.290.0 → 0.292.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.
- package/dist/components/RouteErrorBoundary.d.ts +9 -0
- package/dist/components/RouteErrorBoundary.d.ts.map +1 -0
- package/dist/components/SsrErrorFallback.d.ts +10 -0
- package/dist/components/SsrErrorFallback.d.ts.map +1 -0
- package/dist/index.d.ts +3 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +131 -3
- package/dist/initWithRoutes.d.ts +3 -0
- package/dist/initWithRoutes.d.ts.map +1 -1
- package/dist/ssrErrorState.d.ts +11 -0
- package/dist/ssrErrorState.d.ts.map +1 -0
- package/package.json +1 -1
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import { ReactNode } from 'react';
|
|
2
|
+
import { SsrErrorStatePayload } from '../ssrErrorState';
|
|
3
|
+
type RenderErrorExtra = (state: SsrErrorStatePayload) => ReactNode;
|
|
4
|
+
type RouteErrorBoundaryProps = {
|
|
5
|
+
renderErrorExtra?: RenderErrorExtra;
|
|
6
|
+
};
|
|
7
|
+
export declare const RouteErrorBoundary: ({ renderErrorExtra }: RouteErrorBoundaryProps) => import("react/jsx-runtime").JSX.Element;
|
|
8
|
+
export {};
|
|
9
|
+
//# sourceMappingURL=RouteErrorBoundary.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"RouteErrorBoundary.d.ts","sourceRoot":"","sources":["../../src/components/RouteErrorBoundary.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,MAAM,OAAO,CAAA;AAIjC,OAAO,EAAE,oBAAoB,EAAE,MAAM,kBAAkB,CAAA;AAGvD,KAAK,gBAAgB,GAAG,CAAC,KAAK,EAAE,oBAAoB,KAAK,SAAS,CAAA;AAElE,KAAK,uBAAuB,GAAG;IAC7B,gBAAgB,CAAC,EAAE,gBAAgB,CAAA;CACpC,CAAA;AAkDD,eAAO,MAAM,kBAAkB,GAAI,sBAAsB,uBAAuB,4CAU/E,CAAA"}
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import { ReactNode } from 'react';
|
|
2
|
+
import { SsrErrorStatePayload } from '../ssrErrorState';
|
|
3
|
+
type RenderErrorExtra = (state: SsrErrorStatePayload) => ReactNode;
|
|
4
|
+
type SsrErrorFallbackProps = {
|
|
5
|
+
state: SsrErrorStatePayload;
|
|
6
|
+
renderErrorExtra?: RenderErrorExtra;
|
|
7
|
+
};
|
|
8
|
+
export declare const SsrErrorFallback: ({ state, renderErrorExtra }: SsrErrorFallbackProps) => import("react/jsx-runtime").JSX.Element;
|
|
9
|
+
export {};
|
|
10
|
+
//# sourceMappingURL=SsrErrorFallback.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"SsrErrorFallback.d.ts","sourceRoot":"","sources":["../../src/components/SsrErrorFallback.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,MAAM,OAAO,CAAA;AAEjC,OAAO,EAAE,oBAAoB,EAAE,MAAM,kBAAkB,CAAA;AAGvD,KAAK,gBAAgB,GAAG,CAAC,KAAK,EAAE,oBAAoB,KAAK,SAAS,CAAA;AAElE,KAAK,qBAAqB,GAAG;IAC3B,KAAK,EAAE,oBAAoB,CAAA;IAC3B,gBAAgB,CAAC,EAAE,gBAAgB,CAAA;CACpC,CAAA;AAKD,eAAO,MAAM,gBAAgB,GAAI,6BAA6B,qBAAqB,4CAoClF,CAAA"}
|
package/dist/index.d.ts
CHANGED
|
@@ -4,4 +4,7 @@ export * from './types';
|
|
|
4
4
|
export * from './getFeatureFlag';
|
|
5
5
|
export * from './RootProvider';
|
|
6
6
|
export * from './hooks';
|
|
7
|
+
export * from './ssrErrorState';
|
|
8
|
+
export * from './components/SsrErrorFallback';
|
|
9
|
+
export * from './components/RouteErrorBoundary';
|
|
7
10
|
//# sourceMappingURL=index.d.ts.map
|
package/dist/index.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,cAAc,aAAa,CAAA;AAC3B,cAAc,kBAAkB,CAAA;AAChC,cAAc,SAAS,CAAA;AACvB,cAAc,kBAAkB,CAAA;AAChC,cAAc,gBAAgB,CAAA;AAC9B,cAAc,SAAS,CAAA"}
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,cAAc,aAAa,CAAA;AAC3B,cAAc,kBAAkB,CAAA;AAChC,cAAc,SAAS,CAAA;AACvB,cAAc,kBAAkB,CAAA;AAChC,cAAc,gBAAgB,CAAA;AAC9B,cAAc,SAAS,CAAA;AACvB,cAAc,iBAAiB,CAAA;AAC/B,cAAc,+BAA+B,CAAA;AAC7C,cAAc,iCAAiC,CAAA"}
|
package/dist/index.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
import { jsx } from "react/jsx-runtime";
|
|
1
|
+
import { jsx, jsxs } from "react/jsx-runtime";
|
|
2
2
|
import { StrictMode, useRef, useEffect, useCallback, useState, useSyncExternalStore } from "react";
|
|
3
3
|
import posthog from "posthog-js";
|
|
4
|
-
import { createRoutesFromElements, createBrowserRouter, RouterProvider, useLocation } from "@rpcbase/router";
|
|
4
|
+
import { createRoutesFromElements, createBrowserRouter, RouterProvider, useLocation, useRouteError, isRouteErrorResponse } from "@rpcbase/router";
|
|
5
5
|
import { hydrateRoot } from "react-dom/client";
|
|
6
6
|
import { PostHogProvider } from "posthog-js/react/dist/esm/index.js";
|
|
7
7
|
import useMeasure from "react-use/esm/useMeasure.js";
|
|
@@ -77,6 +77,53 @@ const cleanupURL = () => {
|
|
|
77
77
|
document.addEventListener("DOMContentLoaded", runCleanup, { once: true });
|
|
78
78
|
}
|
|
79
79
|
};
|
|
80
|
+
const SSR_ERROR_STATE_GLOBAL_KEY = "__RPCBASE_SSR_ERROR__";
|
|
81
|
+
const ESCAPED_LT = /</g;
|
|
82
|
+
const ESCAPED_U2028 = /\u2028/g;
|
|
83
|
+
const ESCAPED_U2029 = /\u2029/g;
|
|
84
|
+
const serializeSsrErrorState = (state) => JSON.stringify(state).replace(ESCAPED_LT, "\\u003c").replace(ESCAPED_U2028, "\\u2028").replace(ESCAPED_U2029, "\\u2029");
|
|
85
|
+
const peekClientSsrErrorState = () => {
|
|
86
|
+
if (typeof window === "undefined") {
|
|
87
|
+
return null;
|
|
88
|
+
}
|
|
89
|
+
const globalScope = window;
|
|
90
|
+
const state = globalScope[SSR_ERROR_STATE_GLOBAL_KEY];
|
|
91
|
+
if (state && typeof state === "object") {
|
|
92
|
+
return state;
|
|
93
|
+
}
|
|
94
|
+
return null;
|
|
95
|
+
};
|
|
96
|
+
const consumeClientSsrErrorState = () => {
|
|
97
|
+
const state = peekClientSsrErrorState();
|
|
98
|
+
if (!state) {
|
|
99
|
+
return null;
|
|
100
|
+
}
|
|
101
|
+
if (typeof window !== "undefined") {
|
|
102
|
+
delete window[SSR_ERROR_STATE_GLOBAL_KEY];
|
|
103
|
+
}
|
|
104
|
+
return state;
|
|
105
|
+
};
|
|
106
|
+
const DEFAULT_TITLE = "Something went wrong";
|
|
107
|
+
const DEFAULT_MESSAGE = "We couldn't render this page. Please try again in a few seconds.";
|
|
108
|
+
const SsrErrorFallback = ({ state, renderErrorExtra }) => {
|
|
109
|
+
const {
|
|
110
|
+
statusCode = 500,
|
|
111
|
+
title = DEFAULT_TITLE,
|
|
112
|
+
message = DEFAULT_MESSAGE,
|
|
113
|
+
details
|
|
114
|
+
} = state;
|
|
115
|
+
const extra = renderErrorExtra?.(state);
|
|
116
|
+
return /* @__PURE__ */ jsx("div", { className: "bg-white min-h-screen", children: /* @__PURE__ */ jsxs("main", { className: "mx-auto flex min-h-screen max-w-2xl flex-col items-center justify-center px-6 py-12 text-center sm:py-24", children: [
|
|
117
|
+
/* @__PURE__ */ jsx("p", { className: "text-base font-semibold text-rose-600", children: statusCode }),
|
|
118
|
+
/* @__PURE__ */ jsx("h1", { className: "mt-4 text-pretty text-4xl font-semibold tracking-tight text-gray-900 sm:text-5xl", children: title }),
|
|
119
|
+
/* @__PURE__ */ jsx("p", { className: "mt-6 text-lg text-gray-600 sm:text-xl/relaxed", children: message }),
|
|
120
|
+
details ? /* @__PURE__ */ jsxs("div", { className: "mt-10 w-full rounded-2xl bg-gray-900/95 p-5 text-left shadow-2xl", children: [
|
|
121
|
+
/* @__PURE__ */ jsx("p", { className: "text-sm font-semibold uppercase tracking-wide text-gray-400", children: "Debug details" }),
|
|
122
|
+
/* @__PURE__ */ jsx("pre", { className: "mt-3 max-h-64 overflow-auto whitespace-pre-wrap text-sm text-gray-100", children: details })
|
|
123
|
+
] }) : null,
|
|
124
|
+
extra ? /* @__PURE__ */ jsx("div", { className: "mt-10 flex flex-col gap-4 sm:flex-row sm:items-center sm:justify-center", children: extra }) : null
|
|
125
|
+
] }) });
|
|
126
|
+
};
|
|
80
127
|
const isProduction = globalThis.__rb_env__.MODE === "production";
|
|
81
128
|
const showErrorOverlay = (err) => {
|
|
82
129
|
const ErrorOverlay = customElements.get("vite-error-overlay");
|
|
@@ -98,7 +145,30 @@ const handleServerErrors = () => {
|
|
|
98
145
|
});
|
|
99
146
|
}
|
|
100
147
|
};
|
|
148
|
+
const getRootElement = () => {
|
|
149
|
+
const el = document.getElementById("root");
|
|
150
|
+
if (!el) {
|
|
151
|
+
throw new Error("Root element #root not found");
|
|
152
|
+
}
|
|
153
|
+
return el;
|
|
154
|
+
};
|
|
155
|
+
const hydrateSsrFallbackIfPresent = (rootElement, renderErrorExtra) => {
|
|
156
|
+
const ssrErrorState = peekClientSsrErrorState();
|
|
157
|
+
if (!ssrErrorState) {
|
|
158
|
+
return false;
|
|
159
|
+
}
|
|
160
|
+
consumeClientSsrErrorState();
|
|
161
|
+
hydrateRoot(
|
|
162
|
+
rootElement,
|
|
163
|
+
/* @__PURE__ */ jsx(StrictMode, { children: /* @__PURE__ */ jsx(SsrErrorFallback, { state: ssrErrorState, renderErrorExtra }) })
|
|
164
|
+
);
|
|
165
|
+
return true;
|
|
166
|
+
};
|
|
101
167
|
const initWithRoutes = async (routesElement, opts) => {
|
|
168
|
+
const rootElement = getRootElement();
|
|
169
|
+
if (hydrateSsrFallbackIfPresent(rootElement, opts?.renderErrorExtra)) {
|
|
170
|
+
return;
|
|
171
|
+
}
|
|
102
172
|
await initApiClient();
|
|
103
173
|
cleanupURL();
|
|
104
174
|
handleServerErrors();
|
|
@@ -143,7 +213,7 @@ const initWithRoutes = async (routesElement, opts) => {
|
|
|
143
213
|
}
|
|
144
214
|
} : void 0;
|
|
145
215
|
hydrateRoot(
|
|
146
|
-
|
|
216
|
+
rootElement,
|
|
147
217
|
/* @__PURE__ */ jsx(StrictMode, { children: /* @__PURE__ */ jsx(RouterProvider, { router }) }),
|
|
148
218
|
hydrationOptions
|
|
149
219
|
);
|
|
@@ -1514,12 +1584,70 @@ const useMediaQuery = (query) => {
|
|
|
1514
1584
|
};
|
|
1515
1585
|
return useSyncExternalStore(subscribe, getSnapshot, () => false);
|
|
1516
1586
|
};
|
|
1587
|
+
const defaultState = {
|
|
1588
|
+
statusCode: 500,
|
|
1589
|
+
title: "Something went wrong",
|
|
1590
|
+
message: "We couldn't render this route. Please try again shortly."
|
|
1591
|
+
};
|
|
1592
|
+
const toSsrErrorState = (error) => {
|
|
1593
|
+
if (isRouteErrorResponse(error)) {
|
|
1594
|
+
const data = error.data;
|
|
1595
|
+
const message = typeof data === "string" ? data : data?.message || defaultState.message;
|
|
1596
|
+
let details;
|
|
1597
|
+
if (globalThis.__rb_env__.DEV && data && typeof data !== "string") {
|
|
1598
|
+
try {
|
|
1599
|
+
details = JSON.stringify(data, null, 2);
|
|
1600
|
+
} catch {
|
|
1601
|
+
details = void 0;
|
|
1602
|
+
}
|
|
1603
|
+
}
|
|
1604
|
+
return {
|
|
1605
|
+
statusCode: error.status ?? defaultState.statusCode,
|
|
1606
|
+
title: error.statusText || defaultState.title,
|
|
1607
|
+
message,
|
|
1608
|
+
details
|
|
1609
|
+
};
|
|
1610
|
+
}
|
|
1611
|
+
if (error instanceof Error) {
|
|
1612
|
+
return {
|
|
1613
|
+
statusCode: defaultState.statusCode,
|
|
1614
|
+
title: defaultState.title,
|
|
1615
|
+
message: error.message || defaultState.message,
|
|
1616
|
+
details: globalThis.__rb_env__.DEV ? error.stack ?? error.message : void 0
|
|
1617
|
+
};
|
|
1618
|
+
}
|
|
1619
|
+
if (typeof error === "string") {
|
|
1620
|
+
return {
|
|
1621
|
+
statusCode: defaultState.statusCode,
|
|
1622
|
+
title: defaultState.title,
|
|
1623
|
+
message: error
|
|
1624
|
+
};
|
|
1625
|
+
}
|
|
1626
|
+
return defaultState;
|
|
1627
|
+
};
|
|
1628
|
+
const RouteErrorBoundary = ({ renderErrorExtra }) => {
|
|
1629
|
+
const routeError = useRouteError();
|
|
1630
|
+
const state = toSsrErrorState(routeError);
|
|
1631
|
+
return /* @__PURE__ */ jsx(
|
|
1632
|
+
SsrErrorFallback,
|
|
1633
|
+
{
|
|
1634
|
+
state,
|
|
1635
|
+
renderErrorExtra
|
|
1636
|
+
}
|
|
1637
|
+
);
|
|
1638
|
+
};
|
|
1517
1639
|
export {
|
|
1518
1640
|
RootProvider,
|
|
1641
|
+
RouteErrorBoundary,
|
|
1642
|
+
SSR_ERROR_STATE_GLOBAL_KEY,
|
|
1643
|
+
SsrErrorFallback,
|
|
1519
1644
|
apiClient,
|
|
1645
|
+
consumeClientSsrErrorState,
|
|
1520
1646
|
getFeatureFlag,
|
|
1521
1647
|
initApiClient,
|
|
1522
1648
|
initWithRoutes,
|
|
1649
|
+
peekClientSsrErrorState,
|
|
1650
|
+
serializeSsrErrorState,
|
|
1523
1651
|
useMediaQuery,
|
|
1524
1652
|
useThrottledMeasure
|
|
1525
1653
|
};
|
package/dist/initWithRoutes.d.ts
CHANGED
|
@@ -1,6 +1,9 @@
|
|
|
1
|
+
import { ReactNode } from 'react';
|
|
1
2
|
import { createRoutesFromElements } from '../../router/src';
|
|
3
|
+
import { SsrErrorStatePayload } from './ssrErrorState';
|
|
2
4
|
type InitWithRoutesOptions = {
|
|
3
5
|
devThrowsOnHydrationErrors?: boolean;
|
|
6
|
+
renderErrorExtra?: (state: SsrErrorStatePayload) => ReactNode;
|
|
4
7
|
};
|
|
5
8
|
type RoutesElement = Parameters<typeof createRoutesFromElements>[0];
|
|
6
9
|
export declare const initWithRoutes: (routesElement: RoutesElement, opts?: InitWithRoutesOptions) => Promise<void>;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"initWithRoutes.d.ts","sourceRoot":"","sources":["../src/initWithRoutes.tsx"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"initWithRoutes.d.ts","sourceRoot":"","sources":["../src/initWithRoutes.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAc,MAAM,OAAO,CAAA;AAE7C,OAAO,EAAsB,wBAAwB,EAAiB,MAAM,iBAAiB,CAAA;AAK7F,OAAO,EAGL,oBAAoB,EACrB,MAAM,iBAAiB,CAAA;AAkCxB,KAAK,qBAAqB,GAAG;IAC3B,0BAA0B,CAAC,EAAE,OAAO,CAAA;IACpC,gBAAgB,CAAC,EAAE,CAAC,KAAK,EAAE,oBAAoB,KAAK,SAAS,CAAA;CAC9D,CAAA;AAED,KAAK,aAAa,GAAG,UAAU,CAAC,OAAO,wBAAwB,CAAC,CAAC,CAAC,CAAC,CAAA;AA8BnE,eAAO,MAAM,cAAc,GACzB,eAAe,aAAa,EAC5B,OAAO,qBAAqB,kBA+E7B,CAAA"}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
export declare const SSR_ERROR_STATE_GLOBAL_KEY = "__RPCBASE_SSR_ERROR__";
|
|
2
|
+
export type SsrErrorStatePayload = {
|
|
3
|
+
statusCode?: number;
|
|
4
|
+
title?: string;
|
|
5
|
+
message?: string;
|
|
6
|
+
details?: string;
|
|
7
|
+
};
|
|
8
|
+
export declare const serializeSsrErrorState: (state: SsrErrorStatePayload) => string;
|
|
9
|
+
export declare const peekClientSsrErrorState: () => SsrErrorStatePayload | null;
|
|
10
|
+
export declare const consumeClientSsrErrorState: () => SsrErrorStatePayload | null;
|
|
11
|
+
//# sourceMappingURL=ssrErrorState.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"ssrErrorState.d.ts","sourceRoot":"","sources":["../src/ssrErrorState.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,0BAA0B,0BAA0B,CAAA;AAEjE,MAAM,MAAM,oBAAoB,GAAG;IACjC,UAAU,CAAC,EAAE,MAAM,CAAA;IACnB,KAAK,CAAC,EAAE,MAAM,CAAA;IACd,OAAO,CAAC,EAAE,MAAM,CAAA;IAChB,OAAO,CAAC,EAAE,MAAM,CAAA;CACjB,CAAA;AAMD,eAAO,MAAM,sBAAsB,GAAI,OAAO,oBAAoB,KAAG,MAI/B,CAAA;AAEtC,eAAO,MAAM,uBAAuB,QAAO,oBAAoB,GAAG,IAUjE,CAAA;AAED,eAAO,MAAM,0BAA0B,QAAO,oBAAoB,GAAG,IASpE,CAAA"}
|