@rpcbase/client 0.290.0 → 0.291.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/index.d.ts CHANGED
@@ -4,4 +4,5 @@ export * from './types';
4
4
  export * from './getFeatureFlag';
5
5
  export * from './RootProvider';
6
6
  export * from './hooks';
7
+ export * from './ssrErrorState';
7
8
  //# sourceMappingURL=index.d.ts.map
@@ -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"}
package/dist/index.js CHANGED
@@ -77,6 +77,32 @@ 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
+ };
80
106
  const isProduction = globalThis.__rb_env__.MODE === "production";
81
107
  const showErrorOverlay = (err) => {
82
108
  const ErrorOverlay = customElements.get("vite-error-overlay");
@@ -98,7 +124,34 @@ const handleServerErrors = () => {
98
124
  });
99
125
  }
100
126
  };
127
+ const getRootElement = () => {
128
+ const el = document.getElementById("root");
129
+ if (!el) {
130
+ throw new Error("Root element #root not found");
131
+ }
132
+ return el;
133
+ };
134
+ const hydrateSsrFallbackIfPresent = (rootElement, renderSsrErrorFallback) => {
135
+ const ssrErrorState = peekClientSsrErrorState();
136
+ if (!ssrErrorState) {
137
+ return false;
138
+ }
139
+ const fallback = renderSsrErrorFallback?.(ssrErrorState);
140
+ if (!fallback) {
141
+ return false;
142
+ }
143
+ consumeClientSsrErrorState();
144
+ hydrateRoot(
145
+ rootElement,
146
+ /* @__PURE__ */ jsx(StrictMode, { children: fallback })
147
+ );
148
+ return true;
149
+ };
101
150
  const initWithRoutes = async (routesElement, opts) => {
151
+ const rootElement = getRootElement();
152
+ if (hydrateSsrFallbackIfPresent(rootElement, opts?.renderSsrErrorFallback)) {
153
+ return;
154
+ }
102
155
  await initApiClient();
103
156
  cleanupURL();
104
157
  handleServerErrors();
@@ -143,7 +196,7 @@ const initWithRoutes = async (routesElement, opts) => {
143
196
  }
144
197
  } : void 0;
145
198
  hydrateRoot(
146
- document.getElementById("root"),
199
+ rootElement,
147
200
  /* @__PURE__ */ jsx(StrictMode, { children: /* @__PURE__ */ jsx(RouterProvider, { router }) }),
148
201
  hydrationOptions
149
202
  );
@@ -1516,10 +1569,14 @@ const useMediaQuery = (query) => {
1516
1569
  };
1517
1570
  export {
1518
1571
  RootProvider,
1572
+ SSR_ERROR_STATE_GLOBAL_KEY,
1519
1573
  apiClient,
1574
+ consumeClientSsrErrorState,
1520
1575
  getFeatureFlag,
1521
1576
  initApiClient,
1522
1577
  initWithRoutes,
1578
+ peekClientSsrErrorState,
1579
+ serializeSsrErrorState,
1523
1580
  useMediaQuery,
1524
1581
  useThrottledMeasure
1525
1582
  };
@@ -1,6 +1,9 @@
1
+ import { ReactElement } from 'react';
1
2
  import { createRoutesFromElements } from '../../router/src';
3
+ import { SsrErrorStatePayload } from './ssrErrorState';
2
4
  type InitWithRoutesOptions = {
3
5
  devThrowsOnHydrationErrors?: boolean;
6
+ renderSsrErrorFallback?: (state: SsrErrorStatePayload) => ReactElement | null;
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":"AAEA,OAAO,EAAsB,wBAAwB,EAAiB,MAAM,iBAAiB,CAAA;AAqC7F,KAAK,qBAAqB,GAAG;IAC3B,0BAA0B,CAAC,EAAE,OAAO,CAAA;CACrC,CAAA;AAED,KAAK,aAAa,GAAG,UAAU,CAAC,OAAO,wBAAwB,CAAC,CAAC,CAAC,CAAC,CAAA;AAEnE,eAAO,MAAM,cAAc,GACzB,eAAe,aAAa,EAC5B,OAAO,qBAAqB,kBA0E7B,CAAA"}
1
+ {"version":3,"file":"initWithRoutes.d.ts","sourceRoot":"","sources":["../src/initWithRoutes.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAc,MAAM,OAAO,CAAA;AAEhD,OAAO,EAAsB,wBAAwB,EAAiB,MAAM,iBAAiB,CAAA;AAK7F,OAAO,EAGL,oBAAoB,EACrB,MAAM,iBAAiB,CAAA;AAiCxB,KAAK,qBAAqB,GAAG;IAC3B,0BAA0B,CAAC,EAAE,OAAO,CAAA;IACpC,sBAAsB,CAAC,EAAE,CAAC,KAAK,EAAE,oBAAoB,KAAK,YAAY,GAAG,IAAI,CAAA;CAC9E,CAAA;AAED,KAAK,aAAa,GAAG,UAAU,CAAC,OAAO,wBAAwB,CAAC,CAAC,CAAC,CAAC,CAAA;AAkCnE,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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@rpcbase/client",
3
- "version": "0.290.0",
3
+ "version": "0.291.0",
4
4
  "type": "module",
5
5
  "files": [
6
6
  "dist"