hadars 0.1.35 → 0.1.37

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.
@@ -0,0 +1,188 @@
1
+ import { MetaHTMLAttributes, LinkHTMLAttributes, StyleHTMLAttributes, ScriptHTMLAttributes } from 'react';
2
+
3
+ type HadarsGetInitialProps<T extends {}> = (req: HadarsRequest) => Promise<T> | T;
4
+ type HadarsGetClientProps<T extends {}> = (props: T) => Promise<T> | T;
5
+ type HadarsGetAfterRenderProps<T extends {}> = (props: HadarsProps<T>, html: string) => Promise<HadarsProps<T>> | HadarsProps<T>;
6
+ type HadarsGetFinalProps<T extends {}> = (props: HadarsProps<T>) => Promise<T> | T;
7
+ type HadarsApp<T extends {}> = React.FC<HadarsProps<T>>;
8
+ type HadarsEntryModule<T extends {}> = {
9
+ default: HadarsApp<T>;
10
+ getInitProps?: HadarsGetInitialProps<T>;
11
+ getAfterRenderProps?: HadarsGetAfterRenderProps<T>;
12
+ getFinalProps?: HadarsGetFinalProps<T>;
13
+ getClientProps?: HadarsGetClientProps<T>;
14
+ };
15
+ interface AppHead {
16
+ title: string;
17
+ status: number;
18
+ meta: Record<string, MetaProps>;
19
+ link: Record<string, LinkProps>;
20
+ style: Record<string, StyleProps>;
21
+ script: Record<string, ScriptProps>;
22
+ }
23
+ type UnsuspendEntry = {
24
+ status: 'pending';
25
+ promise: Promise<unknown>;
26
+ } | {
27
+ status: 'fulfilled';
28
+ value: unknown;
29
+ } | {
30
+ status: 'rejected';
31
+ reason: unknown;
32
+ };
33
+ /** @internal Populated by the framework's render loop — use useServerData() instead. */
34
+ interface AppUnsuspend {
35
+ cache: Map<string, UnsuspendEntry>;
36
+ }
37
+ interface AppContext {
38
+ path?: string;
39
+ head: AppHead;
40
+ /** @internal Framework use only — use the useServerData() hook instead. */
41
+ _unsuspend?: AppUnsuspend;
42
+ }
43
+ type HadarsEntryBase = {
44
+ location: string;
45
+ context: AppContext;
46
+ };
47
+ type HadarsProps<T extends {}> = T & HadarsEntryBase;
48
+ type MetaProps = MetaHTMLAttributes<HTMLMetaElement>;
49
+ type LinkProps = LinkHTMLAttributes<HTMLLinkElement>;
50
+ type StyleProps = StyleHTMLAttributes<HTMLStyleElement>;
51
+ type ScriptProps = ScriptHTMLAttributes<HTMLScriptElement>;
52
+ interface HadarsOptions {
53
+ port?: number;
54
+ entry: string;
55
+ baseURL?: string;
56
+ swcPlugins?: SwcPluginList;
57
+ proxy?: Record<string, string> | ((req: HadarsRequest) => Promise<Response | null> | Response | null);
58
+ proxyCORS?: boolean;
59
+ define?: Record<string, string>;
60
+ /**
61
+ * Bun WebSocket handler passed directly to `Bun.serve()`.
62
+ * Ignored on Node.js and Deno — use `fetch` + a third-party WS library there.
63
+ * Pass a `Bun.WebSocketHandler` instance here when running on Bun.
64
+ */
65
+ websocket?: unknown;
66
+ fetch?: (req: HadarsRequest) => Promise<Response | undefined> | Response | undefined;
67
+ wsPath?: string;
68
+ hmrPort?: number;
69
+ /**
70
+ * Parallelism level for `run()` mode (production server). Defaults to 1.
71
+ * Has no effect in `dev()` mode.
72
+ *
73
+ * **Node.js** — forks this many worker processes via `node:cluster`, each
74
+ * binding to the same port via OS round-robin. Set to `os.cpus().length`
75
+ * to saturate all CPU cores.
76
+ *
77
+ * **Bun / Deno** — creates a `node:worker_threads` render pool of this size.
78
+ * Each thread handles the synchronous `renderToString` step, freeing the
79
+ * main event loop for I/O.
80
+ */
81
+ workers?: number;
82
+ /**
83
+ * Override or extend rspack's `optimization` config for production client builds.
84
+ * Merged on top of hadars defaults (splitChunks vendor splitting, deterministic moduleIds).
85
+ * Has no effect on the SSR bundle or dev mode.
86
+ */
87
+ optimization?: Record<string, unknown>;
88
+ /**
89
+ * Path to a custom HTML template file (relative to the project root).
90
+ * Replaces the built-in minimal template used to generate the HTML shell.
91
+ *
92
+ * The file must include two marker elements so hadars can inject the
93
+ * per-request head tags and the server-rendered body:
94
+ *
95
+ * ```html
96
+ * <meta name="HADARS_HEAD"> <!-- replaced with <title>, <meta>, <link>, <style> tags -->
97
+ * <meta name="HADARS_BODY"> <!-- replaced with the SSR-rendered React tree -->
98
+ * ```
99
+ *
100
+ * Any `<style>` blocks in the template are automatically processed through
101
+ * PostCSS (using the project's `postcss.config.js`) at build/dev startup time,
102
+ * so `@import "tailwindcss"` and other PostCSS directives work as expected.
103
+ * Note: inline styles are processed once at startup and are not live-reloaded.
104
+ */
105
+ htmlTemplate?: string;
106
+ /**
107
+ * Force the React runtime mode independently of the build mode.
108
+ * Useful when you need production build optimizations (minification, tree-shaking)
109
+ * but want React's development build for debugging hydration mismatches or
110
+ * component stack traces.
111
+ *
112
+ * - `'development'` — forces `process.env.NODE_ENV = "development"` and enables
113
+ * JSX source info even in `hadars build`. React prints detailed hydration error
114
+ * messages and component stacks.
115
+ * - `'production'` — the default; React uses the optimised production bundle.
116
+ *
117
+ * Only affects the **client** bundle. The SSR bundle always uses slim-react.
118
+ *
119
+ * @example
120
+ * // hadars.config.ts — debug hydration errors in a production build
121
+ * reactMode: 'development'
122
+ */
123
+ reactMode?: 'development' | 'production';
124
+ /**
125
+ * Additional rspack module rules appended to the built-in rule set.
126
+ * Applied to both the client and the SSR bundle.
127
+ *
128
+ * Useful for loaders not included by default, such as `@mdx-js/loader`,
129
+ * `less-loader`, `yaml-loader`, etc.
130
+ *
131
+ * @example
132
+ * moduleRules: [
133
+ * {
134
+ * test: /\.mdx?$/,
135
+ * use: [{ loader: '@mdx-js/loader' }],
136
+ * },
137
+ * ]
138
+ */
139
+ moduleRules?: Record<string, any>[];
140
+ /**
141
+ * Additional rspack/webpack-compatible plugins applied to both the client
142
+ * and SSR bundles. Any object that implements the `apply(compiler)` method
143
+ * (the standard webpack/rspack plugin interface) is accepted.
144
+ *
145
+ * @example
146
+ * import { SubresourceIntegrityPlugin } from 'webpack-subresource-integrity';
147
+ * plugins: [new SubresourceIntegrityPlugin()]
148
+ */
149
+ plugins?: Array<{
150
+ apply(compiler: any): void;
151
+ }>;
152
+ /**
153
+ * SSR response cache for `run()` mode. Has no effect in `dev()` mode.
154
+ *
155
+ * Receives the incoming request and should return `{ key, ttl? }` to cache
156
+ * the response, or `null`/`undefined` to skip caching for that request.
157
+ * `ttl` is the time-to-live in milliseconds; omit for entries that never expire.
158
+ * The function may be async.
159
+ *
160
+ * @example
161
+ * // Cache every page by pathname (no per-user personalisation):
162
+ * cache: (req) => ({ key: req.pathname })
163
+ *
164
+ * @example
165
+ * // Cache with a per-route TTL, skip authenticated requests:
166
+ * cache: (req) => req.cookies.session ? null : { key: req.pathname, ttl: 60_000 }
167
+ */
168
+ cache?: (req: HadarsRequest) => {
169
+ key: string;
170
+ ttl?: number;
171
+ } | null | undefined | Promise<{
172
+ key: string;
173
+ ttl?: number;
174
+ } | null | undefined>;
175
+ }
176
+ type SwcPluginItem = string | [string, Record<string, unknown>] | {
177
+ path: string;
178
+ options?: Record<string, unknown>;
179
+ } | ((...args: any[]) => any);
180
+ type SwcPluginList = SwcPluginItem[];
181
+ interface HadarsRequest extends Request {
182
+ pathname: string;
183
+ search: string;
184
+ location: string;
185
+ cookies: Record<string, string>;
186
+ }
187
+
188
+ export type { AppContext as A, HadarsEntryModule as H, HadarsOptions as a, HadarsApp as b, HadarsGetAfterRenderProps as c, HadarsGetClientProps as d, HadarsGetFinalProps as e, HadarsGetInitialProps as f, HadarsProps as g, HadarsRequest as h };
@@ -0,0 +1,188 @@
1
+ import { MetaHTMLAttributes, LinkHTMLAttributes, StyleHTMLAttributes, ScriptHTMLAttributes } from 'react';
2
+
3
+ type HadarsGetInitialProps<T extends {}> = (req: HadarsRequest) => Promise<T> | T;
4
+ type HadarsGetClientProps<T extends {}> = (props: T) => Promise<T> | T;
5
+ type HadarsGetAfterRenderProps<T extends {}> = (props: HadarsProps<T>, html: string) => Promise<HadarsProps<T>> | HadarsProps<T>;
6
+ type HadarsGetFinalProps<T extends {}> = (props: HadarsProps<T>) => Promise<T> | T;
7
+ type HadarsApp<T extends {}> = React.FC<HadarsProps<T>>;
8
+ type HadarsEntryModule<T extends {}> = {
9
+ default: HadarsApp<T>;
10
+ getInitProps?: HadarsGetInitialProps<T>;
11
+ getAfterRenderProps?: HadarsGetAfterRenderProps<T>;
12
+ getFinalProps?: HadarsGetFinalProps<T>;
13
+ getClientProps?: HadarsGetClientProps<T>;
14
+ };
15
+ interface AppHead {
16
+ title: string;
17
+ status: number;
18
+ meta: Record<string, MetaProps>;
19
+ link: Record<string, LinkProps>;
20
+ style: Record<string, StyleProps>;
21
+ script: Record<string, ScriptProps>;
22
+ }
23
+ type UnsuspendEntry = {
24
+ status: 'pending';
25
+ promise: Promise<unknown>;
26
+ } | {
27
+ status: 'fulfilled';
28
+ value: unknown;
29
+ } | {
30
+ status: 'rejected';
31
+ reason: unknown;
32
+ };
33
+ /** @internal Populated by the framework's render loop — use useServerData() instead. */
34
+ interface AppUnsuspend {
35
+ cache: Map<string, UnsuspendEntry>;
36
+ }
37
+ interface AppContext {
38
+ path?: string;
39
+ head: AppHead;
40
+ /** @internal Framework use only — use the useServerData() hook instead. */
41
+ _unsuspend?: AppUnsuspend;
42
+ }
43
+ type HadarsEntryBase = {
44
+ location: string;
45
+ context: AppContext;
46
+ };
47
+ type HadarsProps<T extends {}> = T & HadarsEntryBase;
48
+ type MetaProps = MetaHTMLAttributes<HTMLMetaElement>;
49
+ type LinkProps = LinkHTMLAttributes<HTMLLinkElement>;
50
+ type StyleProps = StyleHTMLAttributes<HTMLStyleElement>;
51
+ type ScriptProps = ScriptHTMLAttributes<HTMLScriptElement>;
52
+ interface HadarsOptions {
53
+ port?: number;
54
+ entry: string;
55
+ baseURL?: string;
56
+ swcPlugins?: SwcPluginList;
57
+ proxy?: Record<string, string> | ((req: HadarsRequest) => Promise<Response | null> | Response | null);
58
+ proxyCORS?: boolean;
59
+ define?: Record<string, string>;
60
+ /**
61
+ * Bun WebSocket handler passed directly to `Bun.serve()`.
62
+ * Ignored on Node.js and Deno — use `fetch` + a third-party WS library there.
63
+ * Pass a `Bun.WebSocketHandler` instance here when running on Bun.
64
+ */
65
+ websocket?: unknown;
66
+ fetch?: (req: HadarsRequest) => Promise<Response | undefined> | Response | undefined;
67
+ wsPath?: string;
68
+ hmrPort?: number;
69
+ /**
70
+ * Parallelism level for `run()` mode (production server). Defaults to 1.
71
+ * Has no effect in `dev()` mode.
72
+ *
73
+ * **Node.js** — forks this many worker processes via `node:cluster`, each
74
+ * binding to the same port via OS round-robin. Set to `os.cpus().length`
75
+ * to saturate all CPU cores.
76
+ *
77
+ * **Bun / Deno** — creates a `node:worker_threads` render pool of this size.
78
+ * Each thread handles the synchronous `renderToString` step, freeing the
79
+ * main event loop for I/O.
80
+ */
81
+ workers?: number;
82
+ /**
83
+ * Override or extend rspack's `optimization` config for production client builds.
84
+ * Merged on top of hadars defaults (splitChunks vendor splitting, deterministic moduleIds).
85
+ * Has no effect on the SSR bundle or dev mode.
86
+ */
87
+ optimization?: Record<string, unknown>;
88
+ /**
89
+ * Path to a custom HTML template file (relative to the project root).
90
+ * Replaces the built-in minimal template used to generate the HTML shell.
91
+ *
92
+ * The file must include two marker elements so hadars can inject the
93
+ * per-request head tags and the server-rendered body:
94
+ *
95
+ * ```html
96
+ * <meta name="HADARS_HEAD"> <!-- replaced with <title>, <meta>, <link>, <style> tags -->
97
+ * <meta name="HADARS_BODY"> <!-- replaced with the SSR-rendered React tree -->
98
+ * ```
99
+ *
100
+ * Any `<style>` blocks in the template are automatically processed through
101
+ * PostCSS (using the project's `postcss.config.js`) at build/dev startup time,
102
+ * so `@import "tailwindcss"` and other PostCSS directives work as expected.
103
+ * Note: inline styles are processed once at startup and are not live-reloaded.
104
+ */
105
+ htmlTemplate?: string;
106
+ /**
107
+ * Force the React runtime mode independently of the build mode.
108
+ * Useful when you need production build optimizations (minification, tree-shaking)
109
+ * but want React's development build for debugging hydration mismatches or
110
+ * component stack traces.
111
+ *
112
+ * - `'development'` — forces `process.env.NODE_ENV = "development"` and enables
113
+ * JSX source info even in `hadars build`. React prints detailed hydration error
114
+ * messages and component stacks.
115
+ * - `'production'` — the default; React uses the optimised production bundle.
116
+ *
117
+ * Only affects the **client** bundle. The SSR bundle always uses slim-react.
118
+ *
119
+ * @example
120
+ * // hadars.config.ts — debug hydration errors in a production build
121
+ * reactMode: 'development'
122
+ */
123
+ reactMode?: 'development' | 'production';
124
+ /**
125
+ * Additional rspack module rules appended to the built-in rule set.
126
+ * Applied to both the client and the SSR bundle.
127
+ *
128
+ * Useful for loaders not included by default, such as `@mdx-js/loader`,
129
+ * `less-loader`, `yaml-loader`, etc.
130
+ *
131
+ * @example
132
+ * moduleRules: [
133
+ * {
134
+ * test: /\.mdx?$/,
135
+ * use: [{ loader: '@mdx-js/loader' }],
136
+ * },
137
+ * ]
138
+ */
139
+ moduleRules?: Record<string, any>[];
140
+ /**
141
+ * Additional rspack/webpack-compatible plugins applied to both the client
142
+ * and SSR bundles. Any object that implements the `apply(compiler)` method
143
+ * (the standard webpack/rspack plugin interface) is accepted.
144
+ *
145
+ * @example
146
+ * import { SubresourceIntegrityPlugin } from 'webpack-subresource-integrity';
147
+ * plugins: [new SubresourceIntegrityPlugin()]
148
+ */
149
+ plugins?: Array<{
150
+ apply(compiler: any): void;
151
+ }>;
152
+ /**
153
+ * SSR response cache for `run()` mode. Has no effect in `dev()` mode.
154
+ *
155
+ * Receives the incoming request and should return `{ key, ttl? }` to cache
156
+ * the response, or `null`/`undefined` to skip caching for that request.
157
+ * `ttl` is the time-to-live in milliseconds; omit for entries that never expire.
158
+ * The function may be async.
159
+ *
160
+ * @example
161
+ * // Cache every page by pathname (no per-user personalisation):
162
+ * cache: (req) => ({ key: req.pathname })
163
+ *
164
+ * @example
165
+ * // Cache with a per-route TTL, skip authenticated requests:
166
+ * cache: (req) => req.cookies.session ? null : { key: req.pathname, ttl: 60_000 }
167
+ */
168
+ cache?: (req: HadarsRequest) => {
169
+ key: string;
170
+ ttl?: number;
171
+ } | null | undefined | Promise<{
172
+ key: string;
173
+ ttl?: number;
174
+ } | null | undefined>;
175
+ }
176
+ type SwcPluginItem = string | [string, Record<string, unknown>] | {
177
+ path: string;
178
+ options?: Record<string, unknown>;
179
+ } | ((...args: any[]) => any);
180
+ type SwcPluginList = SwcPluginItem[];
181
+ interface HadarsRequest extends Request {
182
+ pathname: string;
183
+ search: string;
184
+ location: string;
185
+ cookies: Record<string, string>;
186
+ }
187
+
188
+ export type { AppContext as A, HadarsEntryModule as H, HadarsOptions as a, HadarsApp as b, HadarsGetAfterRenderProps as c, HadarsGetClientProps as d, HadarsGetFinalProps as e, HadarsGetInitialProps as f, HadarsProps as g, HadarsRequest as h };
package/dist/index.cjs CHANGED
@@ -28,8 +28,8 @@ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__ge
28
28
  var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
