@clarify-labs/renderer 0.7.2 → 0.8.2

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.
Files changed (59) hide show
  1. package/output/{ThemeRoot-UWj0iK1X.cjs → ClarifyShell-B74Fq4UU.cjs} +389 -161
  2. package/output/ClarifyShell-B74Fq4UU.cjs.map +1 -0
  3. package/output/{ThemeRoot-QULrwQf6.js → ClarifyShell-BPv2bxI4.js} +361 -157
  4. package/output/ClarifyShell-BPv2bxI4.js.map +1 -0
  5. package/output/{OpenApiOperation-BcyW_ULy.cjs → OpenApiOperation-BMXfV15v.cjs} +209 -7
  6. package/output/OpenApiOperation-BMXfV15v.cjs.map +1 -0
  7. package/output/{OpenApiOperation-tUKf7lZ4.js → OpenApiOperation-fJ3QQOJX.js} +205 -9
  8. package/output/OpenApiOperation-fJ3QQOJX.js.map +1 -0
  9. package/output/{PageActions-yoDRjkq8.js → PageActions-BwY7ierv.js} +55 -81
  10. package/output/PageActions-BwY7ierv.js.map +1 -0
  11. package/output/{PageActions-1RDCHcUY.cjs → PageActions-DOKkt2zo.cjs} +59 -79
  12. package/output/PageActions-DOKkt2zo.cjs.map +1 -0
  13. package/output/app/AppShell.d.ts +2 -3
  14. package/output/app/PageBanner.d.ts +0 -2
  15. package/output/app/PageFooter.d.ts +1 -5
  16. package/output/client.cjs +8 -8
  17. package/output/client.js +3 -3
  18. package/output/components/Code.d.ts +5 -1
  19. package/output/components/Mermaid.d.ts +7 -0
  20. package/output/components/index.d.ts +1 -0
  21. package/output/context.d.ts +1 -1
  22. package/output/core/i18n.d.ts +1 -1
  23. package/output/core/types.d.ts +8 -14
  24. package/output/index.cjs +27 -24
  25. package/output/index.cjs.map +1 -1
  26. package/output/index.d.ts +7 -4
  27. package/output/index.js +14 -14
  28. package/output/index.js.map +1 -1
  29. package/output/mdx/components.d.ts +3 -0
  30. package/output/mdx/primitives.d.ts +1 -0
  31. package/output/preview.cjs +3 -2
  32. package/output/preview.cjs.map +1 -1
  33. package/output/preview.js +3 -2
  34. package/output/preview.js.map +1 -1
  35. package/output/{render-psutGbsg.js → render-Cghgq1AQ.js} +10 -20
  36. package/output/render-Cghgq1AQ.js.map +1 -0
  37. package/output/{render-ByWbJbrA.cjs → render-ZSckbg74.cjs} +10 -20
  38. package/output/render-ZSckbg74.cjs.map +1 -0
  39. package/output/renderer.css +77 -21
  40. package/output/runtime/ClarifyShell.d.ts +22 -0
  41. package/output/server.cjs +10 -19
  42. package/output/server.cjs.map +1 -1
  43. package/output/server.js +10 -19
  44. package/output/server.js.map +1 -1
  45. package/output/shell/search/pagefind.d.ts +0 -1
  46. package/output/slots/RuntimeSlot.d.ts +58 -0
  47. package/output/slots/context.d.ts +20 -0
  48. package/output/slots/index.d.ts +5 -0
  49. package/output/slots/types.d.ts +50 -0
  50. package/output/utils/localized-text.d.ts +7 -0
  51. package/package.json +8 -3
  52. package/output/OpenApiOperation-BcyW_ULy.cjs.map +0 -1
  53. package/output/OpenApiOperation-tUKf7lZ4.js.map +0 -1
  54. package/output/PageActions-1RDCHcUY.cjs.map +0 -1
  55. package/output/PageActions-yoDRjkq8.js.map +0 -1
  56. package/output/ThemeRoot-QULrwQf6.js.map +0 -1
  57. package/output/ThemeRoot-UWj0iK1X.cjs.map +0 -1
  58. package/output/render-ByWbJbrA.cjs.map +0 -1
  59. package/output/render-psutGbsg.js.map +0 -1
@@ -1278,6 +1278,10 @@
1278
1278
  flex: none;
1279
1279
  margin-top: .45rem;
1280
1280
  }
1281
+
1282
+ .prose thead th, .prose :not(pre) > code {
1283
+ white-space: nowrap;
1284
+ }
1281
1285
  }
1282
1286
 
1283
1287
  @layer utilities {
@@ -1353,6 +1357,10 @@
1353
1357
  top: 50%;
1354
1358
  }
1355
1359
 
1360
+ .top-2 {
1361
+ top: calc(var(--spacing) * 2);
1362
+ }
1363
+
1356
1364
  .top-3\.5 {
1357
1365
  top: calc(var(--spacing) * 3.5);
1358
1366
  }
