@phtngyn/cms 0.2.0-beta.5 → 0.2.0-beta.7
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/package.json +1 -1
- package/src/{Configuration-JQ1qyaU0.js → Configuration-Da5B2PVH.js} +2 -2
- package/src/{Configuration-JQ1qyaU0.js.map → Configuration-Da5B2PVH.js.map} +1 -1
- package/src/Content.js +3 -3
- package/src/Content.js.map +1 -1
- package/src/{DocumentEngine-j6Vi7nQo.js → DocumentEngine-hh_IGPXO.js} +2 -2
- package/src/{DocumentEngine-j6Vi7nQo.js.map → DocumentEngine-hh_IGPXO.js.map} +1 -1
- package/src/Module.js +1 -1
- package/src/{S3MediaObjects-BRuPQbxl.js → S3MediaObjects-Dwhl2deX.js} +4 -4
- package/src/{S3MediaObjects-BRuPQbxl.js.map → S3MediaObjects-Dwhl2deX.js.map} +1 -1
- package/src/cli.js +3 -3
- package/src/{dev-lifecycle-DdBluSiR.js → dev-lifecycle-CjDq63Ft.js} +8 -8
- package/src/dev-lifecycle-CjDq63Ft.js.map +1 -0
- package/src/{installation-BoG8E3nJ.js → installation-DYNQQBD3.js} +7 -9
- package/src/{installation-BoG8E3nJ.js.map → installation-DYNQQBD3.js.map} +1 -1
- package/src/internal/authoring-catalog.js +1 -1
- package/src/internal/authoring-metadata.js +1 -1
- package/src/internal/configuration.js +1 -1
- package/src/internal/dev-lifecycle.js +1 -1
- package/src/internal/document-model.js +2 -2
- package/src/{metadata-UzZmjwxM.js → metadata-DN9_K6Yl.js} +87 -7
- package/src/metadata-DN9_K6Yl.js.map +1 -0
- package/src/runtime/installation.js +1 -1
- package/src/runtime/plugin.js +1 -1
- package/src/runtime/preview/controller.js +3 -2
- package/src/runtime/preview/controller.js.map +1 -1
- package/src/runtime/preview/crypto.js +16 -0
- package/src/runtime/preview/crypto.js.map +1 -0
- package/src/runtime/preview/plugin.client.js +1 -1
- package/src/runtime/preview/store.js +1 -1
- package/src/runtime/studio-app.js +1 -1
- package/src/runtime/studio-app.js.map +1 -1
- package/src/runtime/studio-document.js +46 -0
- package/src/runtime/studio-document.js.map +1 -0
- package/src/runtime/studio-entry.js +5 -22
- package/src/runtime/studio-entry.js.map +1 -1
- package/src/{store-PKKB8xa2.js → store-X1e1o_MF.js} +2 -2
- package/src/{store-PKKB8xa2.js.map → store-X1e1o_MF.js.map} +1 -1
- package/studio/CreateDocumentDialog-BpjBYGfI.js +335 -0
- package/studio/{documentPlanning-Bx3W9KkD.js → SelectMenu-KiXwx4Y_.js} +15513 -11376
- package/studio/host.css +1 -1
- package/studio/host.js +10343 -14430
- package/src/dev-lifecycle-DdBluSiR.js.map +0 -1
- package/src/metadata-UzZmjwxM.js.map +0 -1
- package/studio/CreateDocumentDialog-vQ8hDs2C.js +0 -253
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { n as formAuthoring } from "../Forms-CX-hwmJF.js";
|
|
2
|
-
import { l as validateCollectionBody, n as ComponentDefinition, t as AuthoringCatalog } from "../Configuration-
|
|
2
|
+
import { l as validateCollectionBody, n as ComponentDefinition, t as AuthoringCatalog } from "../Configuration-Da5B2PVH.js";
|
|
3
3
|
import { resolveBlockAuthoring } from "./authoring-metadata.js";
|
|
4
4
|
import { Crypto, Effect, Encoding, FileSystem, Path, Schema } from "effect";
|
|
5
5
|
import { addTemplate, addVitePlugin, updateTemplates } from "@nuxt/kit";
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { a as BlockAuthoring, c as parseAuthoringContent, n as ComponentDefinition, s as createAuthoringSchema } from "../Configuration-
|
|
1
|
+
import { a as BlockAuthoring, c as parseAuthoringContent, n as ComponentDefinition, s as createAuthoringSchema } from "../Configuration-Da5B2PVH.js";
|
|
2
2
|
import { compileCmsBlock, readAuthoringDefault } from "./authoring-compiler.js";
|
|
3
3
|
import { Effect, Result, Schema } from "effect";
|
|
4
4
|
import ts from "typescript";
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { B as SeoConfiguration } from "../models-VmGmG19-.js";
|
|
2
|
-
import { M as StudioBootstrap, t as maxS3SingleCopyBytes, u as makeDefaultSeoOptions } from "../S3MediaObjects-
|
|
2
|
+
import { M as StudioBootstrap, t as maxS3SingleCopyBytes, u as makeDefaultSeoOptions } from "../S3MediaObjects-Dwhl2deX.js";
|
|
3
3
|
import { validateFormCapabilities } from "./form-capabilities.js";
|
|
4
4
|
import { compileCmsI18n } from "./i18n.js";
|
|
5
5
|
import { i as PreviewOrigin } from "../models-5j67LMqW.js";
|
|
@@ -1,3 +1,3 @@
|
|
|
1
|
-
import { a as resetCmsDevelopment, i as loadCmsProjectEnvironment, n as checkCmsConfiguration, r as doctorCmsDevelopment, t as bootstrapCmsDevelopment } from "../dev-lifecycle-
|
|
1
|
+
import { a as resetCmsDevelopment, i as loadCmsProjectEnvironment, n as checkCmsConfiguration, r as doctorCmsDevelopment, t as bootstrapCmsDevelopment } from "../dev-lifecycle-CjDq63Ft.js";
|
|
2
2
|
|
|
3
3
|
export { bootstrapCmsDevelopment, checkCmsConfiguration, doctorCmsDevelopment, loadCmsProjectEnvironment, resetCmsDevelopment };
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { FIELD_INPUT_METADATA, FIELD_OPTIONS_METADATA } from "./field-metadata.js";
|
|
2
|
-
import { r as DocumentConfiguration, u as compileStructuredFields } from "../Configuration-
|
|
3
|
-
import { t as createDocumentEngine } from "../DocumentEngine-
|
|
2
|
+
import { r as DocumentConfiguration, u as compileStructuredFields } from "../Configuration-Da5B2PVH.js";
|
|
3
|
+
import { t as createDocumentEngine } from "../DocumentEngine-hh_IGPXO.js";
|
|
4
4
|
import { Effect, Predicate, Result, Schema } from "effect";
|
|
5
5
|
|
|
6
6
|
//#region src/internal/document-model.ts
|
|
@@ -1,8 +1,92 @@
|
|
|
1
1
|
import { a as EditorNodeId } from "./scalars-CVZqT3L0.js";
|
|
2
|
-
import { Predicate, Schema } from "effect";
|
|
2
|
+
import { Crypto, Effect, Predicate, Schema } from "effect";
|
|
3
|
+
import * as Context$1 from "effect/Context";
|
|
4
|
+
import * as EffectCrypto from "effect/Crypto";
|
|
5
|
+
import * as Effect$1 from "effect/Effect";
|
|
6
|
+
import * as Layer$1 from "effect/Layer";
|
|
7
|
+
import * as PlatformError from "effect/PlatformError";
|
|
3
8
|
|
|
9
|
+
//#region ../../node_modules/.pnpm/@effect+platform-browser@4.0.0-rc.116_effect@4.0.0-rc.116/node_modules/@effect/platform-browser/dist/BrowserCrypto.js
|
|
10
|
+
/**
|
|
11
|
+
* Browser-backed implementation of Effect's Crypto service.
|
|
12
|
+
*
|
|
13
|
+
* This module provides a `Crypto.Crypto` layer backed by the Web Crypto API.
|
|
14
|
+
* The {@link WebCrypto} context reference defaults to `globalThis.crypto`, so
|
|
15
|
+
* browser programs can use the standard implementation while tests or embedded
|
|
16
|
+
* runtimes can provide their own `Crypto` object.
|
|
17
|
+
*
|
|
18
|
+
* @since 1.0.0
|
|
19
|
+
*/
|
|
20
|
+
/**
|
|
21
|
+
* Provides Browser Web Crypto APIs used by the Crypto service implementation.
|
|
22
|
+
*
|
|
23
|
+
* **When to use**
|
|
24
|
+
*
|
|
25
|
+
* Use to override the browser `Crypto` object used by the platform crypto
|
|
26
|
+
* layer.
|
|
27
|
+
*
|
|
28
|
+
* @category services
|
|
29
|
+
* @since 1.0.0
|
|
30
|
+
*/
|
|
31
|
+
const WebCrypto = /*#__PURE__*/ Context$1.Reference("@effect/platform-browser/Crypto/WebCrypto", { defaultValue: () => globalThis.crypto });
|
|
32
|
+
/**
|
|
33
|
+
* Layer that directly interfaces with the Web Crypto API.
|
|
34
|
+
*
|
|
35
|
+
* **When to use**
|
|
36
|
+
*
|
|
37
|
+
* Use to provide cryptographic randomness, UUID generation, and digest
|
|
38
|
+
* operations in browser runtimes backed by `globalThis.crypto`.
|
|
39
|
+
*
|
|
40
|
+
* **Details**
|
|
41
|
+
*
|
|
42
|
+
* Random bytes are produced with `crypto.getRandomValues`. Digests are computed
|
|
43
|
+
* with `crypto.subtle.digest` and returned as `Uint8Array` values.
|
|
44
|
+
*
|
|
45
|
+
* **Gotchas**
|
|
46
|
+
*
|
|
47
|
+
* The layer dies if the Web Crypto object is unavailable. Digest operations
|
|
48
|
+
* fail with `PlatformError` when `crypto.subtle.digest` is unavailable or the
|
|
49
|
+
* browser rejects the digest request.
|
|
50
|
+
*
|
|
51
|
+
* @category layers
|
|
52
|
+
* @since 1.0.0
|
|
53
|
+
*/
|
|
54
|
+
const layer = /*#__PURE__*/ Layer$1.effect(EffectCrypto.Crypto, /*#__PURE__*/ Effect$1.gen(function* () {
|
|
55
|
+
const crypto = yield* WebCrypto;
|
|
56
|
+
if (!crypto) return yield* Effect$1.die(/* @__PURE__ */ new Error("Web Crypto API is not available"));
|
|
57
|
+
const randomBytes = (size) => {
|
|
58
|
+
const bytes = new Uint8Array(size);
|
|
59
|
+
for (let i = 0; i < bytes.length; i += 65536) crypto.getRandomValues(bytes.subarray(i, i + 65536));
|
|
60
|
+
return bytes;
|
|
61
|
+
};
|
|
62
|
+
const digest = (algorithm, data) => {
|
|
63
|
+
if (typeof crypto.subtle?.digest !== "function") return Effect$1.fail(PlatformError.systemError({
|
|
64
|
+
module: "Crypto",
|
|
65
|
+
method: "digest",
|
|
66
|
+
_tag: "Unknown",
|
|
67
|
+
description: "crypto.subtle.digest is not available"
|
|
68
|
+
}));
|
|
69
|
+
return Effect$1.map(Effect$1.tryPromise({
|
|
70
|
+
try: () => crypto.subtle.digest(algorithm, new Uint8Array(data)),
|
|
71
|
+
catch: (cause) => PlatformError.systemError({
|
|
72
|
+
module: "Crypto",
|
|
73
|
+
method: "digest",
|
|
74
|
+
_tag: "Unknown",
|
|
75
|
+
description: "Could not compute digest",
|
|
76
|
+
cause
|
|
77
|
+
})
|
|
78
|
+
}), (buffer) => new Uint8Array(buffer));
|
|
79
|
+
};
|
|
80
|
+
return EffectCrypto.make({
|
|
81
|
+
randomBytes,
|
|
82
|
+
digest
|
|
83
|
+
});
|
|
84
|
+
}));
|
|
85
|
+
|
|
86
|
+
//#endregion
|
|
4
87
|
//#region ../document/src/internal/editor/identity.ts
|
|
5
88
|
const isEditorNodeId = Schema.is(EditorNodeId);
|
|
89
|
+
const crypto = Effect.runSync(Crypto.Crypto.pipe(Effect.provide(layer)));
|
|
6
90
|
const IDENTIFIED_EDITOR_TYPES = /* @__PURE__ */ new Set([
|
|
7
91
|
"blockquote",
|
|
8
92
|
"bulletList",
|
|
@@ -18,11 +102,7 @@ const IDENTIFIED_EDITOR_TYPES = /* @__PURE__ */ new Set([
|
|
|
18
102
|
"paragraph"
|
|
19
103
|
]);
|
|
20
104
|
function createEditorNodeId() {
|
|
21
|
-
|
|
22
|
-
bytes[6] = (bytes[6] ?? 0) & 15 | 64;
|
|
23
|
-
bytes[8] = (bytes[8] ?? 0) & 63 | 128;
|
|
24
|
-
const hex = Array.from(bytes, (byte) => byte.toString(16).padStart(2, "0")).join("");
|
|
25
|
-
return EditorNodeId.make(`${hex.slice(0, 8)}-${hex.slice(8, 12)}-${hex.slice(12, 16)}-${hex.slice(16, 20)}-${hex.slice(20)}`);
|
|
105
|
+
return EditorNodeId.make(Effect.runSync(crypto.randomUUIDv4.pipe(Effect.orDie)));
|
|
26
106
|
}
|
|
27
107
|
function editorNodeId(value) {
|
|
28
108
|
return isEditorNodeId(value) ? value : void 0;
|
|
@@ -118,4 +198,4 @@ function jsonObject(value) {
|
|
|
118
198
|
|
|
119
199
|
//#endregion
|
|
120
200
|
export { createEditorNodeId as a, withoutEditorMetadata as i, editorMetadata as n, editorNodeId as o, identifiedAttributes as r, assertCanonicalEditorContent as t };
|
|
121
|
-
//# sourceMappingURL=metadata-
|
|
201
|
+
//# sourceMappingURL=metadata-DN9_K6Yl.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"metadata-DN9_K6Yl.js","names":["Effect","EditorNodeIdSchema","BrowserCrypto.layer"],"sources":["../../../../../node_modules/.pnpm/@effect+platform-browser@4.0.0-rc.116_effect@4.0.0-rc.116/node_modules/@effect/platform-browser/dist/BrowserCrypto.js","../../../../document/src/internal/editor/identity.ts","../../../../document/src/internal/editor/metadata.ts"],"sourcesContent":["/**\n * Browser-backed implementation of Effect's Crypto service.\n *\n * This module provides a `Crypto.Crypto` layer backed by the Web Crypto API.\n * The {@link WebCrypto} context reference defaults to `globalThis.crypto`, so\n * browser programs can use the standard implementation while tests or embedded\n * runtimes can provide their own `Crypto` object.\n *\n * @since 1.0.0\n */\nimport * as Context from \"effect/Context\";\nimport * as EffectCrypto from \"effect/Crypto\";\nimport * as Effect from \"effect/Effect\";\nimport * as Layer from \"effect/Layer\";\nimport * as PlatformError from \"effect/PlatformError\";\n/**\n * Provides Browser Web Crypto APIs used by the Crypto service implementation.\n *\n * **When to use**\n *\n * Use to override the browser `Crypto` object used by the platform crypto\n * layer.\n *\n * @category services\n * @since 1.0.0\n */\nexport const WebCrypto = /*#__PURE__*/Context.Reference(\"@effect/platform-browser/Crypto/WebCrypto\", {\n defaultValue: () => globalThis.crypto\n});\n/**\n * Layer that directly interfaces with the Web Crypto API.\n *\n * **When to use**\n *\n * Use to provide cryptographic randomness, UUID generation, and digest\n * operations in browser runtimes backed by `globalThis.crypto`.\n *\n * **Details**\n *\n * Random bytes are produced with `crypto.getRandomValues`. Digests are computed\n * with `crypto.subtle.digest` and returned as `Uint8Array` values.\n *\n * **Gotchas**\n *\n * The layer dies if the Web Crypto object is unavailable. Digest operations\n * fail with `PlatformError` when `crypto.subtle.digest` is unavailable or the\n * browser rejects the digest request.\n *\n * @category layers\n * @since 1.0.0\n */\nexport const layer = /*#__PURE__*/Layer.effect(EffectCrypto.Crypto, /*#__PURE__*/Effect.gen(function* () {\n const crypto = yield* WebCrypto;\n if (!crypto) {\n return yield* Effect.die(new Error(\"Web Crypto API is not available\"));\n }\n const randomBytes = size => {\n const bytes = new Uint8Array(size);\n for (let i = 0; i < bytes.length; i += 65_536) {\n crypto.getRandomValues(bytes.subarray(i, i + 65_536));\n }\n return bytes;\n };\n const digest = (algorithm, data) => {\n if (typeof crypto.subtle?.digest !== \"function\") {\n return Effect.fail(PlatformError.systemError({\n module: \"Crypto\",\n method: \"digest\",\n _tag: \"Unknown\",\n description: \"crypto.subtle.digest is not available\"\n }));\n }\n return Effect.map(Effect.tryPromise({\n try: () => crypto.subtle.digest(algorithm, new Uint8Array(data)),\n catch: cause => PlatformError.systemError({\n module: \"Crypto\",\n method: \"digest\",\n _tag: \"Unknown\",\n description: \"Could not compute digest\",\n cause\n })\n }), buffer => new Uint8Array(buffer));\n };\n return EffectCrypto.make({\n randomBytes,\n digest\n });\n}));\n//# sourceMappingURL=BrowserCrypto.js.map","import type { EditorNodeId } from '@internal/protocol/Documents'\nimport { BrowserCrypto } from '@effect/platform-browser'\nimport { EditorNodeId as EditorNodeIdSchema } from '@internal/protocol/Documents'\nimport { Crypto, Effect, Schema } from 'effect'\n\nconst isEditorNodeId = Schema.is(EditorNodeIdSchema)\n\nconst crypto = Effect.runSync(Crypto.Crypto.pipe(Effect.provide(BrowserCrypto.layer)))\n\nexport const IDENTIFIED_EDITOR_TYPES = new Set([\n 'blockquote',\n 'bulletList',\n 'cmsBlock',\n 'cmsOpaque',\n 'cmsSlot',\n 'codeBlock',\n 'heading',\n 'horizontalRule',\n 'image',\n 'listItem',\n 'orderedList',\n 'paragraph',\n])\n\nexport function createEditorNodeId(): EditorNodeId {\n return EditorNodeIdSchema.make(Effect.runSync(crypto.randomUUIDv4.pipe(Effect.orDie)))\n}\n\nexport function editorNodeId(value: Schema.Json | undefined): EditorNodeId | undefined {\n return isEditorNodeId(value) ? value : undefined\n}\n\nexport function isIdentifiedEditorType(type: string | undefined): boolean {\n return type !== undefined && IDENTIFIED_EDITOR_TYPES.has(type)\n}\n","import type { CmsMarkdownDocument, MarkdownNode } from '@internal/protocol/Documents'\nimport type { EditorNodeId } from '@internal/protocol/Documents'\nimport type { JSONContent } from '@tiptap/core'\nimport { Predicate, Schema } from 'effect'\nimport { editorNodeId, isIdentifiedEditorType } from './identity'\n\nconst isJsonObject = Schema.is(Schema.JsonObject)\n\ninterface EditorMetadata {\n readonly implicitSlotId?: EditorNodeId\n readonly nodeId: EditorNodeId\n}\n\nexport function assertCanonicalEditorContent(content: JSONContent): void {\n const seen = new Set<EditorNodeId>()\n\n const visit = (node: JSONContent, path: ReadonlyArray<number>) => {\n if (isIdentifiedEditorNode(node)) {\n const id = editorNodeId(node.attrs?.cmsNodeId)\n\n if (id === undefined) {\n throw new Error(`Authorable ${node.type} at ${diagnosticPath(path)} has no valid node identity.`)\n }\n\n if (seen.has(id)) {\n throw new Error(`Authorable ${node.type} at ${diagnosticPath(path)} duplicates node identity \"${id}\".`)\n }\n\n seen.add(id)\n }\n\n node.content?.forEach((child, index) => visit(child, [...path, index]))\n }\n\n visit(content, [])\n}\n\nexport function identifiedAttributes(\n attributes: Schema.JsonObject,\n nodeIdValue: Schema.Json | undefined,\n implicitSlotIdValue?: Schema.Json,\n): Schema.JsonObject {\n const nodeId = editorNodeId(nodeIdValue)\n const implicitSlotId = implicitSlotIdValue === undefined ? undefined : editorNodeId(implicitSlotIdValue)\n\n if (nodeId === undefined) throw new Error('Cannot project an authorable node without a valid identity.')\n\n if (implicitSlotIdValue !== undefined && implicitSlotId === undefined)\n throw new Error('Cannot project an implicit slot without a valid identity.')\n\n const internal: Record<string, Schema.Json> = structuredClone(jsonObject(attributes.$))\n\n if (implicitSlotId === undefined) internal.editor = { nodeId }\n else internal.editor = { implicitSlotId, nodeId }\n const result: Record<string, Schema.Json> = structuredClone(attributes)\n result.$ = internal\n\n return result\n}\n\nexport function editorMetadata(attributes: Schema.JsonObject): EditorMetadata | undefined {\n const metadata = jsonObject(jsonObject(attributes.$).editor)\n const nodeId = editorNodeId(metadata.nodeId)\n const implicitSlotId = metadata.implicitSlotId === undefined ? undefined : editorNodeId(metadata.implicitSlotId)\n\n if (nodeId === undefined) return undefined\n\n if (metadata.implicitSlotId !== undefined && implicitSlotId === undefined) return undefined\n\n return implicitSlotId === undefined ? { nodeId } : { implicitSlotId, nodeId }\n}\n\nexport function withoutEditorMetadata(body: CmsMarkdownDocument): CmsMarkdownDocument {\n return {\n frontmatter: structuredClone(body.frontmatter),\n meta: structuredClone(body.meta),\n nodes: body.nodes.map(cleanNode),\n }\n}\n\nfunction cleanNode(node: MarkdownNode): MarkdownNode {\n if (Predicate.isString(node)) return node\n\n if (node[0] === null) {\n const cleanAttributes = cleanNodeAttributes(node[1])\n\n return [null, cleanAttributes, node[2]]\n }\n\n const [tag, attributes, ...children] = node\n\n return [tag, cleanNodeAttributes(attributes), ...children.map(cleanNode)]\n}\n\nfunction cleanNodeAttributes(attributes: Schema.JsonObject): Record<string, Schema.Json> {\n const cleanAttributes: Record<string, Schema.Json> = structuredClone(attributes)\n const internal = jsonObject(cleanAttributes.$)\n\n if (internal.editor !== undefined) {\n const { editor: _editor, ...remaining } = internal\n\n if (Object.keys(remaining).length) cleanAttributes.$ = remaining\n else delete cleanAttributes.$\n }\n\n return cleanAttributes\n}\n\nfunction isIdentifiedEditorNode(node: JSONContent): boolean {\n if (!isIdentifiedEditorType(node.type)) return false\n\n if (node.attrs?.cmsSynthetic === true || node.attrs?.cmsTransient === true) return false\n\n return node.type !== 'paragraph' || Boolean(node.content?.length)\n}\n\nfunction diagnosticPath(path: ReadonlyArray<number>): string {\n return path.length ? path.join('.') : 'document root'\n}\n\nfunction jsonObject(value: Schema.Json | undefined): Schema.JsonObject {\n return isJsonObject(value) ? value : {}\n}\n"],"x_google_ignoreList":[0],"mappings":"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"}
|
|
@@ -1,3 +1,3 @@
|
|
|
1
|
-
import { n as scopedDatabaseUrl, r as toS3MediaObjectStoreOptions, t as installCms } from "../installation-
|
|
1
|
+
import { n as scopedDatabaseUrl, r as toS3MediaObjectStoreOptions, t as installCms } from "../installation-DYNQQBD3.js";
|
|
2
2
|
|
|
3
3
|
export { installCms, scopedDatabaseUrl, toS3MediaObjectStoreOptions };
|
package/src/runtime/plugin.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { resolveCmsInstallation } from "../internal/configuration.js";
|
|
2
|
-
import { t as installCms } from "../installation-
|
|
2
|
+
import { t as installCms } from "../installation-DYNQQBD3.js";
|
|
3
3
|
import { diagnosticFromCause, renderDiagnostic } from "../internal/diagnostics.js";
|
|
4
4
|
import { Effect } from "effect";
|
|
5
5
|
import { defineNitroPlugin, useNitroApp, useRuntimeConfig } from "nitropack/runtime";
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import { a as EditorNodeId, c as RevisionNumber, r as DocumentId } from "../../scalars-CVZqT3L0.js";
|
|
2
2
|
import { st as RequestId } from "../../models-VmGmG19-.js";
|
|
3
3
|
import { r as PreviewIntentId } from "../../models-5j67LMqW.js";
|
|
4
|
+
import { randomUUIDv4 } from "./crypto.js";
|
|
4
5
|
import { mountPreviewOverlay } from "./overlay.js";
|
|
5
6
|
import { mountPreviewRegions } from "./regions.js";
|
|
6
7
|
import { Schema } from "effect";
|
|
@@ -170,7 +171,7 @@ function mountPreviewController(options) {
|
|
|
170
171
|
const nodeId = Schema.is(EditorNodeId)(nodeIdValue) ? nodeIdValue : void 0;
|
|
171
172
|
const activationFocus = {
|
|
172
173
|
documentId: documentIdValue,
|
|
173
|
-
id: PreviewIntentId.make(
|
|
174
|
+
id: PreviewIntentId.make(randomUUIDv4(view.crypto)),
|
|
174
175
|
origin: "preview",
|
|
175
176
|
reveal: false,
|
|
176
177
|
revision
|
|
@@ -182,7 +183,7 @@ function mountPreviewController(options) {
|
|
|
182
183
|
lastApplied = "";
|
|
183
184
|
const activation = {
|
|
184
185
|
documentId: desiredFocus.documentId,
|
|
185
|
-
requestId: RequestId.make(
|
|
186
|
+
requestId: RequestId.make(randomUUIDv4(view.crypto)),
|
|
186
187
|
revision,
|
|
187
188
|
type: "preview:activate"
|
|
188
189
|
};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"controller.js","names":[],"sources":["../../../../../src/runtime/preview/controller.ts"],"sourcesContent":["import type { DocumentPreviewFocusIntent, PreviewSiteBridge, StudioPreviewPayload } from '@internal/protocol/Preview'\nimport type { StudioPreviewStore } from './store'\nimport { DocumentId, EditorNodeId, RevisionNumber } from '@internal/protocol/Documents'\nimport { RequestId } from '@internal/protocol/Identity'\nimport { PreviewIntentId } from '@internal/protocol/Preview'\nimport { Schema } from 'effect'\nimport { mountPreviewOverlay } from './overlay'\nimport { mountPreviewRegions } from './regions'\n\nexport function mountPreviewController(options: {\n readonly bridge: PreviewSiteBridge\n readonly navigate: (path: string) => Promise<void> | void\n readonly onPatchError: (message: string | null) => void\n readonly root: Document\n readonly store: StudioPreviewStore\n readonly view: Window\n}): () => void {\n type PreviewFallbacks = Extract<StudioPreviewPayload, { readonly type: 'studio:patch' }>['fallbacks']\n\n const { bridge, root, store, view } = options\n const selection = mountPreviewOverlay(root, view)\n const hover = mountPreviewOverlay(root, view, 'hover')\n const regions = mountPreviewRegions(root, view)\n let active = false\n let desiredFocus: DocumentPreviewFocusIntent | undefined\n let fallbacks: PreviewFallbacks = {}\n let mode: 'browse' | 'edit' = 'edit'\n let renderSequence = 0\n let revision = RevisionNumber.make(0)\n let lastApplied = ''\n let revealedIntentId = ''\n\n const sendManifest = (): void => {\n bridge.send({ manifest: store.manifest(), revision, type: 'preview:manifest' })\n }\n\n const stopManifest = store.subscribe(sendManifest)\n\n const sendApplied = (result: 'exact' | 'fallback' | 'missing'): void => {\n if (!desiredFocus) return\n const signature = `${desiredFocus.id}:${result}`\n\n if (signature === lastApplied) return\n lastApplied = signature\n\n const applied = {\n intentId: desiredFocus.id,\n result,\n revision,\n type: 'preview:applied',\n } as const\n\n bridge.send(desiredFocus.nodeId ? { ...applied, nodeId: desiredFocus.nodeId } : applied)\n }\n\n const documentRoot = (documentId: string): ParentNode =>\n [...root.querySelectorAll('[data-cms-document]')].find(\n (element) => element.getAttribute('data-cms-document') === documentId,\n ) ?? root\n\n const applyFocus = (reveal = false): void => {\n if (!active && mode === 'edit') {\n selection.setPending(true)\n\n return\n }\n\n selection.setPending(false)\n\n if (mode !== 'edit') {\n selection.show([])\n\n return\n }\n\n const intent = desiredFocus\n const nodeId = intent?.nodeId\n\n if (!intent || !nodeId) {\n selection.show([])\n sendApplied('exact')\n\n return\n }\n\n const scope = documentRoot(intent.documentId)\n const target = regions.locate(nodeId, fallbacks, scope)\n const result = !target.nodeId ? 'missing' : target.nodeId === nodeId ? 'exact' : 'fallback'\n\n selection.show(target.geometries, {\n label: intent.label,\n match: result === 'missing' ? undefined : result,\n reveal,\n })\n\n if (reveal && result !== 'missing' && revealedIntentId !== intent.id) {\n revealedIntentId = intent.id\n revealElement(regions.nearest(target.geometries), view)\n }\n\n sendApplied(result)\n }\n\n const hoverElements = (target?: Element, x?: number, y?: number): void => {\n if (!active || mode !== 'edit' || !target || x === undefined || y === undefined) {\n hover.show([])\n\n return\n }\n\n const scope = target.closest('[data-cms-document]') ?? root\n const nodeId = regions.hitTest(x, y, scope)\n\n if (!nodeId) {\n hover.show([])\n\n return\n }\n\n hover.show(regions.locate(nodeId, fallbacks, scope).geometries)\n }\n\n const settleRender = (sequence: number): void => {\n view.requestAnimationFrame(() =>\n view.requestAnimationFrame(() => {\n if (sequence !== renderSequence) return\n active = true\n regions.decorate()\n bridge.send({ revision, type: 'preview:rendered' })\n applyFocus(desiredFocus?.reveal)\n }),\n )\n }\n\n const stopBridge = bridge.subscribe((message) => {\n if (message.type === 'studio:connect') {\n active = true\n regions.clear()\n regions.decorate()\n sendManifest()\n\n return\n }\n\n if (message.type === 'studio:mode') {\n mode = message.mode\n\n if (mode === 'browse') {\n hoverElements()\n selection.setPending(false)\n selection.show([])\n regions.clear()\n } else {\n regions.decorate()\n applyFocus()\n }\n\n return\n }\n\n if (message.type === 'studio:navigate') {\n void options.navigate(message.path)\n\n return\n }\n\n if (message.type === 'studio:focus') {\n if (message.focus.revision !== revision) return\n desiredFocus = message.focus\n applyFocus(desiredFocus.reveal)\n\n return\n }\n\n if (message.type !== 'studio:patch' || message.revision < revision) return\n revision = message.revision\n active = false\n selection.setPending(true)\n desiredFocus = message.focus\n lastApplied = ''\n const sequence = ++renderSequence\n void store.patch(message.document).then(\n (localFallbacks) => {\n if (sequence !== renderSequence) return\n options.onPatchError(null)\n fallbacks = Object.assign({}, message.fallbacks, localFallbacks)\n settleRender(sequence)\n },\n () => {\n if (sequence !== renderSequence) return\n options.onPatchError('Preview could not apply this update.')\n },\n )\n })\n\n const handleClick = (event: MouseEvent) => {\n if (!active) return\n const target = event.target instanceof Element ? event.target : null\n\n if (mode === 'browse') {\n const link = target?.closest('a[href]')\n\n if (\n !(link instanceof HTMLAnchorElement) ||\n link.target ||\n link.hasAttribute('download') ||\n event.metaKey ||\n event.ctrlKey ||\n event.shiftKey ||\n event.altKey\n )\n return\n const destination = new URL(link.href, view.location.href)\n\n if (destination.origin !== view.location.origin) return\n event.preventDefault()\n event.stopPropagation()\n void options.navigate(`${destination.pathname}${destination.search}${destination.hash}`)\n\n return\n }\n\n const scope = target?.closest('[data-cms-document]')\n const documentIdValue = scope?.getAttribute('data-cms-document')\n\n if (!target || !scope || !Schema.is(DocumentId)(documentIdValue)) return\n event.preventDefault()\n event.stopPropagation()\n const nodeIdValue = regions.hitTest(event.clientX, event.clientY, scope)\n const nodeId = Schema.is(EditorNodeId)(nodeIdValue) ? nodeIdValue : undefined\n\n const activationFocus = {\n documentId: documentIdValue,\n // oxlint-disable-next-line effecttsgo/crypto-random-uuid -- Browser interactions use the native Web Crypto host API.\n id: PreviewIntentId.make(globalThis.crypto.randomUUID()),\n origin: 'preview',\n reveal: false,\n revision,\n } as const\n\n desiredFocus = nodeId ? { ...activationFocus, nodeId } : activationFocus\n lastApplied = ''\n\n const activation = {\n documentId: desiredFocus.documentId,\n // oxlint-disable-next-line effecttsgo/crypto-random-uuid -- Browser interactions use the native Web Crypto host API.\n requestId: RequestId.make(globalThis.crypto.randomUUID()),\n revision,\n type: 'preview:activate',\n } as const\n\n if (nodeId) bridge.send({ ...activation, nodeId })\n else bridge.send(activation)\n applyFocus()\n }\n\n let hoverFrame = 0\n let hoverPointer: { readonly target: Element; readonly x: number; readonly y: number } | undefined\n\n const handlePointerMove = (event: PointerEvent) => {\n if (!(event.target instanceof Element)) return\n hoverPointer = { target: event.target, x: event.clientX, y: event.clientY }\n\n if (hoverFrame) return\n hoverFrame = view.requestAnimationFrame(() => {\n hoverFrame = 0\n const pointer = hoverPointer\n\n if (pointer) hoverElements(pointer.target, pointer.x, pointer.y)\n })\n }\n\n const handlePointerOut = (event: PointerEvent) => {\n if (!(event.relatedTarget instanceof Element)) {\n hoverPointer = undefined\n hoverElements()\n }\n }\n\n let mutationQueued = false\n\n const observer = new MutationObserver((records) => {\n if (\n records.every((record) => record.target instanceof Element && record.target.closest('[data-cms-preview-overlay]'))\n )\n return\n\n if (mutationQueued) return\n mutationQueued = true\n queueMicrotask(() => {\n mutationQueued = false\n\n if (!active) return\n hoverElements()\n regions.decorate()\n\n if (desiredFocus) applyFocus(false)\n })\n })\n\n root.addEventListener('click', handleClick, true)\n root.addEventListener('pointermove', handlePointerMove, true)\n root.addEventListener('pointerout', handlePointerOut, true)\n observer.observe(root.documentElement, { childList: true, subtree: true })\n\n return () => {\n stopBridge()\n stopManifest()\n observer.disconnect()\n\n if (hoverFrame) view.cancelAnimationFrame(hoverFrame)\n selection.destroy()\n hover.destroy()\n root.removeEventListener('click', handleClick, true)\n root.removeEventListener('pointermove', handlePointerMove, true)\n root.removeEventListener('pointerout', handlePointerOut, true)\n regions.clear()\n }\n}\n\nfunction revealElement(element: Element | undefined, view: Window): void {\n if (!element) return\n const rect = element.getBoundingClientRect()\n\n if (rect.bottom > 0 && rect.top < view.innerHeight && rect.right > 0 && rect.left < view.innerWidth) return\n element.scrollIntoView({\n behavior: 'instant',\n block: 'center',\n inline: 'nearest',\n })\n}\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"controller.js","names":[],"sources":["../../../../../src/runtime/preview/controller.ts"],"sourcesContent":["import type { DocumentPreviewFocusIntent, PreviewSiteBridge, StudioPreviewPayload } from '@internal/protocol/Preview'\nimport type { StudioPreviewStore } from './store'\nimport { DocumentId, EditorNodeId, RevisionNumber } from '@internal/protocol/Documents'\nimport { RequestId } from '@internal/protocol/Identity'\nimport { PreviewIntentId } from '@internal/protocol/Preview'\nimport { Schema } from 'effect'\nimport { randomUUIDv4 } from './crypto'\nimport { mountPreviewOverlay } from './overlay'\nimport { mountPreviewRegions } from './regions'\n\nexport function mountPreviewController(options: {\n readonly bridge: PreviewSiteBridge\n readonly navigate: (path: string) => Promise<void> | void\n readonly onPatchError: (message: string | null) => void\n readonly root: Document\n readonly store: StudioPreviewStore\n readonly view: Window\n}): () => void {\n type PreviewFallbacks = Extract<StudioPreviewPayload, { readonly type: 'studio:patch' }>['fallbacks']\n\n const { bridge, root, store, view } = options\n const selection = mountPreviewOverlay(root, view)\n const hover = mountPreviewOverlay(root, view, 'hover')\n const regions = mountPreviewRegions(root, view)\n let active = false\n let desiredFocus: DocumentPreviewFocusIntent | undefined\n let fallbacks: PreviewFallbacks = {}\n let mode: 'browse' | 'edit' = 'edit'\n let renderSequence = 0\n let revision = RevisionNumber.make(0)\n let lastApplied = ''\n let revealedIntentId = ''\n\n const sendManifest = (): void => {\n bridge.send({ manifest: store.manifest(), revision, type: 'preview:manifest' })\n }\n\n const stopManifest = store.subscribe(sendManifest)\n\n const sendApplied = (result: 'exact' | 'fallback' | 'missing'): void => {\n if (!desiredFocus) return\n const signature = `${desiredFocus.id}:${result}`\n\n if (signature === lastApplied) return\n lastApplied = signature\n\n const applied = {\n intentId: desiredFocus.id,\n result,\n revision,\n type: 'preview:applied',\n } as const\n\n bridge.send(desiredFocus.nodeId ? { ...applied, nodeId: desiredFocus.nodeId } : applied)\n }\n\n const documentRoot = (documentId: string): ParentNode =>\n [...root.querySelectorAll('[data-cms-document]')].find(\n (element) => element.getAttribute('data-cms-document') === documentId,\n ) ?? root\n\n const applyFocus = (reveal = false): void => {\n if (!active && mode === 'edit') {\n selection.setPending(true)\n\n return\n }\n\n selection.setPending(false)\n\n if (mode !== 'edit') {\n selection.show([])\n\n return\n }\n\n const intent = desiredFocus\n const nodeId = intent?.nodeId\n\n if (!intent || !nodeId) {\n selection.show([])\n sendApplied('exact')\n\n return\n }\n\n const scope = documentRoot(intent.documentId)\n const target = regions.locate(nodeId, fallbacks, scope)\n const result = !target.nodeId ? 'missing' : target.nodeId === nodeId ? 'exact' : 'fallback'\n\n selection.show(target.geometries, {\n label: intent.label,\n match: result === 'missing' ? undefined : result,\n reveal,\n })\n\n if (reveal && result !== 'missing' && revealedIntentId !== intent.id) {\n revealedIntentId = intent.id\n revealElement(regions.nearest(target.geometries), view)\n }\n\n sendApplied(result)\n }\n\n const hoverElements = (target?: Element, x?: number, y?: number): void => {\n if (!active || mode !== 'edit' || !target || x === undefined || y === undefined) {\n hover.show([])\n\n return\n }\n\n const scope = target.closest('[data-cms-document]') ?? root\n const nodeId = regions.hitTest(x, y, scope)\n\n if (!nodeId) {\n hover.show([])\n\n return\n }\n\n hover.show(regions.locate(nodeId, fallbacks, scope).geometries)\n }\n\n const settleRender = (sequence: number): void => {\n view.requestAnimationFrame(() =>\n view.requestAnimationFrame(() => {\n if (sequence !== renderSequence) return\n active = true\n regions.decorate()\n bridge.send({ revision, type: 'preview:rendered' })\n applyFocus(desiredFocus?.reveal)\n }),\n )\n }\n\n const stopBridge = bridge.subscribe((message) => {\n if (message.type === 'studio:connect') {\n active = true\n regions.clear()\n regions.decorate()\n sendManifest()\n\n return\n }\n\n if (message.type === 'studio:mode') {\n mode = message.mode\n\n if (mode === 'browse') {\n hoverElements()\n selection.setPending(false)\n selection.show([])\n regions.clear()\n } else {\n regions.decorate()\n applyFocus()\n }\n\n return\n }\n\n if (message.type === 'studio:navigate') {\n void options.navigate(message.path)\n\n return\n }\n\n if (message.type === 'studio:focus') {\n if (message.focus.revision !== revision) return\n desiredFocus = message.focus\n applyFocus(desiredFocus.reveal)\n\n return\n }\n\n if (message.type !== 'studio:patch' || message.revision < revision) return\n revision = message.revision\n active = false\n selection.setPending(true)\n desiredFocus = message.focus\n lastApplied = ''\n const sequence = ++renderSequence\n void store.patch(message.document).then(\n (localFallbacks) => {\n if (sequence !== renderSequence) return\n options.onPatchError(null)\n fallbacks = Object.assign({}, message.fallbacks, localFallbacks)\n settleRender(sequence)\n },\n () => {\n if (sequence !== renderSequence) return\n options.onPatchError('Preview could not apply this update.')\n },\n )\n })\n\n const handleClick = (event: MouseEvent) => {\n if (!active) return\n const target = event.target instanceof Element ? event.target : null\n\n if (mode === 'browse') {\n const link = target?.closest('a[href]')\n\n if (\n !(link instanceof HTMLAnchorElement) ||\n link.target ||\n link.hasAttribute('download') ||\n event.metaKey ||\n event.ctrlKey ||\n event.shiftKey ||\n event.altKey\n )\n return\n const destination = new URL(link.href, view.location.href)\n\n if (destination.origin !== view.location.origin) return\n event.preventDefault()\n event.stopPropagation()\n void options.navigate(`${destination.pathname}${destination.search}${destination.hash}`)\n\n return\n }\n\n const scope = target?.closest('[data-cms-document]')\n const documentIdValue = scope?.getAttribute('data-cms-document')\n\n if (!target || !scope || !Schema.is(DocumentId)(documentIdValue)) return\n event.preventDefault()\n event.stopPropagation()\n const nodeIdValue = regions.hitTest(event.clientX, event.clientY, scope)\n const nodeId = Schema.is(EditorNodeId)(nodeIdValue) ? nodeIdValue : undefined\n\n const activationFocus = {\n documentId: documentIdValue,\n id: PreviewIntentId.make(randomUUIDv4(view.crypto)),\n origin: 'preview',\n reveal: false,\n revision,\n } as const\n\n desiredFocus = nodeId ? { ...activationFocus, nodeId } : activationFocus\n lastApplied = ''\n\n const activation = {\n documentId: desiredFocus.documentId,\n requestId: RequestId.make(randomUUIDv4(view.crypto)),\n revision,\n type: 'preview:activate',\n } as const\n\n if (nodeId) bridge.send({ ...activation, nodeId })\n else bridge.send(activation)\n applyFocus()\n }\n\n let hoverFrame = 0\n let hoverPointer: { readonly target: Element; readonly x: number; readonly y: number } | undefined\n\n const handlePointerMove = (event: PointerEvent) => {\n if (!(event.target instanceof Element)) return\n hoverPointer = { target: event.target, x: event.clientX, y: event.clientY }\n\n if (hoverFrame) return\n hoverFrame = view.requestAnimationFrame(() => {\n hoverFrame = 0\n const pointer = hoverPointer\n\n if (pointer) hoverElements(pointer.target, pointer.x, pointer.y)\n })\n }\n\n const handlePointerOut = (event: PointerEvent) => {\n if (!(event.relatedTarget instanceof Element)) {\n hoverPointer = undefined\n hoverElements()\n }\n }\n\n let mutationQueued = false\n\n const observer = new MutationObserver((records) => {\n if (\n records.every((record) => record.target instanceof Element && record.target.closest('[data-cms-preview-overlay]'))\n )\n return\n\n if (mutationQueued) return\n mutationQueued = true\n queueMicrotask(() => {\n mutationQueued = false\n\n if (!active) return\n hoverElements()\n regions.decorate()\n\n if (desiredFocus) applyFocus(false)\n })\n })\n\n root.addEventListener('click', handleClick, true)\n root.addEventListener('pointermove', handlePointerMove, true)\n root.addEventListener('pointerout', handlePointerOut, true)\n observer.observe(root.documentElement, { childList: true, subtree: true })\n\n return () => {\n stopBridge()\n stopManifest()\n observer.disconnect()\n\n if (hoverFrame) view.cancelAnimationFrame(hoverFrame)\n selection.destroy()\n hover.destroy()\n root.removeEventListener('click', handleClick, true)\n root.removeEventListener('pointermove', handlePointerMove, true)\n root.removeEventListener('pointerout', handlePointerOut, true)\n regions.clear()\n }\n}\n\nfunction revealElement(element: Element | undefined, view: Window): void {\n if (!element) return\n const rect = element.getBoundingClientRect()\n\n if (rect.bottom > 0 && rect.top < view.innerHeight && rect.right > 0 && rect.left < view.innerWidth) return\n element.scrollIntoView({\n behavior: 'instant',\n block: 'center',\n inline: 'nearest',\n })\n}\n"],"mappings":"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"}
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import { Crypto, Effect } from "effect";
|
|
2
|
+
|
|
3
|
+
//#region src/runtime/preview/crypto.ts
|
|
4
|
+
function browserCrypto(host) {
|
|
5
|
+
return Crypto.make({
|
|
6
|
+
digest: (algorithm, data) => Effect.promise(() => host.subtle.digest(algorithm, new Uint8Array(data)).then((digest) => new Uint8Array(digest))),
|
|
7
|
+
randomBytes: (size) => host.getRandomValues(new Uint8Array(size))
|
|
8
|
+
});
|
|
9
|
+
}
|
|
10
|
+
function randomUUIDv4(host) {
|
|
11
|
+
return Effect.runSync(browserCrypto(host).randomUUIDv4.pipe(Effect.orDie));
|
|
12
|
+
}
|
|
13
|
+
|
|
14
|
+
//#endregion
|
|
15
|
+
export { randomUUIDv4 };
|
|
16
|
+
//# sourceMappingURL=crypto.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"crypto.js","names":["EffectCrypto"],"sources":["../../../../../src/runtime/preview/crypto.ts"],"sourcesContent":["import { Crypto as EffectCrypto, Effect } from 'effect'\n\nfunction browserCrypto(host: Crypto): EffectCrypto.Crypto {\n return EffectCrypto.make({\n digest: (algorithm, data) =>\n Effect.promise(() =>\n host.subtle.digest(algorithm, new Uint8Array(data)).then((digest) => new Uint8Array(digest)),\n ),\n randomBytes: (size) => host.getRandomValues(new Uint8Array(size)),\n })\n}\n\nexport function randomUUIDv4(host: Crypto): string {\n return Effect.runSync(browserCrypto(host).randomUUIDv4.pipe(Effect.orDie))\n}\n"],"mappings":";;;AAEA,SAAS,cAAc,MAAmC;CACxD,OAAOA,OAAa,KAAK;EACvB,SAAS,WAAW,SAClB,OAAO,cACL,KAAK,OAAO,OAAO,WAAW,IAAI,WAAW,IAAI,CAAC,CAAC,CAAC,MAAM,WAAW,IAAI,WAAW,MAAM,CAAC,CAC7F;EACF,cAAc,SAAS,KAAK,gBAAgB,IAAI,WAAW,IAAI,CAAC;CAClE,CAAC;AACH;AAEA,SAAgB,aAAa,MAAsB;CACjD,OAAO,OAAO,QAAQ,cAAc,IAAI,CAAC,CAAC,aAAa,KAAK,OAAO,KAAK,CAAC;AAC3E"}
|
|
@@ -4,7 +4,7 @@ import { n as readPreviewLocation, r as withPreviewLocation } from "../../locati
|
|
|
4
4
|
import { formComponentsKey } from "../delivery/blocks.js";
|
|
5
5
|
import { documentPreviewStoreKey } from "../delivery/preview.js";
|
|
6
6
|
import { mountPreviewController } from "./controller.js";
|
|
7
|
-
import { t as createStudioPreviewStore } from "../../store-
|
|
7
|
+
import { t as createStudioPreviewStore } from "../../store-X1e1o_MF.js";
|
|
8
8
|
import { Result, Schema } from "effect";
|
|
9
9
|
import { inject, watch } from "vue";
|
|
10
10
|
import { defineNuxtPlugin, navigateTo, onNuxtReady, useNuxtApp, useState } from "nuxt/app";
|
|
@@ -1,4 +1,4 @@
|
|
|
1
1
|
import { documentPreviewStoreKey } from "../delivery/preview.js";
|
|
2
|
-
import { t as createStudioPreviewStore } from "../../store-
|
|
2
|
+
import { t as createStudioPreviewStore } from "../../store-X1e1o_MF.js";
|
|
3
3
|
|
|
4
4
|
export { createStudioPreviewStore, documentPreviewStoreKey };
|
|
@@ -4,7 +4,7 @@ import { defineEventHandler, setResponseHeader } from "h3";
|
|
|
4
4
|
function createStudioAppHandler(entryUrl, hmrUrl) {
|
|
5
5
|
const escape = (value) => value.replaceAll("&", "&").replaceAll("\"", """).replaceAll("<", "<");
|
|
6
6
|
const script = (url) => `<script type="module" src="${escape(url)}"><\/script>`;
|
|
7
|
-
const shell = `<!doctype html><html lang="en"><head><meta charset="utf-8"><meta name="viewport" content="width=device-width, initial-scale=1"><title>CMS Studio</title></head><body
|
|
7
|
+
const shell = `<!doctype html><html lang="en"><head><meta charset="utf-8"><meta name="viewport" content="width=device-width, initial-scale=1"><title>CMS Studio</title></head><body>${hmrUrl ? script(hmrUrl) : ""}${script(entryUrl)}</body></html>`;
|
|
8
8
|
return defineEventHandler((event) => {
|
|
9
9
|
setResponseHeader(event, "content-type", "text/html; charset=utf-8");
|
|
10
10
|
setResponseHeader(event, "cache-control", "no-store");
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"studio-app.js","names":[],"sources":["../../../../src/runtime/studio-app.ts"],"sourcesContent":["import { defineEventHandler, setResponseHeader } from 'h3'\n\nexport function createStudioAppHandler(entryUrl: string, hmrUrl?: string) {\n const escape = (value: string) => value.replaceAll('&', '&').replaceAll('\"', '"').replaceAll('<', '<')\n const script = (url: string) => `<script type=\"module\" src=\"${escape(url)}\"></script>`\n const shell = `<!doctype html><html lang=\"en\"><head><meta charset=\"utf-8\"><meta name=\"viewport\" content=\"width=device-width, initial-scale=1\"><title>CMS Studio</title></head><body
|
|
1
|
+
{"version":3,"file":"studio-app.js","names":[],"sources":["../../../../src/runtime/studio-app.ts"],"sourcesContent":["import { defineEventHandler, setResponseHeader } from 'h3'\n\nexport function createStudioAppHandler(entryUrl: string, hmrUrl?: string) {\n const escape = (value: string) => value.replaceAll('&', '&').replaceAll('\"', '"').replaceAll('<', '<')\n const script = (url: string) => `<script type=\"module\" src=\"${escape(url)}\"></script>`\n const shell = `<!doctype html><html lang=\"en\"><head><meta charset=\"utf-8\"><meta name=\"viewport\" content=\"width=device-width, initial-scale=1\"><title>CMS Studio</title></head><body>${hmrUrl ? script(hmrUrl) : ''}${script(entryUrl)}</body></html>`\n\n return defineEventHandler((event) => {\n setResponseHeader(event, 'content-type', 'text/html; charset=utf-8')\n setResponseHeader(event, 'cache-control', 'no-store')\n\n return shell\n })\n}\n"],"mappings":";;;AAEA,SAAgB,uBAAuB,UAAkB,QAAiB;CACxE,MAAM,UAAU,UAAkB,MAAM,WAAW,KAAK,OAAO,CAAC,CAAC,WAAW,MAAK,QAAQ,CAAC,CAAC,WAAW,KAAK,MAAM;CACjH,MAAM,UAAU,QAAgB,8BAA8B,OAAO,GAAG,EAAE;CAC1E,MAAM,QAAQ,wKAAwK,SAAS,OAAO,MAAM,IAAI,KAAK,OAAO,QAAQ,EAAE;CAEtO,OAAO,oBAAoB,UAAU;EACnC,kBAAkB,OAAO,gBAAgB,0BAA0B;EACnE,kBAAkB,OAAO,iBAAiB,UAAU;EAEpD,OAAO;CACT,CAAC;AACH"}
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
import { d as STUDIO_APP_PATH } from "../HttpPaths-c9nLZ9H2.js";
|
|
2
|
+
|
|
3
|
+
//#region src/runtime/studio-document.ts
|
|
4
|
+
function resolveStudioRoot(document, pathname) {
|
|
5
|
+
const root = document.getElementById("cms-studio");
|
|
6
|
+
if (root) return root;
|
|
7
|
+
if (pathname !== STUDIO_APP_PATH && !pathname.startsWith(`${STUDIO_APP_PATH}/`)) return null;
|
|
8
|
+
const created = document.createElement("div");
|
|
9
|
+
created.id = "cms-studio";
|
|
10
|
+
document.body.replaceChildren(created);
|
|
11
|
+
return created;
|
|
12
|
+
}
|
|
13
|
+
function startStudioDocument(root, catalog, stylesheet, mountStudio) {
|
|
14
|
+
if (!root) return {
|
|
15
|
+
unmount: () => void 0,
|
|
16
|
+
updateAuthoring: () => void 0
|
|
17
|
+
};
|
|
18
|
+
let currentCatalog = catalog;
|
|
19
|
+
let studio;
|
|
20
|
+
const link = document.createElement("link");
|
|
21
|
+
link.rel = "stylesheet";
|
|
22
|
+
link.href = stylesheet;
|
|
23
|
+
link.onload = () => {
|
|
24
|
+
studio = mountStudio(root, currentCatalog);
|
|
25
|
+
};
|
|
26
|
+
link.onerror = () => {
|
|
27
|
+
root.textContent = "CMS Studio styles could not load. Reload this page to retry.";
|
|
28
|
+
};
|
|
29
|
+
document.head.append(link);
|
|
30
|
+
return {
|
|
31
|
+
unmount() {
|
|
32
|
+
link.onload = null;
|
|
33
|
+
link.onerror = null;
|
|
34
|
+
studio?.unmount();
|
|
35
|
+
link.remove();
|
|
36
|
+
},
|
|
37
|
+
updateAuthoring(next) {
|
|
38
|
+
currentCatalog = next;
|
|
39
|
+
studio?.updateAuthoring(next);
|
|
40
|
+
}
|
|
41
|
+
};
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
//#endregion
|
|
45
|
+
export { resolveStudioRoot, startStudioDocument };
|
|
46
|
+
//# sourceMappingURL=studio-document.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"studio-document.js","names":[],"sources":["../../../../src/runtime/studio-document.ts"],"sourcesContent":["import type { AuthoringCatalog } from '@internal/protocol/Configuration'\nimport { STUDIO_APP_PATH } from '@internal/protocol/HttpPaths'\n\ninterface MountedStudio {\n readonly unmount: () => void\n readonly updateAuthoring: (catalog: AuthoringCatalog) => void\n}\n\ninterface StudioDocument {\n readonly unmount: () => void\n readonly updateAuthoring: (catalog: AuthoringCatalog) => void\n}\n\nexport function resolveStudioRoot(document: Document, pathname: string): HTMLElement | null {\n const root = document.getElementById('cms-studio')\n\n if (root) return root\n\n if (pathname !== STUDIO_APP_PATH && !pathname.startsWith(`${STUDIO_APP_PATH}/`)) return null\n\n const created = document.createElement('div')\n created.id = 'cms-studio'\n document.body.replaceChildren(created)\n\n return created\n}\n\nexport function startStudioDocument(\n root: HTMLElement | null,\n catalog: AuthoringCatalog,\n stylesheet: string,\n mountStudio: (root: HTMLElement, catalog: AuthoringCatalog) => MountedStudio,\n): StudioDocument {\n if (!root) return { unmount: () => undefined, updateAuthoring: () => undefined }\n\n let currentCatalog = catalog\n let studio: MountedStudio | undefined\n const link = document.createElement('link')\n link.rel = 'stylesheet'\n link.href = stylesheet\n link.onload = () => {\n studio = mountStudio(root, currentCatalog)\n }\n\n link.onerror = () => {\n root.textContent = 'CMS Studio styles could not load. Reload this page to retry.'\n }\n\n document.head.append(link)\n\n return {\n unmount() {\n link.onload = null\n link.onerror = null\n studio?.unmount()\n link.remove()\n },\n updateAuthoring(next: AuthoringCatalog) {\n currentCatalog = next\n studio?.updateAuthoring(next)\n },\n }\n}\n"],"mappings":";;;AAaA,SAAgB,kBAAkB,UAAoB,UAAsC;CAC1F,MAAM,OAAO,SAAS,eAAe,YAAY;CAEjD,IAAI,MAAM,OAAO;CAEjB,IAAI,aAAa,mBAAmB,CAAC,SAAS,WAAW,GAAG,gBAAgB,EAAE,GAAG,OAAO;CAExF,MAAM,UAAU,SAAS,cAAc,KAAK;CAC5C,QAAQ,KAAK;CACb,SAAS,KAAK,gBAAgB,OAAO;CAErC,OAAO;AACT;AAEA,SAAgB,oBACd,MACA,SACA,YACA,aACgB;CAChB,IAAI,CAAC,MAAM,OAAO;EAAE,eAAe;EAAW,uBAAuB;CAAU;CAE/E,IAAI,iBAAiB;CACrB,IAAI;CACJ,MAAM,OAAO,SAAS,cAAc,MAAM;CAC1C,KAAK,MAAM;CACX,KAAK,OAAO;CACZ,KAAK,eAAe;EAClB,SAAS,YAAY,MAAM,cAAc;CAC3C;CAEA,KAAK,gBAAgB;EACnB,KAAK,cAAc;CACrB;CAEA,SAAS,KAAK,OAAO,IAAI;CAEzB,OAAO;EACL,UAAU;GACR,KAAK,SAAS;GACd,KAAK,UAAU;GACf,QAAQ,QAAQ;GAChB,KAAK,OAAO;EACd;EACA,gBAAgB,MAAwB;GACtC,iBAAiB;GACjB,QAAQ,gBAAgB,IAAI;EAC9B;CACF;AACF"}
|
|
@@ -1,34 +1,17 @@
|
|
|
1
|
+
import { resolveStudioRoot, startStudioDocument } from "./studio-document.js";
|
|
1
2
|
import authoring from "#cms/authoring";
|
|
2
3
|
import { mountStudio } from "#cms/studio";
|
|
3
4
|
import stylesheet from "#cms/studio-styles";
|
|
4
5
|
|
|
5
6
|
//#region src/runtime/studio-entry.ts
|
|
6
|
-
const root = document.
|
|
7
|
-
|
|
8
|
-
let currentCatalog = authoring;
|
|
9
|
-
let studio;
|
|
10
|
-
const link = document.createElement("link");
|
|
11
|
-
link.rel = "stylesheet";
|
|
12
|
-
link.href = stylesheet;
|
|
13
|
-
link.onload = () => {
|
|
14
|
-
studio = mountStudio(root, currentCatalog);
|
|
15
|
-
};
|
|
16
|
-
link.onerror = () => {
|
|
17
|
-
root.textContent = "CMS Studio styles could not load. Reload this page to retry.";
|
|
18
|
-
};
|
|
19
|
-
document.head.append(link);
|
|
7
|
+
const root = resolveStudioRoot(document, window.location.pathname);
|
|
8
|
+
const studio = startStudioDocument(root, authoring, stylesheet, mountStudio);
|
|
20
9
|
if (import.meta.hot) {
|
|
21
10
|
import.meta.hot.accept("#cms/authoring", (module) => {
|
|
22
11
|
if (!module) return;
|
|
23
|
-
|
|
24
|
-
studio?.updateAuthoring(currentCatalog);
|
|
25
|
-
});
|
|
26
|
-
import.meta.hot.dispose(() => {
|
|
27
|
-
link.onload = null;
|
|
28
|
-
link.onerror = null;
|
|
29
|
-
studio?.unmount();
|
|
30
|
-
link.remove();
|
|
12
|
+
studio.updateAuthoring(module.default);
|
|
31
13
|
});
|
|
14
|
+
import.meta.hot.dispose(studio.unmount);
|
|
32
15
|
}
|
|
33
16
|
|
|
34
17
|
//#endregion
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"studio-entry.js","names":["catalog"],"sources":["../../../../src/runtime/studio-entry.ts"],"sourcesContent":["import { mountStudio } from '#cms/studio'\nimport catalog from '#cms/authoring'\nimport stylesheet from '#cms/studio-styles'\
|
|
1
|
+
{"version":3,"file":"studio-entry.js","names":["catalog"],"sources":["../../../../src/runtime/studio-entry.ts"],"sourcesContent":["import { mountStudio } from '#cms/studio'\nimport catalog from '#cms/authoring'\nimport stylesheet from '#cms/studio-styles'\nimport { resolveStudioRoot, startStudioDocument } from './studio-document'\n\nconst root = resolveStudioRoot(document, window.location.pathname)\n\nconst studio = startStudioDocument(root, catalog, stylesheet, mountStudio)\n\nif (import.meta.hot) {\n import.meta.hot.accept('#cms/authoring', (module) => {\n if (!module) return\n studio.updateAuthoring(module.default)\n })\n import.meta.hot.dispose(studio.unmount)\n}\n"],"mappings":";;;;;;AAKA,MAAM,OAAO,kBAAkB,UAAU,OAAO,SAAS,QAAQ;AAEjE,MAAM,SAAS,oBAAoB,MAAMA,WAAS,YAAY,WAAW;AAEzE,IAAI,YAAY,KAAK;CACnB,YAAY,IAAI,OAAO,mBAAmB,WAAW;EACnD,IAAI,CAAC,QAAQ;EACb,OAAO,gBAAgB,OAAO,OAAO;CACvC,CAAC;CACD,YAAY,IAAI,QAAQ,OAAO,OAAO;AACxC"}
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { o as PublicPath, r as DocumentId } from "./scalars-CVZqT3L0.js";
|
|
2
2
|
import { it as CollectionName, n as CmsMarkdownDocument } from "./models-VmGmG19-.js";
|
|
3
3
|
import { f as mutableJson, p as mutableJsonObject } from "./Forms-CX-hwmJF.js";
|
|
4
|
-
import { n as editorMetadata } from "./metadata-
|
|
4
|
+
import { n as editorMetadata } from "./metadata-DN9_K6Yl.js";
|
|
5
5
|
import { prepareFormDocument } from "./runtime/forms/document.js";
|
|
6
6
|
import { CMS_PREVIEW_EDGE_PROPERTY, CMS_PREVIEW_KIND_PROPERTY, CMS_PREVIEW_MARKER_TAG, CMS_PREVIEW_NODE_PROPERTY } from "./runtime/preview/protocol.js";
|
|
7
7
|
import { toPreviewRenderDocument } from "./runtime/preview/comark-document.js";
|
|
@@ -206,4 +206,4 @@ function createPreviewDocument(body) {
|
|
|
206
206
|
|
|
207
207
|
//#endregion
|
|
208
208
|
export { createStudioPreviewStore as t };
|
|
209
|
-
//# sourceMappingURL=store-
|
|
209
|
+
//# sourceMappingURL=store-X1e1o_MF.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"store-PKKB8xa2.js","names":["CmsMarkdownDocumentSchema"],"sources":["../../../../document/src/PreviewProjection.ts","../../../src/runtime/preview/store.ts"],"sourcesContent":["import type { CmsMarkdownDocument, MarkdownNode } from '@internal/protocol/Documents'\nimport type { EditorNodeId } from '@internal/protocol/Documents'\nimport { CmsMarkdownDocument as CmsMarkdownDocumentSchema } from '@internal/protocol/Documents'\nimport { Predicate, Result, Schema } from 'effect'\nimport { mutableJson, mutableJsonObject } from './internal/comark/document-adapter'\nimport { editorMetadata } from './internal/editor/metadata'\n\nexport interface PreviewProjectionMarkers {\n readonly edgeProperty: string\n readonly kindProperty: string\n readonly nodeProperty: string\n readonly tag: string\n}\n\nexport interface PreviewProjection {\n readonly body: CmsMarkdownDocument\n readonly fallbacks: Readonly<Record<string, string>>\n}\n\nexport class PreviewProjectionInvalid extends Schema.TaggedError<PreviewProjectionInvalid>()(\n 'PreviewProjection.Invalid',\n {\n message: Schema.NonEmptyString,\n cause: Schema.Defect(),\n },\n) {}\n\nconst NATIVE_BLOCK_TAGS = new Set([\n 'blockquote',\n 'h1',\n 'h2',\n 'h3',\n 'h4',\n 'h5',\n 'h6',\n 'hr',\n 'img',\n 'li',\n 'math',\n 'ol',\n 'p',\n 'pre',\n 'table',\n 'tbody',\n 'td',\n 'th',\n 'thead',\n 'tr',\n 'ul',\n])\n\nexport function projectPreviewDocument(\n body: CmsMarkdownDocument,\n markers: PreviewProjectionMarkers,\n): Result.Result<PreviewProjection, PreviewProjectionInvalid> {\n return Result.try({\n try: () => projectPreviewDocumentUnsafe(body, markers),\n catch: (cause) =>\n new PreviewProjectionInvalid({\n cause,\n message: cause instanceof Error && cause.message ? cause.message : 'The preview projection is invalid.',\n }),\n })\n}\n\nfunction projectPreviewDocumentUnsafe(body: CmsMarkdownDocument, markers: PreviewProjectionMarkers): PreviewProjection {\n const fallbacks: Record<string, string> = {}\n let identifiedTargets = 0\n\n function cloneNode(\n node: MarkdownNode,\n componentId?: EditorNodeId,\n slotId?: EditorNodeId,\n ): ReadonlyArray<Schema.Json> {\n if (Predicate.isString(node) || node[0] === null) return [mutableJson(node)]\n const [tag, originalAttributes, ...originalChildren] = node\n const isSlot = tag === 'template'\n const isNative = NATIVE_BLOCK_TAGS.has(tag)\n const attributes = mutableJsonObject(originalAttributes)\n const metadata = editorMetadata(attributes)\n const id = metadata?.nodeId\n\n if (id) {\n identifiedTargets++\n const parentId = slotId ?? componentId\n\n if (parentId) fallbacks[id] = parentId\n }\n\n const nextComponentId = !isNative && !isSlot && id ? id : componentId\n\n const implicitSlotId =\n id && metadata?.implicitSlotId && !isNative && !isSlot && hasImplicitDefaultContent(originalChildren)\n ? metadata.implicitSlotId\n : undefined\n\n const children = originalChildren.flatMap((child) => {\n const childSlotId = explicitSlotId(child) ?? (isSlot ? id : implicitSlotId) ?? slotId\n const projected = cloneNode(child, nextComponentId, childSlotId)\n\n return implicitSlotId && !isSlot && !isSlotNode(child)\n ? previewRange(implicitSlotId, 'field', projected, markers)\n : projected\n })\n\n if (id && implicitSlotId) fallbacks[implicitSlotId] = id\n\n if (isSlot && id && componentId) fallbacks[id] = componentId\n\n const cloned: Schema.Json = [tag, attributes, ...children]\n\n if (isSlot && id && componentId) return [[tag, attributes, ...previewRange(id, 'field', children, markers)]]\n\n if (id && isNative) return previewRange(id, 'native', [cloned], markers)\n\n if (id && !isSlot) return previewRange(id, 'component', [cloned], markers)\n\n return [cloned]\n }\n\n const nodes = body.nodes.flatMap((node) => cloneNode(node))\n\n if (body.nodes.length && !identifiedTargets)\n throw new Error('Studio preview requires an identified authoring document.')\n\n return {\n body: CmsMarkdownDocumentSchema.make({\n frontmatter: mutableJsonObject(body.frontmatter),\n meta: mutableJsonObject(body.meta),\n nodes,\n }),\n fallbacks,\n }\n}\n\nfunction previewRange(\n nodeId: EditorNodeId,\n kind: 'component' | 'field' | 'native',\n children: ReadonlyArray<Schema.Json>,\n markers: PreviewProjectionMarkers,\n): ReadonlyArray<Schema.Json> {\n const marker = (edge: 'end' | 'start'): Schema.Json => [\n markers.tag,\n {\n [markers.edgeProperty]: edge,\n [markers.kindProperty]: kind,\n [markers.nodeProperty]: nodeId,\n },\n ]\n\n return [marker('start'), ...children, marker('end')]\n}\n\nfunction explicitSlotId(node: MarkdownNode): EditorNodeId | undefined {\n if (Predicate.isString(node) || node[0] !== 'template') return undefined\n\n return editorMetadata(node[1])?.nodeId\n}\n\nfunction isSlotNode(node: MarkdownNode): boolean {\n return !Predicate.isString(node) && node[0] === 'template'\n}\n\nfunction hasImplicitDefaultContent(nodes: ReadonlyArray<MarkdownNode>): boolean {\n const hasExplicitDefault = nodes.some(\n (node) => Array.isArray(node) && node[0] === 'template' && node[1].name === 'default',\n )\n\n return (\n !hasExplicitDefault && nodes.some((node) => (Predicate.isString(node) ? Boolean(node) : node[0] !== 'template'))\n )\n}\n","import { prepareFormDocument } from '../forms/document'\nimport type { ComponentDefinition } from '@internal/protocol/Configuration'\nimport type { RenderedCompiledDocument, RenderedDocumentManifest } from '@internal/protocol/Preview'\nimport { projectPreviewDocument } from '@internal/document/PreviewProjection'\nimport { CollectionName } from '@internal/protocol/Configuration'\nimport { DocumentId, PublicPath } from '@internal/protocol/Documents'\nimport { Result } from 'effect'\nimport { createComarkContext } from 'comark'\nimport { shallowRef } from 'vue'\nimport type { DeliveryDocument as PreviewCompiledDocument } from '../delivery/types'\nimport type { DocumentPreviewStore, PreviewDocumentRole } from '../delivery/preview'\nimport { toPreviewRenderDocument } from './comark-document'\nimport {\n CMS_PREVIEW_EDGE_PROPERTY,\n CMS_PREVIEW_KIND_PROPERTY,\n CMS_PREVIEW_MARKER_TAG,\n CMS_PREVIEW_NODE_PROPERTY,\n} from './protocol'\n\nexport { documentPreviewStoreKey, type DocumentPreviewStore, type PreviewDocumentRole } from '../delivery/preview'\n\nexport type { DeliveryDocument as PreviewCompiledDocument } from '../delivery/types'\n\nexport interface StudioPreviewStore extends DocumentPreviewStore {\n readonly manifest: () => RenderedDocumentManifest\n readonly patch: (document: PreviewCompiledDocument) => Promise<Readonly<Record<string, string>>>\n readonly routeChanged: () => void\n readonly subscribe: (listener: (manifest: RenderedDocumentManifest) => void) => () => void\n}\n\nexport function createStudioPreviewStore(\n route: () => RenderedDocumentManifest['route'],\n forms: () => ReadonlyArray<ComponentDefinition> = () => [],\n): StudioPreviewStore {\n const context = createComarkContext()\n const patches = shallowRef(new Map<string, PreviewCompiledDocument>())\n\n const registrations = new Map<\n symbol,\n { readonly document: PreviewCompiledDocument; readonly role: PreviewDocumentRole }\n >()\n\n const listeners = new Set<(manifest: RenderedDocumentManifest) => void>()\n\n const manifest = (): RenderedDocumentManifest => ({\n documents: renderedDocuments(registrations.values(), patches.value),\n route: route(),\n })\n\n const notify = (): void => {\n const value = manifest()\n\n for (const listener of listeners) listener(value)\n }\n\n return {\n manifest,\n // oxlint-disable-next-line effecttsgo/async-function -- The Promise contract turns synchronous projection failures into patch rejections for the preview controller.\n async patch(document) {\n const preview = createPreviewDocument(document.body)\n const patched = prepareFormDocument({ ...document, body: preview.body }, forms(), true)\n patches.value = new Map(patches.value).set(document.id, patched)\n const renderBody = toPreviewRenderDocument(patched.body)\n context.get(document.id, renderBody).set(renderBody)\n notify()\n\n return preview.fallbacks\n },\n register(document, role) {\n const registration = Symbol(document.id)\n registrations.set(registration, { document, role })\n notify()\n\n return () => {\n registrations.delete(registration)\n notify()\n }\n },\n resolve(document) {\n return patches.value.get(document.id) ?? document\n },\n routeChanged: notify,\n subscribe(listener) {\n listeners.add(listener)\n listener(manifest())\n\n return () => listeners.delete(listener)\n },\n }\n}\n\nfunction renderedDocuments(\n registrations: Iterable<{ readonly document: PreviewCompiledDocument; readonly role: PreviewDocumentRole }>,\n patches: ReadonlyMap<string, PreviewCompiledDocument>,\n): ReadonlyArray<RenderedCompiledDocument> {\n const priority = { embedded: 1, primary: 4, related: 2, summary: 3 } satisfies Record<PreviewDocumentRole, number>\n const documents = new Map<string, RenderedCompiledDocument>()\n\n for (const registration of registrations) {\n const document = patches.get(registration.document.id) ?? registration.document\n const current = documents.get(document.id)\n\n if (current && priority[current.role] >= priority[registration.role]) continue\n documents.set(document.id, {\n collection: CollectionName.make(document.collection),\n documentId: DocumentId.make(document.id),\n path: PublicPath.make(document.path),\n role: registration.role,\n title: document.title,\n })\n }\n\n return [...documents.values()].sort(\n (left, right) => priority[right.role] - priority[left.role] || left.title.localeCompare(right.title),\n )\n}\n\nfunction createPreviewDocument(body: PreviewCompiledDocument['body']) {\n const projection = projectPreviewDocument(body, {\n edgeProperty: CMS_PREVIEW_EDGE_PROPERTY,\n kindProperty: CMS_PREVIEW_KIND_PROPERTY,\n nodeProperty: CMS_PREVIEW_NODE_PROPERTY,\n tag: CMS_PREVIEW_MARKER_TAG,\n })\n\n if (Result.isFailure(projection)) throw projection.failure\n\n return projection.success\n}\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"store-X1e1o_MF.js","names":["CmsMarkdownDocumentSchema"],"sources":["../../../../document/src/PreviewProjection.ts","../../../src/runtime/preview/store.ts"],"sourcesContent":["import type { CmsMarkdownDocument, MarkdownNode } from '@internal/protocol/Documents'\nimport type { EditorNodeId } from '@internal/protocol/Documents'\nimport { CmsMarkdownDocument as CmsMarkdownDocumentSchema } from '@internal/protocol/Documents'\nimport { Predicate, Result, Schema } from 'effect'\nimport { mutableJson, mutableJsonObject } from './internal/comark/document-adapter'\nimport { editorMetadata } from './internal/editor/metadata'\n\nexport interface PreviewProjectionMarkers {\n readonly edgeProperty: string\n readonly kindProperty: string\n readonly nodeProperty: string\n readonly tag: string\n}\n\nexport interface PreviewProjection {\n readonly body: CmsMarkdownDocument\n readonly fallbacks: Readonly<Record<string, string>>\n}\n\nexport class PreviewProjectionInvalid extends Schema.TaggedError<PreviewProjectionInvalid>()(\n 'PreviewProjection.Invalid',\n {\n message: Schema.NonEmptyString,\n cause: Schema.Defect(),\n },\n) {}\n\nconst NATIVE_BLOCK_TAGS = new Set([\n 'blockquote',\n 'h1',\n 'h2',\n 'h3',\n 'h4',\n 'h5',\n 'h6',\n 'hr',\n 'img',\n 'li',\n 'math',\n 'ol',\n 'p',\n 'pre',\n 'table',\n 'tbody',\n 'td',\n 'th',\n 'thead',\n 'tr',\n 'ul',\n])\n\nexport function projectPreviewDocument(\n body: CmsMarkdownDocument,\n markers: PreviewProjectionMarkers,\n): Result.Result<PreviewProjection, PreviewProjectionInvalid> {\n return Result.try({\n try: () => projectPreviewDocumentUnsafe(body, markers),\n catch: (cause) =>\n new PreviewProjectionInvalid({\n cause,\n message: cause instanceof Error && cause.message ? cause.message : 'The preview projection is invalid.',\n }),\n })\n}\n\nfunction projectPreviewDocumentUnsafe(body: CmsMarkdownDocument, markers: PreviewProjectionMarkers): PreviewProjection {\n const fallbacks: Record<string, string> = {}\n let identifiedTargets = 0\n\n function cloneNode(\n node: MarkdownNode,\n componentId?: EditorNodeId,\n slotId?: EditorNodeId,\n ): ReadonlyArray<Schema.Json> {\n if (Predicate.isString(node) || node[0] === null) return [mutableJson(node)]\n const [tag, originalAttributes, ...originalChildren] = node\n const isSlot = tag === 'template'\n const isNative = NATIVE_BLOCK_TAGS.has(tag)\n const attributes = mutableJsonObject(originalAttributes)\n const metadata = editorMetadata(attributes)\n const id = metadata?.nodeId\n\n if (id) {\n identifiedTargets++\n const parentId = slotId ?? componentId\n\n if (parentId) fallbacks[id] = parentId\n }\n\n const nextComponentId = !isNative && !isSlot && id ? id : componentId\n\n const implicitSlotId =\n id && metadata?.implicitSlotId && !isNative && !isSlot && hasImplicitDefaultContent(originalChildren)\n ? metadata.implicitSlotId\n : undefined\n\n const children = originalChildren.flatMap((child) => {\n const childSlotId = explicitSlotId(child) ?? (isSlot ? id : implicitSlotId) ?? slotId\n const projected = cloneNode(child, nextComponentId, childSlotId)\n\n return implicitSlotId && !isSlot && !isSlotNode(child)\n ? previewRange(implicitSlotId, 'field', projected, markers)\n : projected\n })\n\n if (id && implicitSlotId) fallbacks[implicitSlotId] = id\n\n if (isSlot && id && componentId) fallbacks[id] = componentId\n\n const cloned: Schema.Json = [tag, attributes, ...children]\n\n if (isSlot && id && componentId) return [[tag, attributes, ...previewRange(id, 'field', children, markers)]]\n\n if (id && isNative) return previewRange(id, 'native', [cloned], markers)\n\n if (id && !isSlot) return previewRange(id, 'component', [cloned], markers)\n\n return [cloned]\n }\n\n const nodes = body.nodes.flatMap((node) => cloneNode(node))\n\n if (body.nodes.length && !identifiedTargets)\n throw new Error('Studio preview requires an identified authoring document.')\n\n return {\n body: CmsMarkdownDocumentSchema.make({\n frontmatter: mutableJsonObject(body.frontmatter),\n meta: mutableJsonObject(body.meta),\n nodes,\n }),\n fallbacks,\n }\n}\n\nfunction previewRange(\n nodeId: EditorNodeId,\n kind: 'component' | 'field' | 'native',\n children: ReadonlyArray<Schema.Json>,\n markers: PreviewProjectionMarkers,\n): ReadonlyArray<Schema.Json> {\n const marker = (edge: 'end' | 'start'): Schema.Json => [\n markers.tag,\n {\n [markers.edgeProperty]: edge,\n [markers.kindProperty]: kind,\n [markers.nodeProperty]: nodeId,\n },\n ]\n\n return [marker('start'), ...children, marker('end')]\n}\n\nfunction explicitSlotId(node: MarkdownNode): EditorNodeId | undefined {\n if (Predicate.isString(node) || node[0] !== 'template') return undefined\n\n return editorMetadata(node[1])?.nodeId\n}\n\nfunction isSlotNode(node: MarkdownNode): boolean {\n return !Predicate.isString(node) && node[0] === 'template'\n}\n\nfunction hasImplicitDefaultContent(nodes: ReadonlyArray<MarkdownNode>): boolean {\n const hasExplicitDefault = nodes.some(\n (node) => Array.isArray(node) && node[0] === 'template' && node[1].name === 'default',\n )\n\n return (\n !hasExplicitDefault && nodes.some((node) => (Predicate.isString(node) ? Boolean(node) : node[0] !== 'template'))\n )\n}\n","import { prepareFormDocument } from '../forms/document'\nimport type { ComponentDefinition } from '@internal/protocol/Configuration'\nimport type { RenderedCompiledDocument, RenderedDocumentManifest } from '@internal/protocol/Preview'\nimport { projectPreviewDocument } from '@internal/document/PreviewProjection'\nimport { CollectionName } from '@internal/protocol/Configuration'\nimport { DocumentId, PublicPath } from '@internal/protocol/Documents'\nimport { Result } from 'effect'\nimport { createComarkContext } from 'comark'\nimport { shallowRef } from 'vue'\nimport type { DeliveryDocument as PreviewCompiledDocument } from '../delivery/types'\nimport type { DocumentPreviewStore, PreviewDocumentRole } from '../delivery/preview'\nimport { toPreviewRenderDocument } from './comark-document'\nimport {\n CMS_PREVIEW_EDGE_PROPERTY,\n CMS_PREVIEW_KIND_PROPERTY,\n CMS_PREVIEW_MARKER_TAG,\n CMS_PREVIEW_NODE_PROPERTY,\n} from './protocol'\n\nexport { documentPreviewStoreKey, type DocumentPreviewStore, type PreviewDocumentRole } from '../delivery/preview'\n\nexport type { DeliveryDocument as PreviewCompiledDocument } from '../delivery/types'\n\nexport interface StudioPreviewStore extends DocumentPreviewStore {\n readonly manifest: () => RenderedDocumentManifest\n readonly patch: (document: PreviewCompiledDocument) => Promise<Readonly<Record<string, string>>>\n readonly routeChanged: () => void\n readonly subscribe: (listener: (manifest: RenderedDocumentManifest) => void) => () => void\n}\n\nexport function createStudioPreviewStore(\n route: () => RenderedDocumentManifest['route'],\n forms: () => ReadonlyArray<ComponentDefinition> = () => [],\n): StudioPreviewStore {\n const context = createComarkContext()\n const patches = shallowRef(new Map<string, PreviewCompiledDocument>())\n\n const registrations = new Map<\n symbol,\n { readonly document: PreviewCompiledDocument; readonly role: PreviewDocumentRole }\n >()\n\n const listeners = new Set<(manifest: RenderedDocumentManifest) => void>()\n\n const manifest = (): RenderedDocumentManifest => ({\n documents: renderedDocuments(registrations.values(), patches.value),\n route: route(),\n })\n\n const notify = (): void => {\n const value = manifest()\n\n for (const listener of listeners) listener(value)\n }\n\n return {\n manifest,\n // oxlint-disable-next-line effecttsgo/async-function -- The Promise contract turns synchronous projection failures into patch rejections for the preview controller.\n async patch(document) {\n const preview = createPreviewDocument(document.body)\n const patched = prepareFormDocument({ ...document, body: preview.body }, forms(), true)\n patches.value = new Map(patches.value).set(document.id, patched)\n const renderBody = toPreviewRenderDocument(patched.body)\n context.get(document.id, renderBody).set(renderBody)\n notify()\n\n return preview.fallbacks\n },\n register(document, role) {\n const registration = Symbol(document.id)\n registrations.set(registration, { document, role })\n notify()\n\n return () => {\n registrations.delete(registration)\n notify()\n }\n },\n resolve(document) {\n return patches.value.get(document.id) ?? document\n },\n routeChanged: notify,\n subscribe(listener) {\n listeners.add(listener)\n listener(manifest())\n\n return () => listeners.delete(listener)\n },\n }\n}\n\nfunction renderedDocuments(\n registrations: Iterable<{ readonly document: PreviewCompiledDocument; readonly role: PreviewDocumentRole }>,\n patches: ReadonlyMap<string, PreviewCompiledDocument>,\n): ReadonlyArray<RenderedCompiledDocument> {\n const priority = { embedded: 1, primary: 4, related: 2, summary: 3 } satisfies Record<PreviewDocumentRole, number>\n const documents = new Map<string, RenderedCompiledDocument>()\n\n for (const registration of registrations) {\n const document = patches.get(registration.document.id) ?? registration.document\n const current = documents.get(document.id)\n\n if (current && priority[current.role] >= priority[registration.role]) continue\n documents.set(document.id, {\n collection: CollectionName.make(document.collection),\n documentId: DocumentId.make(document.id),\n path: PublicPath.make(document.path),\n role: registration.role,\n title: document.title,\n })\n }\n\n return [...documents.values()].sort(\n (left, right) => priority[right.role] - priority[left.role] || left.title.localeCompare(right.title),\n )\n}\n\nfunction createPreviewDocument(body: PreviewCompiledDocument['body']) {\n const projection = projectPreviewDocument(body, {\n edgeProperty: CMS_PREVIEW_EDGE_PROPERTY,\n kindProperty: CMS_PREVIEW_KIND_PROPERTY,\n nodeProperty: CMS_PREVIEW_NODE_PROPERTY,\n tag: CMS_PREVIEW_MARKER_TAG,\n })\n\n if (Result.isFailure(projection)) throw projection.failure\n\n return projection.success\n}\n"],"mappings":"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"}
|