29
29
 
30
30
  // src/index.tsx
31
- var src_exports = {};
32
- __export(src_exports, {
31
+ var index_exports = {};
32
+ __export(index_exports, {
33
33
  CacheSegment: () => CacheSegment,
34
34
  HadarsContext: () => HadarsContext,
35
35
  HadarsHead: () => Head,
@@ -39,7 +39,7 @@ __export(src_exports, {
39
39
  loadModule: () => loadModule,
40
40
  useServerData: () => useServerData
41
41
  });
42
- module.exports = __toCommonJS(src_exports);
42
+ module.exports = __toCommonJS(index_exports);
43
43
 
44
44
  // src/utils/Head.tsx
45
45
  var import_react = __toESM(require("react"), 1);
@@ -179,8 +179,7 @@ var fetchedPaths = /* @__PURE__ */ new Set();
179
179
  var ssrInitialKeys = null;
180
180
  var unclaimedKeyCheckScheduled = false;
181
181
  function scheduleUnclaimedKeyCheck() {
182
- if (unclaimedKeyCheckScheduled)
183
- return;
182
+ if (unclaimedKeyCheckScheduled) return;
184
183
  unclaimedKeyCheckScheduled = true;
185
184
  setTimeout(() => {
186
185
  unclaimedKeyCheckScheduled = false;
@@ -241,13 +240,10 @@ function useServerData(key, fn) {
241
240
  throw pendingDataFetch.get(pathKey);
242
241
  }
243
242
  const unsuspend = globalThis.__hadarsUnsuspend;
244
- if (!unsuspend)
245
- return void 0;
243
+ if (!unsuspend) return void 0;
246
244
  const _u = unsuspend;
247
- if (!_u.seenThisPass)
248
- _u.seenThisPass = /* @__PURE__ */ new Set();
249
- if (!_u.seenLastPass)
250
- _u.seenLastPass = /* @__PURE__ */ new Set();
245
+ if (!_u.seenThisPass) _u.seenThisPass = /* @__PURE__ */ new Set();
246
+ if (!_u.seenLastPass) _u.seenLastPass = /* @__PURE__ */ new Set();
251
247
  if (_u.newPassStarting) {
252
248
  _u.seenLastPass = new Set(_u.seenThisPass);
253
249
  _u.seenThisPass.clear();
@@ -289,8 +285,7 @@ function useServerData(key, fn) {
289
285
  _u.newPassStarting = true;
290
286
  throw existing.promise;
291
287
  }
292
- if (existing.status === "rejected")
293
- throw existing.reason;
288
+ if (existing.status === "rejected") throw existing.reason;
294
289
  return existing.value;
295
290
  }
296
291
  var genRandomId = () => {
@@ -309,8 +304,7 @@ var Head = import_react.default.memo(({ children, status }) => {
309
304
  setStatus(status);
310
305
  }
311
306
  import_react.default.Children.forEach(children, (child) => {
312
- if (!import_react.default.isValidElement(child))
313
- return;
307
+ if (!import_react.default.isValidElement(child)) return;
314
308
  const childType = child.type;
315
309
  const childProps = child.props;
316
310
  const id = childProps["id"] || genRandomId();
@@ -357,8 +351,7 @@ function getStore() {
357
351
  }
358
352
  function getSegment(key) {
359
353
  const entry = getStore().get(key);
360
- if (!entry)
361
- return null;
354
+ if (!entry) return null;
362
355
  if (entry.expiresAt !== null && Date.now() >= entry.expiresAt) {
363
356
  getStore().delete(key);
364
357
  return null;
@@ -391,8 +384,7 @@ function CacheSegment({ cacheKey, ttl, children }) {
391
384
  "data-key": cacheKey,
392
385
  "data-cache": "miss"
393
386
  };
394
- if (ttl != null)
395
- props["data-ttl"] = ttl;
387
+ if (ttl != null) props["data-ttl"] = ttl;
396
388
  return import_react2.default.createElement(CACHE_TAG, props, children);
397
389
  }
398
390
 
@@ -0,0 +1,105 @@
1
+ import * as React$1 from 'react';
2
+ import React__default from 'react';
3
+ import { A as AppContext } from './hadars-B3b_6sj2.cjs';
4
+ export { b as HadarsApp, H as HadarsEntryModule, c as HadarsGetAfterRenderProps, d as HadarsGetClientProps, e as HadarsGetFinalProps, f as HadarsGetInitialProps, a as HadarsOptions, g as HadarsProps, h as HadarsRequest } from './hadars-B3b_6sj2.cjs';
5
+ import * as react_jsx_runtime from 'react/jsx-runtime';
6
+
7
+ /** Call this before hydrating to seed the client cache from the server's data.
8
+ * Invoked automatically by the hadars client bootstrap.
9
+ * Always clears the existing cache before populating — call with `{}` to just clear. */
10
+ declare function initServerDataCache(data: Record<string, unknown>): void;
11
+ /**
12
+ * Fetch async data on the server during SSR. Returns `undefined` on the first
13
+ * render pass(es) while the promise is in flight; returns the resolved value
14
+ * once the framework's render loop has awaited it.
15
+ *
16
+ * On the client the pre-resolved value is read from the hydration cache
17
+ * serialised into the page by the server, so no fetch is issued in the browser.
18
+ *
19
+ * The `key` (string or array of strings) uniquely identifies the cached value
20
+ * across all SSR render passes and client hydration — it must be stable and
21
+ * unique within the page.
22
+ *
23
+ * `fn` may return a `Promise<T>` (async usage) or return `T` synchronously.
24
+ * The resolved value is serialised into `__serverData` and returned from cache
25
+ * during hydration.
26
+ *
27
+ * `fn` is **server-only**: it is never called in the browser. On client-side
28
+ * navigation (after the initial SSR load), hadars automatically fires a
29
+ * data-only request to the current URL (`X-Hadars-Data: 1`) and suspends via
30
+ * React Suspense until the server returns the JSON map of resolved values.
31
+ *
32
+ * @example
33
+ * const user = useServerData('current_user', () => db.getUser(id));
34
+ * const post = useServerData(['post', postId], () => db.getPost(postId));
35
+ * if (!user) return null; // undefined while pending on the first SSR pass
36
+ */
37
+ declare function useServerData<T>(key: string | string[], fn: () => Promise<T> | T): T | undefined;
38
+ declare const Head: React__default.FC<{
39
+ children?: React__default.ReactNode;
40
+ status?: number;
41
+ }>;
42
+
43
+ interface CacheSegmentProps {
44
+ /**
45
+ * Unique cache key for this segment. Use a key that encodes all values
46
+ * the output depends on, e.g. `"product-" + product.id`.
47
+ */
48
+ cacheKey: string;
49
+ /**
50
+ * Time-to-live in milliseconds. Omit for entries that never expire.
51
+ */
52
+ ttl?: number;
53
+ children: React__default.ReactNode;
54
+ }
55
+ /**
56
+ * Caches the server-rendered HTML of its children across requests.
57
+ *
58
+ * **Server (SSR):**
59
+ * - Cache miss — children are rendered normally as part of the main
60
+ * `renderToString` call, so React context propagates correctly. The output
61
+ * is wrapped in a `<hadars-c>` marker that `processSegmentCache` uses to
62
+ * extract and store the HTML. The marker is stripped before the response
63
+ * is sent; the browser never sees it.
64
+ * - Cache hit — children are **not** rendered at all. The cached HTML is
65
+ * injected directly, saving the entire subtree render cost.
66
+ *
67
+ * **Client:** renders children normally (no caching). Because the server
68
+ * strips the marker wrapper, the client output matches the server HTML and
69
+ * React hydration succeeds without warnings for deterministic components.
70
+ *
71
+ * **Note:** components that rely on request-specific data (cookies, auth,
72
+ * personalisation) must not be wrapped in `CacheSegment` unless the cache
73
+ * key encodes that data — otherwise a cached response for one user could be
74
+ * served to another.
75
+ */
76
+ declare function CacheSegment({ cacheKey, ttl, children }: CacheSegmentProps): react_jsx_runtime.JSX.Element;
77
+
78
+ declare function deleteSegment(key: string): void;
79
+ declare function clearSegments(): void;
80
+
81
+ declare const HadarsContext: React$1.FC<{
82
+ children: React.ReactNode;
83
+ context: AppContext;
84
+ }>;
85
+ /**
86
+ * Dynamically loads a module with target-aware behaviour:
87
+ *
88
+ * - **Browser** (after loader transform): becomes `import('./path')`, which
89
+ * rspack splits into a separate chunk for true code splitting.
90
+ * - **SSR** (after loader transform): becomes
91
+ * `Promise.resolve(require('./path'))`, which rspack bundles statically.
92
+ *
93
+ * The hadars rspack loader must be active for the transform to apply.
94
+ * This runtime fallback uses a plain dynamic import (no code splitting).
95
+ *
96
+ * @example
97
+ * // Code-split React component:
98
+ * const MyComp = React.lazy(() => loadModule('./MyComp'));
99
+ *
100
+ * // Dynamic data:
101
+ * const { default: fn } = await loadModule<typeof import('./util')>('./util');
102
+ */
103
+ declare function loadModule<T = any>(path: string): Promise<T>;
104
+
105
+ export { CacheSegment, HadarsContext, Head as HadarsHead, clearSegments, deleteSegment, initServerDataCache, loadModule, useServerData };