@@ -1369,6 +1377,10 @@
1369
1377
  right: 0;
1370
1378
  }
1371
1379
 
1380
+ .right-2 {
1381
+ right: calc(var(--spacing) * 2);
1382
+ }
1383
+
1372
1384
  .right-3 {
1373
1385
  right: calc(var(--spacing) * 3);
1374
1386
  }
@@ -1381,6 +1393,10 @@
1381
1393
  bottom: 0;
1382
1394
  }
1383
1395
 
1396
+ .bottom-2 {
1397
+ bottom: calc(var(--spacing) * 2);
1398
+ }
1399
+
1384
1400
  .bottom-4 {
1385
1401
  bottom: calc(var(--spacing) * 4);
1386
1402
  }
@@ -1732,7 +1748,6 @@
1732
1748
  .prose :where(table):not(:where([class~="not-prose"], [class~="not-prose"] *)) {
1733
1749
  table-layout: auto;
1734
1750
  text-align: left;
1735
- width: 100%;
1736
1751
  margin-top: 2rem;
1737
1752
  margin-bottom: 2rem;
1738
1753
  line-height: 1.5rem;
@@ -1798,6 +1813,10 @@
1798
1813
  color: inherit;
1799
1814
  }
1800
1815
 
1816
+ .prose :where(:is(tbody, tfoot) td code):not(:where([class~="not-prose"], [class~="not-prose"] *)) {
1817
+ white-space: normal;
1818
+ }
1819
+
1801
1820
  .prose :where(:is(h1, h2, h3) + *):not(:where([class~="not-prose"], [class~="not-prose"] *)) {
1802
1821
  margin-top: 0;
1803
1822
  }
@@ -1993,11 +2012,6 @@
1993
2012
  height: calc(var(--spacing) * 5);
1994
2013
  }
1995
2014
 
1996
- .size-6 {
1997
- width: calc(var(--spacing) * 6);
1998
- height: calc(var(--spacing) * 6);
1999
- }
2000
-
2001
2015
  .size-7 {
2002
2016
  width: calc(var(--spacing) * 7);
2003
2017
  height: calc(var(--spacing) * 7);
@@ -2126,6 +2140,10 @@
2126
2140
  min-height: 100vh;
2127
2141
  }
2128
2142
 
2143
+ .\!w-full {
2144
+ width: 100% !important;
2145
+ }
2146
+
2129
2147
  .w-\(--clarify-schema-row-nested-width\) {
2130
2148
  width: var(--clarify-schema-row-nested-width);
2131
2149
  }
@@ -2190,6 +2208,10 @@
2190
2208
  width: calc(var(--spacing) * 6);
2191
2209
  }
2192
2210
 
2211
+ .w-7 {
2212
+ width: calc(var(--spacing) * 7);
2213
+ }
2214
+
2193
2215
  .w-8 {
2194
2216
  width: calc(var(--spacing) * 8);
2195
2217
  }
@@ -2346,6 +2368,10 @@
2346
2368
  flex-shrink: 0;
2347
2369
  }
2348
2370
 
2371
+ .grow {
2372
+ flex-grow: 1;
2373
+ }
2374
+
2349
2375
  .origin-top {
2350
2376
  transform-origin: top;
2351
2377
  }
@@ -2399,6 +2425,10 @@
2399
2425
  animation: var(--animate-spin);
2400
2426
  }
2401
2427
 
2428
+ .\!cursor-grab {
2429
+ cursor: grab !important;
2430
+ }
2431
+
2402
2432
  .cursor-default {
2403
2433
  cursor: default;
2404
2434
  }
@@ -2599,10 +2629,6 @@
2599
2629
  }
2600
2630
  }
2601
2631
 
2602
- .self-end {
2603
- align-self: flex-end;
2604
- }
2605
-
2606
2632
  .truncate {
2607
2633
  text-overflow: ellipsis;
2608
2634
  white-space: nowrap;
@@ -2873,7 +2899,17 @@
2873
2899
  background-color: var(--clarify-theme-tokens-colors-primary);
2874
2900
  }
2875
2901
 
2876
- .bg-\(--clarify-theme-tokens-colors-surface\), .bg-\(--clarify-theme-tokens-colors-surface\)\/95 {
2902
+ .bg-\(--clarify-theme-tokens-colors-surface\), .bg-\(--clarify-theme-tokens-colors-surface\)\/90 {
2903
+ background-color: var(--clarify-theme-tokens-colors-surface);
2904
+ }
2905
+
2906
+ @supports (color: color-mix(in lab, red, red)) {
2907
+ .bg-\(--clarify-theme-tokens-colors-surface\)\/90 {
2908
+ background-color: color-mix(in oklab, var(--clarify-theme-tokens-colors-surface) 90%, transparent);
2909
+ }
2910
+ }
2911
+
2912
+ .bg-\(--clarify-theme-tokens-colors-surface\)\/95 {
2877
2913
  background-color: var(--clarify-theme-tokens-colors-surface);
2878
2914
  }
2879
2915
 
@@ -3289,8 +3325,8 @@
3289
3325
  padding-top: calc(var(--spacing) * 16);
3290
3326
  }
