@plenary/react 0.1.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/LICENSE +21 -0
- package/dist/bridge.d.ts +34 -0
- package/dist/bridge.js +452 -0
- package/dist/bridge.js.map +1 -0
- package/dist/components/Box.d.ts +14 -0
- package/dist/components/Box.js +8 -0
- package/dist/components/Box.js.map +1 -0
- package/dist/components/Form.d.ts +36 -0
- package/dist/components/Form.js +280 -0
- package/dist/components/Form.js.map +1 -0
- package/dist/components/Image.d.ts +25 -0
- package/dist/components/Image.js +116 -0
- package/dist/components/Image.js.map +1 -0
- package/dist/components/Placeholder.d.ts +12 -0
- package/dist/components/Placeholder.js +24 -0
- package/dist/components/Placeholder.js.map +1 -0
- package/dist/components/Section.d.ts +20 -0
- package/dist/components/Section.js +15 -0
- package/dist/components/Section.js.map +1 -0
- package/dist/components/Text.d.ts +15 -0
- package/dist/components/Text.js +8 -0
- package/dist/components/Text.js.map +1 -0
- package/dist/components/Video.d.ts +48 -0
- package/dist/components/Video.js +131 -0
- package/dist/components/Video.js.map +1 -0
- package/dist/context.d.ts +26 -0
- package/dist/context.js +20 -0
- package/dist/context.js.map +1 -0
- package/dist/form.d.ts +25 -0
- package/dist/form.js +11 -0
- package/dist/form.js.map +1 -0
- package/dist/index.d.ts +16 -0
- package/dist/index.js +55 -0
- package/dist/index.js.map +1 -0
- package/dist/media.d.ts +60 -0
- package/dist/media.js +74 -0
- package/dist/media.js.map +1 -0
- package/dist/registry.d.ts +45 -0
- package/dist/registry.js +232 -0
- package/dist/registry.js.map +1 -0
- package/dist/render.d.ts +46 -0
- package/dist/render.js +179 -0
- package/dist/render.js.map +1 -0
- package/dist/types.d.ts +24 -0
- package/dist/types.js +1 -0
- package/dist/types.js.map +1 -0
- package/package.json +46 -0
|
@@ -0,0 +1,131 @@
|
|
|
1
|
+
import { jsx, jsxs } from "react/jsx-runtime";
|
|
2
|
+
function VideoPlaceholder({ className, style }) {
|
|
3
|
+
return /* @__PURE__ */ jsx(
|
|
4
|
+
"div",
|
|
5
|
+
{
|
|
6
|
+
"data-plenary-video-placeholder": "",
|
|
7
|
+
className,
|
|
8
|
+
style: {
|
|
9
|
+
display: "flex",
|
|
10
|
+
alignItems: "center",
|
|
11
|
+
justifyContent: "center",
|
|
12
|
+
minHeight: 120,
|
|
13
|
+
border: "1px dashed #94a3b8",
|
|
14
|
+
borderRadius: 4,
|
|
15
|
+
background: "#f1f5f9",
|
|
16
|
+
color: "#94a3b8",
|
|
17
|
+
...style
|
|
18
|
+
},
|
|
19
|
+
children: /* @__PURE__ */ jsxs(
|
|
20
|
+
"svg",
|
|
21
|
+
{
|
|
22
|
+
width: "32",
|
|
23
|
+
height: "32",
|
|
24
|
+
viewBox: "0 0 24 24",
|
|
25
|
+
fill: "none",
|
|
26
|
+
stroke: "currentColor",
|
|
27
|
+
strokeWidth: "1.5",
|
|
28
|
+
strokeLinecap: "round",
|
|
29
|
+
strokeLinejoin: "round",
|
|
30
|
+
"aria-hidden": "true",
|
|
31
|
+
children: [
|
|
32
|
+
/* @__PURE__ */ jsx("rect", { x: "3", y: "5", width: "18", height: "14", rx: "2" }),
|
|
33
|
+
/* @__PURE__ */ jsx("path", { d: "m10 9 5 3-5 3z" })
|
|
34
|
+
]
|
|
35
|
+
}
|
|
36
|
+
)
|
|
37
|
+
}
|
|
38
|
+
);
|
|
39
|
+
}
|
|
40
|
+
function MissingVideoPlaceholder({
|
|
41
|
+
className,
|
|
42
|
+
style
|
|
43
|
+
}) {
|
|
44
|
+
return /* @__PURE__ */ jsxs(
|
|
45
|
+
"div",
|
|
46
|
+
{
|
|
47
|
+
"data-plenary-video-missing": "",
|
|
48
|
+
className,
|
|
49
|
+
title: "Video not found \u2014 it may have been deleted from the Media Library",
|
|
50
|
+
style: {
|
|
51
|
+
display: "flex",
|
|
52
|
+
flexDirection: "column",
|
|
53
|
+
alignItems: "center",
|
|
54
|
+
justifyContent: "center",
|
|
55
|
+
gap: 6,
|
|
56
|
+
minHeight: 120,
|
|
57
|
+
padding: 8,
|
|
58
|
+
border: "1px dashed #f87171",
|
|
59
|
+
borderRadius: 4,
|
|
60
|
+
background: "#fef2f2",
|
|
61
|
+
color: "#b91c1c",
|
|
62
|
+
font: "500 12px/1.4 system-ui, sans-serif",
|
|
63
|
+
textAlign: "center",
|
|
64
|
+
...style
|
|
65
|
+
},
|
|
66
|
+
children: [
|
|
67
|
+
/* @__PURE__ */ jsxs(
|
|
68
|
+
"svg",
|
|
69
|
+
{
|
|
70
|
+
width: "32",
|
|
71
|
+
height: "32",
|
|
72
|
+
viewBox: "0 0 24 24",
|
|
73
|
+
fill: "none",
|
|
74
|
+
stroke: "currentColor",
|
|
75
|
+
strokeWidth: "1.5",
|
|
76
|
+
strokeLinecap: "round",
|
|
77
|
+
strokeLinejoin: "round",
|
|
78
|
+
"aria-hidden": "true",
|
|
79
|
+
children: [
|
|
80
|
+
/* @__PURE__ */ jsx("rect", { x: "3", y: "5", width: "18", height: "14", rx: "2" }),
|
|
81
|
+
/* @__PURE__ */ jsx("path", { d: "m10 9 5 3-5 3z" }),
|
|
82
|
+
/* @__PURE__ */ jsx("path", { d: "m3 3 18 18" })
|
|
83
|
+
]
|
|
84
|
+
}
|
|
85
|
+
),
|
|
86
|
+
/* @__PURE__ */ jsx("span", { children: "Video not found" })
|
|
87
|
+
]
|
|
88
|
+
}
|
|
89
|
+
);
|
|
90
|
+
}
|
|
91
|
+
function Video({
|
|
92
|
+
media,
|
|
93
|
+
poster,
|
|
94
|
+
controls,
|
|
95
|
+
autoplay,
|
|
96
|
+
loop,
|
|
97
|
+
muted,
|
|
98
|
+
playsinline,
|
|
99
|
+
preload,
|
|
100
|
+
className,
|
|
101
|
+
style,
|
|
102
|
+
editor
|
|
103
|
+
}) {
|
|
104
|
+
if (media?.missing) {
|
|
105
|
+
return editor ? /* @__PURE__ */ jsx(MissingVideoPlaceholder, { className, style }) : null;
|
|
106
|
+
}
|
|
107
|
+
const url = media?.url;
|
|
108
|
+
if (!url) {
|
|
109
|
+
return editor ? /* @__PURE__ */ jsx(VideoPlaceholder, { className, style }) : null;
|
|
110
|
+
}
|
|
111
|
+
const baseStyle = { maxWidth: "100%", height: "auto", ...style };
|
|
112
|
+
return /* @__PURE__ */ jsx(
|
|
113
|
+
"video",
|
|
114
|
+
{
|
|
115
|
+
src: url,
|
|
116
|
+
poster: poster?.url || void 0,
|
|
117
|
+
controls: editor ? false : controls,
|
|
118
|
+
autoPlay: editor ? false : autoplay,
|
|
119
|
+
loop,
|
|
120
|
+
muted,
|
|
121
|
+
playsInline: playsinline,
|
|
122
|
+
preload,
|
|
123
|
+
className,
|
|
124
|
+
style: baseStyle
|
|
125
|
+
}
|
|
126
|
+
);
|
|
127
|
+
}
|
|
128
|
+
export {
|
|
129
|
+
Video
|
|
130
|
+
};
|
|
131
|
+
//# sourceMappingURL=Video.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../../src/components/Video.tsx"],"sourcesContent":["import type { CSSProperties } from \"react\";\nimport type { MediaValue, ResolvedMedia } from \"../media.js\";\n\nexport interface VideoProps {\n /** A resolved media value (the renderer resolves it before render). */\n media?: ResolvedMedia | MediaValue | null;\n /** Optional poster image, an independent media pick. */\n poster?: ResolvedMedia | MediaValue | null;\n controls?: boolean;\n autoplay?: boolean;\n loop?: boolean;\n muted?: boolean;\n playsinline?: boolean;\n preload?: \"none\" | \"metadata\" | \"auto\";\n className?: string;\n style?: CSSProperties;\n /** True on editor-preview renders; enables the no-media placeholder. */\n editor?: boolean;\n}\n\n/** An empty-state stand-in so a media-less Video block is visible and selectable. */\nfunction VideoPlaceholder({ className, style }: { className?: string; style?: CSSProperties }) {\n return (\n <div\n data-plenary-video-placeholder=\"\"\n className={className}\n style={{\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n minHeight: 120,\n border: \"1px dashed #94a3b8\",\n borderRadius: 4,\n background: \"#f1f5f9\",\n color: \"#94a3b8\",\n ...style,\n }}\n >\n <svg\n width=\"32\"\n height=\"32\"\n viewBox=\"0 0 24 24\"\n fill=\"none\"\n stroke=\"currentColor\"\n strokeWidth=\"1.5\"\n strokeLinecap=\"round\"\n strokeLinejoin=\"round\"\n aria-hidden=\"true\"\n >\n <rect x=\"3\" y=\"5\" width=\"18\" height=\"14\" rx=\"2\" />\n <path d=\"m10 9 5 3-5 3z\" />\n </svg>\n </div>\n );\n}\n\n/**\n * The stand-in for a dangling reference — an asset deleted from the Media\n * Library while blocks still point at it. The mirror of Image's, and distinct\n * from the empty-state placeholder for the same reason: \"this video is gone\"\n * and \"no video chosen yet\" are different problems.\n */\nfunction MissingVideoPlaceholder({\n className,\n style,\n}: {\n className?: string;\n style?: CSSProperties;\n}) {\n return (\n <div\n data-plenary-video-missing=\"\"\n className={className}\n title=\"Video not found — it may have been deleted from the Media Library\"\n style={{\n display: \"flex\",\n flexDirection: \"column\",\n alignItems: \"center\",\n justifyContent: \"center\",\n gap: 6,\n minHeight: 120,\n padding: 8,\n border: \"1px dashed #f87171\",\n borderRadius: 4,\n background: \"#fef2f2\",\n color: \"#b91c1c\",\n font: \"500 12px/1.4 system-ui, sans-serif\",\n textAlign: \"center\",\n ...style,\n }}\n >\n <svg\n width=\"32\"\n height=\"32\"\n viewBox=\"0 0 24 24\"\n fill=\"none\"\n stroke=\"currentColor\"\n strokeWidth=\"1.5\"\n strokeLinecap=\"round\"\n strokeLinejoin=\"round\"\n aria-hidden=\"true\"\n >\n <rect x=\"3\" y=\"5\" width=\"18\" height=\"14\" rx=\"2\" />\n <path d=\"m10 9 5 3-5 3z\" />\n <path d=\"m3 3 18 18\" />\n </svg>\n <span>Video not found</span>\n </div>\n );\n}\n\n/**\n * An HTML5 `video` sourced from a resolved media prop; the file is served\n * as uploaded (no transcoding). Without a URL it renders nothing on a\n * published page — but in the editor preview it renders a placeholder, so a\n * Video block with no media assigned can still be seen and selected. A\n * reference whose asset was deleted gets its own placeholder, so the editor can\n * tell it apart from an unset one.\n *\n * A deleted *poster* needs no such handling: its URL is dropped with the rest\n * of the missing value, so the player simply renders without one.\n *\n * Editor previews render the player inert: the native controls are hidden so\n * a canvas click selects the block instead of toggling playback (a video\n * without controls ignores clicks, and the events bubble to the bridge's\n * selection handler — pointer-events must stay on, or the node would be\n * unhoverable since its annotation wrapper has no box of its own), and\n * autoplay is suppressed so nothing plays while editing.\n *\n * A replaced element renders at the file's intrinsic pixel size by default,\n * which overflows any smaller container (e.g. a section column) — so the\n * responsive default `max-width: 100%; height: auto` is baked in. The Style\n * tab still wins: its compiled sheet applies with `!important`, and explicit\n * inline `style` values override the defaults via merge order.\n */\nexport function Video({\n media,\n poster,\n controls,\n autoplay,\n loop,\n muted,\n playsinline,\n preload,\n className,\n style,\n editor,\n}: VideoProps) {\n if (media?.missing) {\n return editor ? <MissingVideoPlaceholder className={className} style={style} /> : null;\n }\n\n const url = media?.url;\n if (!url) {\n return editor ? <VideoPlaceholder className={className} style={style} /> : null;\n }\n\n const baseStyle: CSSProperties = { maxWidth: \"100%\", height: \"auto\", ...style };\n\n return (\n <video\n src={url}\n poster={poster?.url || undefined}\n controls={editor ? false : controls}\n autoPlay={editor ? false : autoplay}\n loop={loop}\n muted={muted}\n playsInline={playsinline}\n preload={preload}\n className={className}\n style={baseStyle}\n />\n );\n}\n"],"mappings":"AAsCM,SAWE,KAXF;AAjBN,SAAS,iBAAiB,EAAE,WAAW,MAAM,GAAkD;AAC7F,SACE;AAAA,IAAC;AAAA;AAAA,MACC,kCAA+B;AAAA,MAC/B;AAAA,MACA,OAAO;AAAA,QACL,SAAS;AAAA,QACT,YAAY;AAAA,QACZ,gBAAgB;AAAA,QAChB,WAAW;AAAA,QACX,QAAQ;AAAA,QACR,cAAc;AAAA,QACd,YAAY;AAAA,QACZ,OAAO;AAAA,QACP,GAAG;AAAA,MACL;AAAA,MAEA;AAAA,QAAC;AAAA;AAAA,UACC,OAAM;AAAA,UACN,QAAO;AAAA,UACP,SAAQ;AAAA,UACR,MAAK;AAAA,UACL,QAAO;AAAA,UACP,aAAY;AAAA,UACZ,eAAc;AAAA,UACd,gBAAe;AAAA,UACf,eAAY;AAAA,UAEZ;AAAA,gCAAC,UAAK,GAAE,KAAI,GAAE,KAAI,OAAM,MAAK,QAAO,MAAK,IAAG,KAAI;AAAA,YAChD,oBAAC,UAAK,GAAE,kBAAiB;AAAA;AAAA;AAAA,MAC3B;AAAA;AAAA,EACF;AAEJ;AAQA,SAAS,wBAAwB;AAAA,EAC/B;AAAA,EACA;AACF,GAGG;AACD,SACE;AAAA,IAAC;AAAA;AAAA,MACC,8BAA2B;AAAA,MAC3B;AAAA,MACA,OAAM;AAAA,MACN,OAAO;AAAA,QACL,SAAS;AAAA,QACT,eAAe;AAAA,QACf,YAAY;AAAA,QACZ,gBAAgB;AAAA,QAChB,KAAK;AAAA,QACL,WAAW;AAAA,QACX,SAAS;AAAA,QACT,QAAQ;AAAA,QACR,cAAc;AAAA,QACd,YAAY;AAAA,QACZ,OAAO;AAAA,QACP,MAAM;AAAA,QACN,WAAW;AAAA,QACX,GAAG;AAAA,MACL;AAAA,MAEA;AAAA;AAAA,UAAC;AAAA;AAAA,YACC,OAAM;AAAA,YACN,QAAO;AAAA,YACP,SAAQ;AAAA,YACR,MAAK;AAAA,YACL,QAAO;AAAA,YACP,aAAY;AAAA,YACZ,eAAc;AAAA,YACd,gBAAe;AAAA,YACf,eAAY;AAAA,YAEZ;AAAA,kCAAC,UAAK,GAAE,KAAI,GAAE,KAAI,OAAM,MAAK,QAAO,MAAK,IAAG,KAAI;AAAA,cAChD,oBAAC,UAAK,GAAE,kBAAiB;AAAA,cACzB,oBAAC,UAAK,GAAE,cAAa;AAAA;AAAA;AAAA,QACvB;AAAA,QACA,oBAAC,UAAK,6BAAe;AAAA;AAAA;AAAA,EACvB;AAEJ;AA0BO,SAAS,MAAM;AAAA,EACpB;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AACF,GAAe;AACb,MAAI,OAAO,SAAS;AAClB,WAAO,SAAS,oBAAC,2BAAwB,WAAsB,OAAc,IAAK;AAAA,EACpF;AAEA,QAAM,MAAM,OAAO;AACnB,MAAI,CAAC,KAAK;AACR,WAAO,SAAS,oBAAC,oBAAiB,WAAsB,OAAc,IAAK;AAAA,EAC7E;AAEA,QAAM,YAA2B,EAAE,UAAU,QAAQ,QAAQ,QAAQ,GAAG,MAAM;AAE9E,SACE;AAAA,IAAC;AAAA;AAAA,MACC,KAAK;AAAA,MACL,QAAQ,QAAQ,OAAO;AAAA,MACvB,UAAU,SAAS,QAAQ;AAAA,MAC3B,UAAU,SAAS,QAAQ;AAAA,MAC3B;AAAA,MACA;AAAA,MACA,aAAa;AAAA,MACb;AAAA,MACA;AAAA,MACA,OAAO;AAAA;AAAA,EACT;AAEJ;","names":[]}
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
import * as react from 'react';
|
|
2
|
+
import { ReactNode } from 'react';
|
|
3
|
+
import { PlenaryClient, ClientConfig } from '@plenary/client';
|
|
4
|
+
|
|
5
|
+
interface PlenaryProviderProps {
|
|
6
|
+
/** An already-created client (client-rendered apps). */
|
|
7
|
+
client?: PlenaryClient;
|
|
8
|
+
/**
|
|
9
|
+
* Or the client config, from which the provider creates one. This is the
|
|
10
|
+
* RSC-safe path: a client instance cannot cross a server/client component
|
|
11
|
+
* boundary, but plain config can (the API key is a public delivery key, so
|
|
12
|
+
* shipping it to the browser is by design).
|
|
13
|
+
*/
|
|
14
|
+
config?: ClientConfig;
|
|
15
|
+
children?: ReactNode;
|
|
16
|
+
}
|
|
17
|
+
/**
|
|
18
|
+
* Provides a `PlenaryClient` to components that act at runtime in the browser —
|
|
19
|
+
* today the built-in Form block, which submits through it. Rendering content
|
|
20
|
+
* does not require the provider; only interactive blocks do.
|
|
21
|
+
*/
|
|
22
|
+
declare function PlenaryProvider({ client, config, children }: PlenaryProviderProps): react.JSX.Element;
|
|
23
|
+
/** The nearest provided client, or `null` outside a {@link PlenaryProvider}. */
|
|
24
|
+
declare function usePlenaryClient(): PlenaryClient | null;
|
|
25
|
+
|
|
26
|
+
export { PlenaryProvider, type PlenaryProviderProps, usePlenaryClient };
|
package/dist/context.js
ADDED
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
"use client";
|
|
2
|
+
import { jsx } from "react/jsx-runtime";
|
|
3
|
+
import { createContext, useContext, useMemo } from "react";
|
|
4
|
+
import { createClient } from "@plenary/client";
|
|
5
|
+
const PlenaryClientContext = createContext(null);
|
|
6
|
+
function PlenaryProvider({ client, config, children }) {
|
|
7
|
+
const value = useMemo(
|
|
8
|
+
() => client ?? (config ? createClient(config) : null),
|
|
9
|
+
[client, config?.baseUrl, config?.siteKey, config?.apiKey, config?.locale, config?.fetch]
|
|
10
|
+
);
|
|
11
|
+
return /* @__PURE__ */ jsx(PlenaryClientContext.Provider, { value, children });
|
|
12
|
+
}
|
|
13
|
+
function usePlenaryClient() {
|
|
14
|
+
return useContext(PlenaryClientContext);
|
|
15
|
+
}
|
|
16
|
+
export {
|
|
17
|
+
PlenaryProvider,
|
|
18
|
+
usePlenaryClient
|
|
19
|
+
};
|
|
20
|
+
//# sourceMappingURL=context.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/context.tsx"],"sourcesContent":["\"use client\";\n\nimport { createContext, useContext, useMemo, type ReactNode } from \"react\";\nimport { createClient, type ClientConfig, type PlenaryClient } from \"@plenary/client\";\n\nconst PlenaryClientContext = createContext<PlenaryClient | null>(null);\n\nexport interface PlenaryProviderProps {\n /** An already-created client (client-rendered apps). */\n client?: PlenaryClient;\n /**\n * Or the client config, from which the provider creates one. This is the\n * RSC-safe path: a client instance cannot cross a server/client component\n * boundary, but plain config can (the API key is a public delivery key, so\n * shipping it to the browser is by design).\n */\n config?: ClientConfig;\n children?: ReactNode;\n}\n\n/**\n * Provides a `PlenaryClient` to components that act at runtime in the browser —\n * today the built-in Form block, which submits through it. Rendering content\n * does not require the provider; only interactive blocks do.\n */\nexport function PlenaryProvider({ client, config, children }: PlenaryProviderProps) {\n // Keyed on config fields, not object identity — an inline config literal\n // must not rebuild the client (and re-render every consumer) each render.\n const value = useMemo(\n () => client ?? (config ? createClient(config) : null),\n [client, config?.baseUrl, config?.siteKey, config?.apiKey, config?.locale, config?.fetch],\n );\n return <PlenaryClientContext.Provider value={value}>{children}</PlenaryClientContext.Provider>;\n}\n\n/** The nearest provided client, or `null` outside a {@link PlenaryProvider}. */\nexport function usePlenaryClient(): PlenaryClient | null {\n return useContext(PlenaryClientContext);\n}\n"],"mappings":";AAgCS;AA9BT,SAAS,eAAe,YAAY,eAA+B;AACnE,SAAS,oBAA2D;AAEpE,MAAM,uBAAuB,cAAoC,IAAI;AAoB9D,SAAS,gBAAgB,EAAE,QAAQ,QAAQ,SAAS,GAAyB;AAGlF,QAAM,QAAQ;AAAA,IACZ,MAAM,WAAW,SAAS,aAAa,MAAM,IAAI;AAAA,IACjD,CAAC,QAAQ,QAAQ,SAAS,QAAQ,SAAS,QAAQ,QAAQ,QAAQ,QAAQ,QAAQ,KAAK;AAAA,EAC1F;AACA,SAAO,oBAAC,qBAAqB,UAArB,EAA8B,OAAe,UAAS;AAChE;AAGO,SAAS,mBAAyC;AACvD,SAAO,WAAW,oBAAoB;AACxC;","names":[]}
|
package/dist/form.d.ts
ADDED
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
import { PublicFormDefinition } from '@plenary/client';
|
|
2
|
+
|
|
3
|
+
/** The raw value a `form` prop holds in the dom: a pointer to a form by key. */
|
|
4
|
+
interface FormValue {
|
|
5
|
+
form_key?: string;
|
|
6
|
+
/** Present when the value was already resolved (the preview inlines it). */
|
|
7
|
+
definition?: PublicFormDefinition | null;
|
|
8
|
+
}
|
|
9
|
+
/**
|
|
10
|
+
* The shape a component sees after resolution. `definition` is `null` when the
|
|
11
|
+
* form could not be fetched (deleted, inactive, not on this site, no client).
|
|
12
|
+
*/
|
|
13
|
+
interface ResolvedForm {
|
|
14
|
+
form_key: string;
|
|
15
|
+
definition: PublicFormDefinition | null;
|
|
16
|
+
}
|
|
17
|
+
/**
|
|
18
|
+
* Merge a form prop value with its (optional) fetched definition into the
|
|
19
|
+
* resolved shape a component sees. Pure and synchronous — the renderer calls it
|
|
20
|
+
* after a batch definition fetch. A value that already carries a definition
|
|
21
|
+
* (the preview inlines one) is used as-is.
|
|
22
|
+
*/
|
|
23
|
+
declare function toResolvedForm(value: FormValue | null | undefined, definition?: PublicFormDefinition | null): ResolvedForm | null;
|
|
24
|
+
|
|
25
|
+
export { type FormValue, type ResolvedForm, toResolvedForm };
|
package/dist/form.js
ADDED
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
function toResolvedForm(value, definition) {
|
|
2
|
+
if (!value || !value.form_key) return null;
|
|
3
|
+
return {
|
|
4
|
+
form_key: value.form_key,
|
|
5
|
+
definition: value.definition !== void 0 ? value.definition : definition ?? null
|
|
6
|
+
};
|
|
7
|
+
}
|
|
8
|
+
export {
|
|
9
|
+
toResolvedForm
|
|
10
|
+
};
|
|
11
|
+
//# sourceMappingURL=form.js.map
|
package/dist/form.js.map
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/form.ts"],"sourcesContent":["import type { PublicFormDefinition } from \"@plenary/client\";\n\n/** The raw value a `form` prop holds in the dom: a pointer to a form by key. */\nexport interface FormValue {\n form_key?: string;\n /** Present when the value was already resolved (the preview inlines it). */\n definition?: PublicFormDefinition | null;\n}\n\n/**\n * The shape a component sees after resolution. `definition` is `null` when the\n * form could not be fetched (deleted, inactive, not on this site, no client).\n */\nexport interface ResolvedForm {\n form_key: string;\n definition: PublicFormDefinition | null;\n}\n\n/**\n * Merge a form prop value with its (optional) fetched definition into the\n * resolved shape a component sees. Pure and synchronous — the renderer calls it\n * after a batch definition fetch. A value that already carries a definition\n * (the preview inlines one) is used as-is.\n */\nexport function toResolvedForm(\n value: FormValue | null | undefined,\n definition?: PublicFormDefinition | null,\n): ResolvedForm | null {\n if (!value || !value.form_key) return null;\n return {\n form_key: value.form_key,\n definition: value.definition !== undefined ? value.definition : (definition ?? null),\n };\n}\n"],"mappings":"AAwBO,SAAS,eACd,OACA,YACqB;AACrB,MAAI,CAAC,SAAS,CAAC,MAAM,SAAU,QAAO;AACtC,SAAO;AAAA,IACL,UAAU,MAAM;AAAA,IAChB,YAAY,MAAM,eAAe,SAAY,MAAM,aAAc,cAAc;AAAA,EACjF;AACF;","names":[]}
|
package/dist/index.d.ts
ADDED
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
export { PlenaryPage, PlenaryPageProps, SyncRenderOptions, renderDocument, renderDocumentSync } from './render.js';
|
|
2
|
+
export { Plenary, Registry, getManifest, getTheme, register, registerTheme, registry } from './registry.js';
|
|
3
|
+
export { Box, BoxProps } from './components/Box.js';
|
|
4
|
+
export { Section, SectionProps } from './components/Section.js';
|
|
5
|
+
export { Text, TextProps } from './components/Text.js';
|
|
6
|
+
export { Image, ImageProps } from './components/Image.js';
|
|
7
|
+
export { Video, VideoProps } from './components/Video.js';
|
|
8
|
+
export { Form, FormProps } from './components/Form.js';
|
|
9
|
+
export { Placeholder, PlaceholderProps } from './components/Placeholder.js';
|
|
10
|
+
export { MediaValue, ResolvedMedia, resolveMedia, toResolvedMedia } from './media.js';
|
|
11
|
+
export { FormValue, ResolvedForm, toResolvedForm } from './form.js';
|
|
12
|
+
export { PlenaryProvider, PlenaryProviderProps, usePlenaryClient } from './context.js';
|
|
13
|
+
export { PlenaryComponent, RegisteredComponent, RenderContext, SlotProps } from './types.js';
|
|
14
|
+
import 'react';
|
|
15
|
+
import '@plenary/client';
|
|
16
|
+
import '@plenary/core';
|
package/dist/index.js
ADDED
|
@@ -0,0 +1,55 @@
|
|
|
1
|
+
import {
|
|
2
|
+
PlenaryPage,
|
|
3
|
+
renderDocument,
|
|
4
|
+
renderDocumentSync
|
|
5
|
+
} from "./render.js";
|
|
6
|
+
import {
|
|
7
|
+
Registry,
|
|
8
|
+
registry,
|
|
9
|
+
register,
|
|
10
|
+
registerTheme,
|
|
11
|
+
Plenary,
|
|
12
|
+
getManifest,
|
|
13
|
+
getTheme
|
|
14
|
+
} from "./registry.js";
|
|
15
|
+
import { Box } from "./components/Box.js";
|
|
16
|
+
import { Section } from "./components/Section.js";
|
|
17
|
+
import { Text } from "./components/Text.js";
|
|
18
|
+
import { Image } from "./components/Image.js";
|
|
19
|
+
import { Video } from "./components/Video.js";
|
|
20
|
+
import { Form } from "./components/Form.js";
|
|
21
|
+
import { Placeholder } from "./components/Placeholder.js";
|
|
22
|
+
import {
|
|
23
|
+
resolveMedia,
|
|
24
|
+
toResolvedMedia
|
|
25
|
+
} from "./media.js";
|
|
26
|
+
import { toResolvedForm } from "./form.js";
|
|
27
|
+
import {
|
|
28
|
+
PlenaryProvider,
|
|
29
|
+
usePlenaryClient
|
|
30
|
+
} from "./context.js";
|
|
31
|
+
export {
|
|
32
|
+
Box,
|
|
33
|
+
Form,
|
|
34
|
+
Image,
|
|
35
|
+
Placeholder,
|
|
36
|
+
Plenary,
|
|
37
|
+
PlenaryPage,
|
|
38
|
+
PlenaryProvider,
|
|
39
|
+
Registry,
|
|
40
|
+
Section,
|
|
41
|
+
Text,
|
|
42
|
+
Video,
|
|
43
|
+
getManifest,
|
|
44
|
+
getTheme,
|
|
45
|
+
register,
|
|
46
|
+
registerTheme,
|
|
47
|
+
registry,
|
|
48
|
+
renderDocument,
|
|
49
|
+
renderDocumentSync,
|
|
50
|
+
resolveMedia,
|
|
51
|
+
toResolvedForm,
|
|
52
|
+
toResolvedMedia,
|
|
53
|
+
usePlenaryClient
|
|
54
|
+
};
|
|
55
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/index.ts"],"sourcesContent":["/**\n * @plenary/react — the DOM renderer, component registry, and built-in\n * components (Box/Section/Text/Image/Video/Form) for rendering a Page's `dom`\n * tree. Custom components register on top of the built-ins. The preview bridge\n * lands in Phase 5.\n */\n\nexport {\n PlenaryPage,\n renderDocument,\n renderDocumentSync,\n type PlenaryPageProps,\n type SyncRenderOptions,\n} from \"./render.js\";\nexport {\n Registry,\n registry,\n register,\n registerTheme,\n Plenary,\n getManifest,\n getTheme,\n} from \"./registry.js\";\nexport { Box, type BoxProps } from \"./components/Box.js\";\nexport { Section, type SectionProps } from \"./components/Section.js\";\nexport { Text, type TextProps } from \"./components/Text.js\";\nexport { Image, type ImageProps } from \"./components/Image.js\";\nexport { Video, type VideoProps } from \"./components/Video.js\";\nexport { Form, type FormProps } from \"./components/Form.js\";\nexport { Placeholder, type PlaceholderProps } from \"./components/Placeholder.js\";\nexport {\n resolveMedia,\n toResolvedMedia,\n type MediaValue,\n type ResolvedMedia,\n} from \"./media.js\";\nexport { toResolvedForm, type FormValue, type ResolvedForm } from \"./form.js\";\nexport {\n PlenaryProvider,\n usePlenaryClient,\n type PlenaryProviderProps,\n} from \"./context.js\";\nexport type {\n PlenaryComponent,\n RegisteredComponent,\n RenderContext,\n SlotProps,\n} from \"./types.js\";\n"],"mappings":"AAOA;AAAA,EACE;AAAA,EACA;AAAA,EACA;AAAA,OAGK;AACP;AAAA,EACE;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,OACK;AACP,SAAS,WAA0B;AACnC,SAAS,eAAkC;AAC3C,SAAS,YAA4B;AACrC,SAAS,aAA8B;AACvC,SAAS,aAA8B;AACvC,SAAS,YAA4B;AACrC,SAAS,mBAA0C;AACnD;AAAA,EACE;AAAA,EACA;AAAA,OAGK;AACP,SAAS,sBAAyD;AAClE;AAAA,EACE;AAAA,EACA;AAAA,OAEK;","names":[]}
|
package/dist/media.d.ts
ADDED
|
@@ -0,0 +1,60 @@
|
|
|
1
|
+
import { PlenaryClient, MediaDetail } from '@plenary/client';
|
|
2
|
+
|
|
3
|
+
/** The raw value an `image`/`file` prop holds in the dom: a media pointer. */
|
|
4
|
+
interface MediaValue {
|
|
5
|
+
media_id?: string;
|
|
6
|
+
alt?: string;
|
|
7
|
+
caption?: string;
|
|
8
|
+
/** Present when the value was already resolved (carries a URL). */
|
|
9
|
+
url?: string;
|
|
10
|
+
variants?: Record<string, string>;
|
|
11
|
+
/** Server-hydrated URL of the block's one-off variant spec (Image block). */
|
|
12
|
+
variant_url?: string;
|
|
13
|
+
width?: number;
|
|
14
|
+
height?: number;
|
|
15
|
+
/**
|
|
16
|
+
* Set when the referenced asset no longer exists. The editor preview marks
|
|
17
|
+
* values whose detail lookup 404s, so the renderer can tell a dangling
|
|
18
|
+
* pointer from one it simply has not resolved yet.
|
|
19
|
+
*/
|
|
20
|
+
missing?: boolean;
|
|
21
|
+
}
|
|
22
|
+
/** The shape a component sees after resolution. `url` is `""` when unresolved. */
|
|
23
|
+
interface ResolvedMedia {
|
|
24
|
+
media_id?: string;
|
|
25
|
+
url: string;
|
|
26
|
+
alt: string;
|
|
27
|
+
variants: Record<string, string>;
|
|
28
|
+
/** Server-hydrated URL of the block's one-off variant spec (Image block). */
|
|
29
|
+
variant_url?: string;
|
|
30
|
+
caption?: string;
|
|
31
|
+
width?: number;
|
|
32
|
+
height?: number;
|
|
33
|
+
/** The asset this value points at was deleted — the reference is dangling. */
|
|
34
|
+
missing?: boolean;
|
|
35
|
+
}
|
|
36
|
+
/**
|
|
37
|
+
* Merge a media prop value with its (optional) fetched detail into the resolved
|
|
38
|
+
* shape a component sees. Pure and synchronous — the renderer calls it after a
|
|
39
|
+
* batch media fetch. When the value is already resolved it is used as-is; when
|
|
40
|
+
* no detail is available the result is unresolved (empty `url`).
|
|
41
|
+
*
|
|
42
|
+
* `missing` reports that the lookup found the asset gone (a 404, not a failure
|
|
43
|
+
* to fetch); the value's own `missing` flag says the same thing when the
|
|
44
|
+
* console resolved it. Either way every URL on the value is dropped: the server
|
|
45
|
+
* derives an Image block's `variant_url` by content address, without checking
|
|
46
|
+
* the asset still exists, so a stored one outlives the file it names.
|
|
47
|
+
*/
|
|
48
|
+
declare function toResolvedMedia(value: MediaValue | null | undefined, detail?: MediaDetail | null, missing?: boolean): ResolvedMedia | null;
|
|
49
|
+
/**
|
|
50
|
+
* Resolve a media-typed prop value to `{ url, alt, variants }`.
|
|
51
|
+
*
|
|
52
|
+
* - A value already carrying a `url` is used as-is — no fetch.
|
|
53
|
+
* - A bare `{ media_id }` is fetched via the client. A 404 means the asset was
|
|
54
|
+
* deleted, and resolves to a `missing` value; any other failure degrades to
|
|
55
|
+
* an unresolved value (empty `url`) rather than throwing.
|
|
56
|
+
* - Anything without a `media_id` or `url` resolves to `null`.
|
|
57
|
+
*/
|
|
58
|
+
declare function resolveMedia(value: MediaValue | null | undefined, client?: PlenaryClient): Promise<ResolvedMedia | null>;
|
|
59
|
+
|
|
60
|
+
export { type MediaValue, type ResolvedMedia, resolveMedia, toResolvedMedia };
|
package/dist/media.js
ADDED
|
@@ -0,0 +1,74 @@
|
|
|
1
|
+
import { PlenaryNotFoundError } from "@plenary/client";
|
|
2
|
+
function readyVariants(detail) {
|
|
3
|
+
const out = {};
|
|
4
|
+
for (const [key, v] of Object.entries(detail.variants ?? {})) {
|
|
5
|
+
if (v.url) out[key] = v.url;
|
|
6
|
+
}
|
|
7
|
+
return out;
|
|
8
|
+
}
|
|
9
|
+
function isResolved(value) {
|
|
10
|
+
return typeof value.url === "string" && value.url !== "";
|
|
11
|
+
}
|
|
12
|
+
function toResolvedMedia(value, detail, missing) {
|
|
13
|
+
if (!value) return null;
|
|
14
|
+
if ((missing || value.missing) && value.media_id) {
|
|
15
|
+
return {
|
|
16
|
+
media_id: value.media_id,
|
|
17
|
+
url: "",
|
|
18
|
+
alt: value.alt ?? value.caption ?? "",
|
|
19
|
+
variants: {},
|
|
20
|
+
caption: value.caption,
|
|
21
|
+
missing: true
|
|
22
|
+
};
|
|
23
|
+
}
|
|
24
|
+
if (isResolved(value)) {
|
|
25
|
+
return {
|
|
26
|
+
media_id: value.media_id,
|
|
27
|
+
url: value.url,
|
|
28
|
+
alt: value.alt ?? value.caption ?? "",
|
|
29
|
+
variants: value.variants ?? {},
|
|
30
|
+
variant_url: value.variant_url,
|
|
31
|
+
caption: value.caption,
|
|
32
|
+
width: value.width,
|
|
33
|
+
height: value.height
|
|
34
|
+
};
|
|
35
|
+
}
|
|
36
|
+
if (detail) {
|
|
37
|
+
return {
|
|
38
|
+
media_id: detail.media_id,
|
|
39
|
+
url: detail.original_url,
|
|
40
|
+
alt: value.alt ?? detail.label ?? detail.description ?? "",
|
|
41
|
+
variants: readyVariants(detail),
|
|
42
|
+
variant_url: value.variant_url,
|
|
43
|
+
caption: value.caption,
|
|
44
|
+
width: detail.width,
|
|
45
|
+
height: detail.height
|
|
46
|
+
};
|
|
47
|
+
}
|
|
48
|
+
if (value.media_id) {
|
|
49
|
+
return {
|
|
50
|
+
media_id: value.media_id,
|
|
51
|
+
url: "",
|
|
52
|
+
alt: value.alt ?? value.caption ?? "",
|
|
53
|
+
variants: {},
|
|
54
|
+
variant_url: value.variant_url,
|
|
55
|
+
caption: value.caption
|
|
56
|
+
};
|
|
57
|
+
}
|
|
58
|
+
return null;
|
|
59
|
+
}
|
|
60
|
+
async function resolveMedia(value, client) {
|
|
61
|
+
if (!value || isResolved(value) || !value.media_id || !client) {
|
|
62
|
+
return toResolvedMedia(value);
|
|
63
|
+
}
|
|
64
|
+
try {
|
|
65
|
+
return toResolvedMedia(value, await client.getMedia(value.media_id));
|
|
66
|
+
} catch (err) {
|
|
67
|
+
return toResolvedMedia(value, null, err instanceof PlenaryNotFoundError);
|
|
68
|
+
}
|
|
69
|
+
}
|
|
70
|
+
export {
|
|
71
|
+
resolveMedia,
|
|
72
|
+
toResolvedMedia
|
|
73
|
+
};
|
|
74
|
+
//# sourceMappingURL=media.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/media.ts"],"sourcesContent":["import { PlenaryNotFoundError, type PlenaryClient, type MediaDetail } from \"@plenary/client\";\n\n/** The raw value an `image`/`file` prop holds in the dom: a media pointer. */\nexport interface MediaValue {\n media_id?: string;\n alt?: string;\n caption?: string;\n /** Present when the value was already resolved (carries a URL). */\n url?: string;\n variants?: Record<string, string>;\n /** Server-hydrated URL of the block's one-off variant spec (Image block). */\n variant_url?: string;\n width?: number;\n height?: number;\n /**\n * Set when the referenced asset no longer exists. The editor preview marks\n * values whose detail lookup 404s, so the renderer can tell a dangling\n * pointer from one it simply has not resolved yet.\n */\n missing?: boolean;\n}\n\n/** The shape a component sees after resolution. `url` is `\"\"` when unresolved. */\nexport interface ResolvedMedia {\n media_id?: string;\n url: string;\n alt: string;\n variants: Record<string, string>;\n /** Server-hydrated URL of the block's one-off variant spec (Image block). */\n variant_url?: string;\n caption?: string;\n width?: number;\n height?: number;\n /** The asset this value points at was deleted — the reference is dangling. */\n missing?: boolean;\n}\n\nfunction readyVariants(detail: MediaDetail): Record<string, string> {\n const out: Record<string, string> = {};\n for (const [key, v] of Object.entries(detail.variants ?? {})) {\n if (v.url) out[key] = v.url;\n }\n return out;\n}\n\n/** True when the value already carries a URL and needs no client fetch. */\nfunction isResolved(value: MediaValue): value is MediaValue & { url: string } {\n return typeof value.url === \"string\" && value.url !== \"\";\n}\n\n/**\n * Merge a media prop value with its (optional) fetched detail into the resolved\n * shape a component sees. Pure and synchronous — the renderer calls it after a\n * batch media fetch. When the value is already resolved it is used as-is; when\n * no detail is available the result is unresolved (empty `url`).\n *\n * `missing` reports that the lookup found the asset gone (a 404, not a failure\n * to fetch); the value's own `missing` flag says the same thing when the\n * console resolved it. Either way every URL on the value is dropped: the server\n * derives an Image block's `variant_url` by content address, without checking\n * the asset still exists, so a stored one outlives the file it names.\n */\nexport function toResolvedMedia(\n value: MediaValue | null | undefined,\n detail?: MediaDetail | null,\n missing?: boolean,\n): ResolvedMedia | null {\n if (!value) return null;\n\n if ((missing || value.missing) && value.media_id) {\n return {\n media_id: value.media_id,\n url: \"\",\n alt: value.alt ?? value.caption ?? \"\",\n variants: {},\n caption: value.caption,\n missing: true,\n };\n }\n\n if (isResolved(value)) {\n return {\n media_id: value.media_id,\n url: value.url,\n alt: value.alt ?? value.caption ?? \"\",\n variants: value.variants ?? {},\n variant_url: value.variant_url,\n caption: value.caption,\n width: value.width,\n height: value.height,\n };\n }\n\n if (detail) {\n return {\n media_id: detail.media_id,\n url: detail.original_url,\n alt: value.alt ?? detail.label ?? detail.description ?? \"\",\n variants: readyVariants(detail),\n variant_url: value.variant_url,\n caption: value.caption,\n width: detail.width,\n height: detail.height,\n };\n }\n\n if (value.media_id) {\n return {\n media_id: value.media_id,\n url: \"\",\n alt: value.alt ?? value.caption ?? \"\",\n variants: {},\n variant_url: value.variant_url,\n caption: value.caption,\n };\n }\n\n return null;\n}\n\n/**\n * Resolve a media-typed prop value to `{ url, alt, variants }`.\n *\n * - A value already carrying a `url` is used as-is — no fetch.\n * - A bare `{ media_id }` is fetched via the client. A 404 means the asset was\n * deleted, and resolves to a `missing` value; any other failure degrades to\n * an unresolved value (empty `url`) rather than throwing.\n * - Anything without a `media_id` or `url` resolves to `null`.\n */\nexport async function resolveMedia(\n value: MediaValue | null | undefined,\n client?: PlenaryClient,\n): Promise<ResolvedMedia | null> {\n if (!value || isResolved(value) || !value.media_id || !client) {\n return toResolvedMedia(value);\n }\n try {\n return toResolvedMedia(value, await client.getMedia(value.media_id));\n } catch (err) {\n return toResolvedMedia(value, null, err instanceof PlenaryNotFoundError);\n }\n}\n"],"mappings":"AAAA,SAAS,4BAAkE;AAqC3E,SAAS,cAAc,QAA6C;AAClE,QAAM,MAA8B,CAAC;AACrC,aAAW,CAAC,KAAK,CAAC,KAAK,OAAO,QAAQ,OAAO,YAAY,CAAC,CAAC,GAAG;AAC5D,QAAI,EAAE,IAAK,KAAI,GAAG,IAAI,EAAE;AAAA,EAC1B;AACA,SAAO;AACT;AAGA,SAAS,WAAW,OAA0D;AAC5E,SAAO,OAAO,MAAM,QAAQ,YAAY,MAAM,QAAQ;AACxD;AAcO,SAAS,gBACd,OACA,QACA,SACsB;AACtB,MAAI,CAAC,MAAO,QAAO;AAEnB,OAAK,WAAW,MAAM,YAAY,MAAM,UAAU;AAChD,WAAO;AAAA,MACL,UAAU,MAAM;AAAA,MAChB,KAAK;AAAA,MACL,KAAK,MAAM,OAAO,MAAM,WAAW;AAAA,MACnC,UAAU,CAAC;AAAA,MACX,SAAS,MAAM;AAAA,MACf,SAAS;AAAA,IACX;AAAA,EACF;AAEA,MAAI,WAAW,KAAK,GAAG;AACrB,WAAO;AAAA,MACL,UAAU,MAAM;AAAA,MAChB,KAAK,MAAM;AAAA,MACX,KAAK,MAAM,OAAO,MAAM,WAAW;AAAA,MACnC,UAAU,MAAM,YAAY,CAAC;AAAA,MAC7B,aAAa,MAAM;AAAA,MACnB,SAAS,MAAM;AAAA,MACf,OAAO,MAAM;AAAA,MACb,QAAQ,MAAM;AAAA,IAChB;AAAA,EACF;AAEA,MAAI,QAAQ;AACV,WAAO;AAAA,MACL,UAAU,OAAO;AAAA,MACjB,KAAK,OAAO;AAAA,MACZ,KAAK,MAAM,OAAO,OAAO,SAAS,OAAO,eAAe;AAAA,MACxD,UAAU,cAAc,MAAM;AAAA,MAC9B,aAAa,MAAM;AAAA,MACnB,SAAS,MAAM;AAAA,MACf,OAAO,OAAO;AAAA,MACd,QAAQ,OAAO;AAAA,IACjB;AAAA,EACF;AAEA,MAAI,MAAM,UAAU;AAClB,WAAO;AAAA,MACL,UAAU,MAAM;AAAA,MAChB,KAAK;AAAA,MACL,KAAK,MAAM,OAAO,MAAM,WAAW;AAAA,MACnC,UAAU,CAAC;AAAA,MACX,aAAa,MAAM;AAAA,MACnB,SAAS,MAAM;AAAA,IACjB;AAAA,EACF;AAEA,SAAO;AACT;AAWA,eAAsB,aACpB,OACA,QAC+B;AAC/B,MAAI,CAAC,SAAS,WAAW,KAAK,KAAK,CAAC,MAAM,YAAY,CAAC,QAAQ;AAC7D,WAAO,gBAAgB,KAAK;AAAA,EAC9B;AACA,MAAI;AACF,WAAO,gBAAgB,OAAO,MAAM,OAAO,SAAS,MAAM,QAAQ,CAAC;AAAA,EACrE,SAAS,KAAK;AACZ,WAAO,gBAAgB,OAAO,MAAM,eAAe,oBAAoB;AAAA,EACzE;AACF;","names":[]}
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
import { ComponentRegistration, ThemeRegistration, ManifestComponent } from '@plenary/core';
|
|
2
|
+
import { PlenaryComponent, RegisteredComponent } from './types.js';
|
|
3
|
+
import 'react';
|
|
4
|
+
import '@plenary/client';
|
|
5
|
+
|
|
6
|
+
/**
|
|
7
|
+
* The module-singleton component registry. Because it is a shared module, both
|
|
8
|
+
* the render path (SSR + client) and the preview bridge see the same
|
|
9
|
+
* registrations — the site's registry file is imported wherever either is used.
|
|
10
|
+
*/
|
|
11
|
+
declare class Registry {
|
|
12
|
+
private components;
|
|
13
|
+
private theme;
|
|
14
|
+
constructor();
|
|
15
|
+
/** Register a component (built-in or custom) under its registration key. */
|
|
16
|
+
register(component: PlenaryComponent, registration: ComponentRegistration): this;
|
|
17
|
+
/**
|
|
18
|
+
* Declare the site's design tokens. Each token mirrors a CSS custom property
|
|
19
|
+
* the site's stylesheet defines (`--<name>`); the editor stores references
|
|
20
|
+
* (`var(--<name>)`), so the tokens must actually exist in the site's CSS for
|
|
21
|
+
* styled pages to render.
|
|
22
|
+
*/
|
|
23
|
+
registerTheme(theme: ThemeRegistration): this;
|
|
24
|
+
getTheme(): ThemeRegistration | undefined;
|
|
25
|
+
get(key: string): RegisteredComponent | undefined;
|
|
26
|
+
all(): RegisteredComponent[];
|
|
27
|
+
/** The full component manifest announced to the console over the bridge. */
|
|
28
|
+
manifest(): ManifestComponent[];
|
|
29
|
+
}
|
|
30
|
+
declare const registry: Registry;
|
|
31
|
+
/** Register a component so the dom tree may reference it by key. */
|
|
32
|
+
declare function register(component: PlenaryComponent, registration: ComponentRegistration): Registry;
|
|
33
|
+
/** Declare the site's design tokens (see Registry.registerTheme). */
|
|
34
|
+
declare function registerTheme(theme: ThemeRegistration): Registry;
|
|
35
|
+
/** Namespace mirroring the design brief's `Plenary.register(...)` surface. */
|
|
36
|
+
declare const Plenary: {
|
|
37
|
+
register: typeof register;
|
|
38
|
+
registerTheme: typeof registerTheme;
|
|
39
|
+
};
|
|
40
|
+
/** The manifest of every registered component (built-ins + custom). */
|
|
41
|
+
declare function getManifest(): ManifestComponent[];
|
|
42
|
+
/** The site's registered design tokens, if any. */
|
|
43
|
+
declare function getTheme(): ThemeRegistration | undefined;
|
|
44
|
+
|
|
45
|
+
export { Plenary, Registry, getManifest, getTheme, register, registerTheme, registry };
|