3291
3327
 
3292
- .pt-\[6\.5rem\] {
3293
- padding-top: 6.5rem;
3328
+ .pt-26 {
3329
+ padding-top: calc(var(--spacing) * 26);
3294
3330
  }
3295
3331
 
3296
3332
  .pr-3 {
@@ -3329,6 +3365,10 @@
3329
3365
  padding-bottom: calc(var(--spacing) * 12);
3330
3366
  }
3331
3367
 
3368
+ .pb-16 {
3369
+ padding-bottom: calc(var(--spacing) * 16);
3370
+ }
3371
+
3332
3372
  .pl-1\.5 {
3333
3373
  padding-left: calc(var(--spacing) * 1.5);
3334
3374
  }
@@ -3498,14 +3538,14 @@
3498
3538
  letter-spacing: var(--tracking-widest);
3499
3539
  }
3500
3540
 
3501
- .break-words {
3502
- overflow-wrap: break-word;
3503
- }
3504
-
3505
3541
  .wrap-anywhere {
3506
3542
  overflow-wrap: anywhere;
3507
3543
  }
3508
3544
 
3545
+ .wrap-break-word {
3546
+ overflow-wrap: break-word;
3547
+ }
3548
+
3509
3549
  .whitespace-normal {
3510
3550
  white-space: normal;
3511
3551
  }
@@ -4071,6 +4111,10 @@
4071
4111
  display: none;
4072
4112
  }
4073
4113
 
4114
+ .focus-within\:opacity-100:focus-within {
4115
+ opacity: 1;
4116
+ }
4117
+
4074
4118
  @media (hover: hover) {
4075
4119
  .hover\:scale-105:hover {
4076
4120
  --tw-scale-x: 105%;
@@ -4202,6 +4246,10 @@
4202
4246
  outline-style: none;
4203
4247
  }
4204
4248
 
4249
+ .active\:\!cursor-grabbing:active {
4250
+ cursor: grabbing !important;
4251
+ }
4252
+
4205
4253
  .data-closed\:-translate-x-full[data-closed] {
4206
4254
  --tw-translate-x: -100%;
4207
4255
  translate: var(--tw-translate-x) var(--tw-translate-y);
@@ -4474,6 +4522,10 @@
4474
4522
  top: calc(var(--spacing) * 14);
4475
4523
  }
4476
4524
 
4525
+ .lg\:top-26 {
4526
+ top: calc(var(--spacing) * 26);
4527
+ }
4528
+
4477
4529
  .lg\:top-28 {
4478
4530
  top: calc(var(--spacing) * 28);
4479
4531
  }
@@ -4482,10 +4534,6 @@
4482
4534
  top: calc(var(--spacing) * 40);
4483
4535
  }
4484
4536
 
4485
- .lg\:top-\[6\.5rem\] {
4486
- top: 6.5rem;
4487
- }
4488
-
4489
4537
  .lg\:z-30 {
4490
4538
  z-index: 30;
4491
4539
  }
@@ -5221,6 +5269,14 @@
5221
5269
  }
5222
5270
  }
5223
5271
 
5272
+ .\[\&_svg\]\:h-auto svg {
5273
+ height: auto;
5274
+ }
5275
+
5276
+ .\[\&_svg\]\:max-w-full svg {
5277
+ max-width: 100%;
5278
+ }
5279
+
5224
5280
  .\[\&\:\:-webkit-search-cancel-button\]\:hidden::-webkit-search-cancel-button {
5225
5281
  display: none;
5226
5282
  }
@@ -0,0 +1,22 @@
1
+ import { ReactNode } from 'react';
2
+ import { Config, NavigationTree, RouteItem } from '../core/types';
3
+ import { OpenAPISpec } from '../openapi/lib/utils';
4
+ import { RuntimeSlots } from '../slots';
5
+ export type ClarifyShellProps = {
6
+ config: Config;
7
+ routes: RouteItem[];
8
+ navigation?: NavigationTree;
9
+ openApis: Record<string, OpenAPISpec>;
10
+ runtimeSlots?: RuntimeSlots;
11
+ themeEditor?: boolean;
12
+ children?: ReactNode;
13
+ };
14
+ /**
15
+ * Shared provider chain used by both client-side render and server-side
16
+ * renderToHTML. Wraps AppShell with ConfigContext → OpenApisContext →
17
+ * ThemeProvider → ThemeRoot.
18
+ *
19
+ * The outer Router (BrowserRouter / StaticRouter) is left to the caller
20
+ * so each entry point can supply the correct router variant.
21
+ */
22
+ export declare function ClarifyShell(props: ClarifyShellProps): import("react").JSX.Element;
package/output/server.cjs CHANGED
@@ -1,6 +1,6 @@
1
1
  Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
2
- const require_PageActions = require("./PageActions-1RDCHcUY.cjs");
3
- const require_ThemeRoot = require("./ThemeRoot-UWj0iK1X.cjs");
2
+ const require_PageActions = require("./PageActions-DOKkt2zo.cjs");
3
+ const require_ClarifyShell = require("./ClarifyShell-B74Fq4UU.cjs");
4
4
  let react = require("react");
5
5
  let react_router_dom = require("react-router-dom");
6
6
  let react_jsx_runtime = require("react/jsx-runtime");
@@ -12,27 +12,18 @@ let react_dom_server = require("react-dom/server");
12
12
  * 返回 `div#root` 内部的 HTML,由 Clarify CLI 组装为完整的 HTML 文档。
13
13
  */
14
14
  function renderToHTML(options) {
15
- const { config, routes, navigation, openApis = {}, bannerComponent, footerComponent, url, themeEditor = false } = options;
15
+ const { config, routes, navigation, openApis = {}, runtimeSlots, url, themeEditor = false } = options;
16
16
  const location = require_PageActions.prefixHref(url, config.routePrefix);
17
17
  return (0, react_dom_server.renderToString)(/* @__PURE__ */ (0, react_jsx_runtime.jsx)(react.StrictMode, { children: /* @__PURE__ */ (0, react_jsx_runtime.jsx)(react_router_dom.StaticRouter, {
18
18
  basename: config.routePrefix,
19
19
  location,
20
- children: /* @__PURE__ */ (0, react_jsx_runtime.jsx)(require_PageActions.ConfigContext.Provider, {
21
- value: config,
22
- children: /* @__PURE__ */ (0, react_jsx_runtime.jsx)(require_PageActions.OpenApisContext.Provider, {
23
- value: openApis,
24
- children: /* @__PURE__ */ (0, react_jsx_runtime.jsx)(require_PageActions.ThemeProvider, { children: /* @__PURE__ */ (0, react_jsx_runtime.jsx)(require_ThemeRoot.ThemeRoot, {
25
- theme: config.theme,
26
- themeEditor,
27
- children: /* @__PURE__ */ (0, react_jsx_runtime.jsx)(require_ThemeRoot.AppShell, {
28
- config,
29
- routes,
30
- navigation: navigation ?? [],
31
- bannerComponent,
32
- footerComponent
33
- })
34
- }) })
35
- })
20
+ children: /* @__PURE__ */ (0, react_jsx_runtime.jsx)(require_ClarifyShell.ClarifyShell, {
21
+ config,
22
+ routes,
23
+ navigation,
24
+ openApis,
25
+ runtimeSlots,
26
+ themeEditor
36
27
  })
37
28
  }) }));
38
29
  }
@@ -1 +1 @@
1
- {"version":3,"file":"server.cjs","names":[],"sources":["../source/runtime/server.tsx"],"sourcesContent":["import { StrictMode } from 'react'\nimport { renderToString } from 'react-dom/server'\nimport { StaticRouter } from 'react-router-dom'\n\nimport { AppShell } from '../app/AppShell'\nimport { ConfigContext, OpenApisContext } from '../context'\nimport { ThemeProvider } from '../theme/ThemeProvider'\nimport { ThemeRoot } from '../theme/ThemeRoot'\nimport type { ServerRenderOptions } from '../types'\nimport { prefixHref } from '../utils/href'\n\n/**\n * Clarify 服务端渲染入口。\n * 由 @clarify-labs/cli 在构建时调用,为每条路由生成 React HTML 片段。\n * 返回 `div#root` 内部的 HTML,由 Clarify CLI 组装为完整的 HTML 文档。\n */\nexport function renderToHTML(options: ServerRenderOptions): string {\n const { config, routes, navigation, openApis = {}, bannerComponent, footerComponent, url, themeEditor = false } = options\n const location = prefixHref(url, config.routePrefix)\n\n return renderToString(\n <StrictMode>\n <StaticRouter basename={config.routePrefix} location={location}>\n <ConfigContext.Provider value={config}>\n <OpenApisContext.Provider value={openApis}>\n <ThemeProvider>\n <ThemeRoot theme={config.theme} themeEditor={themeEditor}>\n <AppShell config={config} routes={routes} navigation={navigation ?? []} bannerComponent={bannerComponent} footerComponent={footerComponent} />\n </ThemeRoot>\n </ThemeProvider>\n </OpenApisContext.Provider>\n </ConfigContext.Provider>\n </StaticRouter>\n </StrictMode>\n )\n}\n"],"mappings":";;;;;;;;;;;;;AAgBA,SAAgB,aAAa,SAAsC;CACjE,MAAM,EAAE,QAAQ,QAAQ,YAAY,WAAW,CAAC,GAAG,iBAAiB,iBAAiB,KAAK,cAAc,UAAU;CAClH,MAAM,WAAW,oBAAA,WAAW,KAAK,OAAO,WAAW;CAEnD,QAAA,GAAA,iBAAA,gBACE,iBAAA,GAAA,kBAAA,KAAC,MAAA,YAAD,EAAA,UACE,iBAAA,GAAA,kBAAA,KAAC,iBAAA,cAAD;EAAc,UAAU,OAAO;EAAuB;YACpD,iBAAA,GAAA,kBAAA,KAAC,oBAAA,cAAc,UAAf;GAAwB,OAAO;aAC7B,iBAAA,GAAA,kBAAA,KAAC,oBAAA,gBAAgB,UAAjB;IAA0B,OAAO;cAC/B,iBAAA,GAAA,kBAAA,KAAC,oBAAA,eAAD,EAAA,UACE,iBAAA,GAAA,kBAAA,KAAC,kBAAA,WAAD;KAAW,OAAO,OAAO;KAAoB;eAC3C,iBAAA,GAAA,kBAAA,KAAC,kBAAA,UAAD;MAAkB;MAAgB;MAAQ,YAAY,cAAc,CAAC;MAAoB;MAAkC;KAAkB,CAAA;IACpI,CAAA,EACE,CAAA;GACS,CAAA;EACJ,CAAA;CACZ,CAAA,EACJ,CAAA,CACd;AACF"}
1
+ {"version":3,"file":"server.cjs","names":[],"sources":["../source/runtime/server.tsx"],"sourcesContent":["import { StrictMode } from 'react'\nimport { renderToString } from 'react-dom/server'\nimport { StaticRouter } from 'react-router-dom'\n\nimport type { ServerRenderOptions } from '../types'\nimport { prefixHref } from '../utils/href'\n\nimport { ClarifyShell } from './ClarifyShell'\n\n/**\n * Clarify 服务端渲染入口。\n * 由 @clarify-labs/cli 在构建时调用,为每条路由生成 React HTML 片段。\n * 返回 `div#root` 内部的 HTML,由 Clarify CLI 组装为完整的 HTML 文档。\n */\nexport function renderToHTML(options: ServerRenderOptions): string {\n const { config, routes, navigation, openApis = {}, runtimeSlots, url, themeEditor = false } = options\n const location = prefixHref(url, config.routePrefix)\n\n return renderToString(\n <StrictMode>\n <StaticRouter basename={config.routePrefix} location={location}>\n <ClarifyShell\n config={config}\n routes={routes}\n navigation={navigation}\n openApis={openApis}\n runtimeSlots={runtimeSlots}\n themeEditor={themeEditor}\n />\n </StaticRouter>\n </StrictMode>\n )\n}\n"],"mappings":";;;;;;;;;;;;;AAcA,SAAgB,aAAa,SAAsC;CACjE,MAAM,EAAE,QAAQ,QAAQ,YAAY,WAAW,CAAC,GAAG,cAAc,KAAK,cAAc,UAAU;CAC9F,MAAM,WAAW,oBAAA,WAAW,KAAK,OAAO,WAAW;CAEnD,QAAA,GAAA,iBAAA,gBACE,iBAAA,GAAA,kBAAA,KAAC,MAAA,YAAD,EAAA,UACE,iBAAA,GAAA,kBAAA,KAAC,iBAAA,cAAD;EAAc,UAAU,OAAO;EAAuB;YACpD,iBAAA,GAAA,kBAAA,KAAC,qBAAA,cAAD;GACU;GACA;GACI;GACF;GACI;GACD;EACd,CAAA;CACW,CAAA,EACJ,CAAA,CACd;AACF"}
package/output/server.js CHANGED
@@ -1,5 +1,5 @@
1
- import { A as OpenApisContext, O as ConfigContext, T as prefixHref, m as ThemeProvider } from "./PageActions-yoDRjkq8.js";
2
- import { c as AppShell, t as ThemeRoot } from "./ThemeRoot-QULrwQf6.js";
1
+ import { E as prefixHref } from "./PageActions-BwY7ierv.js";
2
+ import { t as ClarifyShell } from "./ClarifyShell-BPv2bxI4.js";
3
3
  import { StrictMode } from "react";
4
4
  import { StaticRouter } from "react-router-dom";
5
5
  import { jsx } from "react/jsx-runtime";
@@ -11,27 +11,18 @@ import { renderToString } from "react-dom/server";
11
11
  * 返回 `div#root` 内部的 HTML,由 Clarify CLI 组装为完整的 HTML 文档。
12
12
  */
13
13
  function renderToHTML(options) {
14
- const { config, routes, navigation, openApis = {}, bannerComponent, footerComponent, url, themeEditor = false } = options;
14
+ const { config, routes, navigation, openApis = {}, runtimeSlots, url, themeEditor = false } = options;
15
15
  const location = prefixHref(url, config.routePrefix);
16
16
  return renderToString(/* @__PURE__ */ jsx(StrictMode, { children: /* @__PURE__ */ jsx(StaticRouter, {
17
17
  basename: config.routePrefix,
18
18
  location,
19
- children: /* @__PURE__ */ jsx(ConfigContext.Provider, {
20
- value: config,
21
- children: /* @__PURE__ */ jsx(OpenApisContext.Provider, {
22
- value: openApis,
23
- children: /* @__PURE__ */ jsx(ThemeProvider, { children: /* @__PURE__ */ jsx(ThemeRoot, {
24
- theme: config.theme,
25
- themeEditor,
26
- children: /* @__PURE__ */ jsx(AppShell, {
27
- config,
28
- routes,
29
- navigation: navigation ?? [],
30
- bannerComponent,
31
- footerComponent
32
- })
33
- }) })
34
- })
19
+ children: /* @__PURE__ */ jsx(ClarifyShell, {
20
+ config,
21
+ routes,
22
+ navigation,
23
+ openApis,
24
+ runtimeSlots,
25
+ themeEditor
35
26
  })
36
27
  }) }));
37
28
  }
@@ -1 +1 @@
1
- {"version":3,"file":"server.js","names":[],"sources":["../source/runtime/server.tsx"],"sourcesContent":["import { StrictMode } from 'react'\nimport { renderToString } from 'react-dom/server'\nimport { StaticRouter } from 'react-router-dom'\n\nimport { AppShell } from '../app/AppShell'\nimport { ConfigContext, OpenApisContext } from '../context'\nimport { ThemeProvider } from '../theme/ThemeProvider'\nimport { ThemeRoot } from '../theme/ThemeRoot'\nimport type { ServerRenderOptions } from '../types'\nimport { prefixHref } from '../utils/href'\n\n/**\n * Clarify 服务端渲染入口。\n * 由 @clarify-labs/cli 在构建时调用,为每条路由生成 React HTML 片段。\n * 返回 `div#root` 内部的 HTML,由 Clarify CLI 组装为完整的 HTML 文档。\n */\nexport function renderToHTML(options: ServerRenderOptions): string {\n const { config, routes, navigation, openApis = {}, bannerComponent, footerComponent, url, themeEditor = false } = options\n const location = prefixHref(url, config.routePrefix)\n\n return renderToString(\n <StrictMode>\n <StaticRouter basename={config.routePrefix} location={location}>\n <ConfigContext.Provider value={config}>\n <OpenApisContext.Provider value={openApis}>\n <ThemeProvider>\n <ThemeRoot theme={config.theme} themeEditor={themeEditor}>\n <AppShell config={config} routes={routes} navigation={navigation ?? []} bannerComponent={bannerComponent} footerComponent={footerComponent} />\n </ThemeRoot>\n </ThemeProvider>\n </OpenApisContext.Provider>\n </ConfigContext.Provider>\n </StaticRouter>\n </StrictMode>\n )\n}\n"],"mappings":";;;;;;;;;;;;AAgBA,SAAgB,aAAa,SAAsC;CACjE,MAAM,EAAE,QAAQ,QAAQ,YAAY,WAAW,CAAC,GAAG,iBAAiB,iBAAiB,KAAK,cAAc,UAAU;CAClH,MAAM,WAAW,WAAW,KAAK,OAAO,WAAW;CAEnD,OAAO,eACL,oBAAC,YAAD,EAAA,UACE,oBAAC,cAAD;EAAc,UAAU,OAAO;EAAuB;YACpD,oBAAC,cAAc,UAAf;GAAwB,OAAO;aAC7B,oBAAC,gBAAgB,UAAjB;IAA0B,OAAO;cAC/B,oBAAC,eAAD,EAAA,UACE,oBAAC,WAAD;KAAW,OAAO,OAAO;KAAoB;eAC3C,oBAAC,UAAD;MAAkB;MAAgB;MAAQ,YAAY,cAAc,CAAC;MAAoB;MAAkC;KAAkB,CAAA;IACpI,CAAA,EACE,CAAA;GACS,CAAA;EACJ,CAAA;CACZ,CAAA,EACJ,CAAA,CACd;AACF"}
1
+ {"version":3,"file":"server.js","names":[],"sources":["../source/runtime/server.tsx"],"sourcesContent":["import { StrictMode } from 'react'\nimport { renderToString } from 'react-dom/server'\nimport { StaticRouter } from 'react-router-dom'\n\nimport type { ServerRenderOptions } from '../types'\nimport { prefixHref } from '../utils/href'\n\nimport { ClarifyShell } from './ClarifyShell'\n\n/**\n * Clarify 服务端渲染入口。\n * 由 @clarify-labs/cli 在构建时调用,为每条路由生成 React HTML 片段。\n * 返回 `div#root` 内部的 HTML,由 Clarify CLI 组装为完整的 HTML 文档。\n */\nexport function renderToHTML(options: ServerRenderOptions): string {\n const { config, routes, navigation, openApis = {}, runtimeSlots, url, themeEditor = false } = options\n const location = prefixHref(url, config.routePrefix)\n\n return renderToString(\n <StrictMode>\n <StaticRouter basename={config.routePrefix} location={location}>\n <ClarifyShell\n config={config}\n routes={routes}\n navigation={navigation}\n openApis={openApis}\n runtimeSlots={runtimeSlots}\n themeEditor={themeEditor}\n />\n </StaticRouter>\n </StrictMode>\n )\n}\n"],"mappings":";;;;;;;;;;;;AAcA,SAAgB,aAAa,SAAsC;CACjE,MAAM,EAAE,QAAQ,QAAQ,YAAY,WAAW,CAAC,GAAG,cAAc,KAAK,cAAc,UAAU;CAC9F,MAAM,WAAW,WAAW,KAAK,OAAO,WAAW;CAEnD,OAAO,eACL,oBAAC,YAAD,EAAA,UACE,oBAAC,cAAD;EAAc,UAAU,OAAO;EAAuB;YACpD,oBAAC,cAAD;GACU;GACA;GACI;GACF;GACI;GACD;EACd,CAAA;CACW,CAAA,EACJ,CAAA,CACd;AACF"}
@@ -1,5 +1,4 @@
1
1
  import { Pagefind } from './types';
2
2
  export declare function pagefindCacheKey(routePrefix: string, locale: string | undefined): string;
3
- export declare function logSearchDebug(message: string, data?: Record<string, unknown>): void;
4
3
  export declare function loadPagefind(routePrefix: string, locale: string | undefined): Promise<Pagefind | null>;
5
4
  export declare function normalizePagefindUrl(url: string, routePrefix: string): string;
@@ -0,0 +1,58 @@
1
+ import { ComponentType, ReactNode } from 'react';
2
+ import { RouteItem } from '../core/types';
3
+ import { UISlotName } from './types';
4
+ /**
5
+ * One registered slot component, as compiled by the CLI into
6
+ * `virtual:clarify/slots`.
7
+ *
8
+ * `component` is a lazy import factory `() => import('path')`. On the client
9
+ * it is passed to `React.lazy`. During SSR the factory is pre-resolved and
10
+ * the resulting component is stored in `_resolved`, which the renderer uses
11
+ * directly (no Suspense needed for `renderToString`).
12
+ */
13
+ export type RuntimeSlotEntry = {
14
+ /** Plugin that registered this component, used as a stable render key. */
15
+ plugin: string;
16
+ /** Lazy import factory — `() => import('path')`. Set by CLI virtual module. */
17
+ component: () => Promise<{
18
+ default: ComponentType;
19
+ }>;
20
+ /** @internal Pre-resolved component set by SSR before {@link renderToHTML}. */
21
+ _resolved?: ComponentType;
22
+ };
23
+ /** Registry keyed by slot name. */
24
+ export type RuntimeSlots = Partial<Record<UISlotName, RuntimeSlotEntry[]>>;
25
+ type RuntimeSlotsContextValue = {
26
+ slots: RuntimeSlots;
27
+ route?: RouteItem;
28
+ };
29
+ export declare const RuntimeSlotsContext: import('react').Context<RuntimeSlotsContextValue>;
30
+ type RuntimeSlotsProviderProps = {
31
+ slots?: RuntimeSlots;
32
+ route?: RouteItem;
33
+ children: ReactNode;
34
+ };
35
+ /**
36
+ * Makes the compiled slot registry and the current route available to every
37
+ * {@link RuntimeSlot} in the tree. Mounted once near the top of `AppShell`.
38
+ */
39
+ export declare function RuntimeSlotsProvider(arg0: RuntimeSlotsProviderProps): ReactNode;
40
+ type RuntimeSlotProps = {
41
+ name: UISlotName;
42
+ /** Built-in default component for replacement slots. */
43
+ default?: ComponentType;
44
+ };
45
+ /**
46
+ * Renders plugin components registered for a slot, in registration order.
47
+ *
48
+ * For extension slots (*.before/*.after), renders all plugin components.
49
+ * For replacement slots (*.replace), renders only the last registered plugin
50
+ * component (if any), and passes the default component through context.
51
+ *
52
+ * Each component is loaded via the import factory. If `_resolved` is set
53
+ * (SSR pre-resolution), the component is rendered synchronously for
54
+ * compatibility with `renderToString`. Otherwise, `React.lazy` + `Suspense`
55
+ * is used for client-side code-splitting.
56
+ */
57
+ export declare function RuntimeSlot(arg0: RuntimeSlotProps): ReactNode;
58
+ export {};
@@ -0,0 +1,20 @@
1
+ import { ReactNode } from 'react';
2
+ import { UISlotName, SlotContext } from './types';
3
+ export type { UISlotName, SlotContext };
4
+ type SlotProviderProps = {
5
+ value: SlotContext;
6
+ children: ReactNode;
7
+ };
8
+ /**
9
+ * Provides an isolated {@link SlotContext} for a single slot component.
10
+ * `RuntimeSlot` wraps every rendered slot component with this provider.
11
+ */
12
+ export declare function SlotProvider(arg0: SlotProviderProps): ReactNode;
13
+ /**
14
+ * Reads the current slot context.
15
+ *
16
+ * Must be called inside a slot component (or a descendant). Calling it outside a
17
+ * slot provider throws, which helps plugin authors notice that the component was
18
+ * not mounted through a Clarify slot.
19
+ */
20
+ export declare function useSlot(): SlotContext;
@@ -0,0 +1,5 @@
1
+ export { SlotProvider, useSlot } from './context';
2
+ export type { SlotContext, UISlotName } from './context';
3
+ export { RuntimeSlot, RuntimeSlotsProvider, RuntimeSlotsContext } from './RuntimeSlot';
4
+ export type { RuntimeSlotEntry, RuntimeSlots } from './RuntimeSlot';
5
+ export type { UISlotRegistration } from './types';
@@ -0,0 +1,50 @@
1
+ import { ComponentType } from 'react';
2
+ import { RouteItem } from '../core/types';
3
+ /**
4
+ * Stable runtime UI slot positions.
5
+ *
6
+ * The name is a dot-path `${scope}.${path}.${position}`:
7
+ * - `*.before`: Extension slot, plugin components render before default
8
+ * - `*.after`: Extension slot, plugin components render after default
9
+ * - `*.replace`: Replacement slot, plugin component replaces default
10
+ */
11
+ export type UISlotName = 'page.footer.before' | 'page.banner.replace' | 'page.footer.replace';
12
+ /**
13
+ * Context exposed to a slot component through the `useSlot` hook.
14
+ *
15
+ * Slot components never receive Clarify context through props. Instead they read
16
+ * everything they need from this hook, which keeps slot components as ordinary
17
+ * React components and lets the slot context grow without changing signatures.
18
+ */
19
+ export type SlotContext = {
20
+ /** The slot the current component is mounted into. */
21
+ name: UISlotName;
22
+ /** Name of the plugin that registered the current slot component. */
23
+ plugin: string;
24
+ /** Current route, when a content route is active. */
25
+ route?: RouteItem;
26
+ /** Current locale, for example `zh-CN` or `en-US`. */
27
+ locale?: string;
28
+ /** Built-in default component for replacement slots. */
29
+ DefaultComponent?: ComponentType;
30
+ };
31
+ /**
32
+ * A runtime UI extension declared by a plugin. The CLI compiles every
33
+ * registration into `virtual:clarify/slots`.
34
+ */
35
+ export type UISlotRegistration = {
36
+ /** Target slot position. */
37
+ name: UISlotName;
38
+ /**
39
+ * Module path of the React component to mount.
40
+ *
41
+ * Use `/` prefix to reference files relative to the project root, for
42
+ * example:
43
+ * ```
44
+ * component: '/source/plugins/custom-footer.tsx'
45
+ * ```
46
+ *
47
+ * The component is imported as a default export.
48
+ */
49
+ component: string;
50
+ };
@@ -0,0 +1,7 @@
1
+ import { LocalizedText } from '../core/types';
2
+ /**
3
+ * Resolve a localized text value for the given locale.
4
+ * Falls back to the fallback locale, then the first available value,
5
+ * then an empty string.
6
+ */
7
+ export declare function resolveLocalizedText(text: LocalizedText, locale?: string, fallbackLocale?: string): string;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@clarify-labs/renderer",
3
- "version": "0.7.2",
3
+ "version": "0.8.2",
4
4
  "license": "AGPL-3.0-only",
5
5
  "type": "module",
6
6
  "repository": {
@@ -54,7 +54,9 @@
54
54
  "build": "vite build",
55
55
  "lint": "eslint source/",
56
56
  "lint:fix": "eslint source/ --fix",
57
- "typecheck": "tsc -p tsconfig.json --noEmit"
57
+ "typecheck": "tsc -p tsconfig.json --noEmit",
58
+ "test": "vitest run",
59
+ "test:watch": "vitest"
58
60
  },
59
61
  "peerDependencies": {
60
62
  "react": "^19.0.0",
@@ -72,7 +74,8 @@
72
74
  "tailwindcss": "^4.1.11",
73
75
  "typescript": "^5.8.3",
74
76
  "vite": "^8.0.15",
75
- "vite-plugin-dts": "^4.5.4"
77
+ "vite-plugin-dts": "^4.5.4",
78
+ "vitest": "^4.1.9"
76
79
  },
77
80
  "dependencies": {
78
81
  "@headlessui/react": "^2.2.10",
@@ -82,8 +85,10 @@
82
85
  "framer-motion": "^12.40.0",
83
86
  "github-slugger": "^2.0.0",
84
87
  "lucide-react": "^1.20.0",
88
+ "mermaid": "^11.4.0",
85
89
  "openapi-types": "^12.1.3",
86
90
  "react-markdown": "^10.1.0",
91
+ "react-zoom-pan-pinch": "^4.0.3",
87
92
  "remark-gfm": "^4.0.1",
88
93
  "zustand": "^5.0.14"
89
94
  }