@vcp-prod/site-edit-engine 0.3.14

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,2 @@
1
+ import type { SiteEditNextRouteConfig } from "./next-app-router.js";
2
+ export declare function scanNextAppRouterRoutes(projectRoot: string): SiteEditNextRouteConfig[];
@@ -0,0 +1,11 @@
1
+ export type SiteEditNextRouteConfig = {
2
+ routeId: string;
3
+ entryFile: string;
4
+ };
5
+ export { scanNextAppRouterRoutes } from "./next-app-router-fs.js";
6
+ export type SiteEditRouteSourceFile = {
7
+ path: string;
8
+ };
9
+ export declare function scanNextAppRouterRoutesFromFiles(files: SiteEditRouteSourceFile[]): SiteEditNextRouteConfig[];
10
+ export declare function resolveNextAppRouteId(pathname: string | null | undefined, routes: SiteEditNextRouteConfig[], basePath?: string): string | undefined;
11
+ export declare function normalizeNextRoutePath(pathname: string | null | undefined, basePath?: string): string;
@@ -0,0 +1 @@
1
+ import u from"node:fs";import a from"node:path";var R=/^page\.(?:tsx|ts|jsx|js|mjs|cjs)$/;function x(t){let r=P(t);return r?l(r).map(e=>({routeId:I(r,e),entryFile:p(a.relative(t,e))})).sort((e,n)=>e.routeId.localeCompare(n.routeId)):[]}function P(t){for(let r of["app","src/app"]){let e=a.join(t,r);if(u.existsSync(e)&&u.statSync(e).isDirectory())return e}return null}function l(t){let r=[];for(let e of u.readdirSync(t,{withFileTypes:!0})){let n=a.join(t,e.name);if(e.isDirectory()){if(e.name==="node_modules"||e.name.startsWith(".")||e.name.startsWith("_"))continue;r.push(...l(n));continue}e.isFile()&&R.test(e.name)&&r.push(n)}return r}function I(t,r){let e=p(a.relative(t,a.dirname(r))),n=e?e.split("/").map(W).filter(i=>!!i):[];return n.length===0?"/":`/${n.join("/")}`}function $(t){return t.startsWith("(")&&t.endsWith(")")}function W(t){return!t||t.startsWith("@")||t.startsWith("_")||$(t)?null:g(t)}function g(t){return t.replace(/^\((?:\.|\.\.|\.\.\.)\)/,"")}function p(t){return t.replace(/\\/g,"/")}var S=/^page\.(?:tsx|ts|jsx|js|mjs|cjs)$/,h=/^\[[^\]]+\]$/,d=/^\[\.\.\.[^\]]+\]$/,m=/^\[\[\.\.\.[^\]]+\]\]$/;function E(t){let r=t.map(n=>C(n.path)),e=A(r);return e?r.filter(n=>j(e,n)).map(n=>({routeId:v(e,n),entryFile:n})).sort((n,i)=>n.routeId.localeCompare(i.routeId)):[]}function G(t,r,e=""){let n=y(t,e);return r.some(o=>o.routeId===n)?n:[...r].sort((o,s)=>f(s.routeId)-f(o.routeId)||s.routeId.length-o.routeId.length||o.routeId.localeCompare(s.routeId)).find(o=>w(o.routeId).test(n))?.routeId}function y(t,r=""){let n=((t??"/").trim()||"/").split(/[?#]/,1)[0]||"/",i=n.startsWith("/")?n:`/${n}`,o=N(r),s=o&&(i===o||i.startsWith(`${o}/`))?i.slice(o.length)||"/":i,c=s.startsWith("/")?s:`/${s}`;return c==="/"?"/":c.replace(/\/+$/,"")}function A(t){return t.some(n=>n.startsWith("app/"))?"app":t.some(n=>n.startsWith("src/app/"))?"src/app":null}function j(t,r){if(!r.startsWith(`${t}/`))return!1;let e=r.slice(r.lastIndexOf("/")+1);return S.test(e)?r.slice(t.length+1,-e.length-1).split("/").filter(Boolean).every(n=>!n.startsWith("_")):!1}function v(t,r){let e=r.slice(t.length+1).split("/").slice(0,-1).map(z).filter(n=>!!n);return e.length===0?"/":`/${e.join("/")}`}function F(t){return t.startsWith("(")&&t.endsWith(")")}function z(t){return!t||t.startsWith("@")||t.startsWith("_")||F(t)?null:B(t)}function B(t){return t.replace(/^\((?:\.|\.\.|\.\.\.)\)/,"")}function w(t){if(t==="/")return/^\/$/;let r=t.split("/").filter(Boolean).map(e=>m.test(e)?"(?:/.*)?":d.test(e)?"/.+":h.test(e)?"/[^/]+":`/${_(e)}`).join("");return new RegExp(`^${r}$`)}function f(t){return t.split("/").filter(Boolean).reduce((r,e)=>m.test(e)?r+1:d.test(e)?r+2:h.test(e)?r+3:r+4,0)}function N(t){let r=t.trim();return!r||r==="/"?"":(r.startsWith("/")?r:`/${r}`).replace(/\/+$/,"")}function _(t){return t.replace(/[.*+?^${}()|[\]\\]/g,"\\$&")}function C(t){return t.replace(/\\/g,"/").replace(/^\.\//,"")}export{y as normalizeNextRoutePath,G as resolveNextAppRouteId,x as scanNextAppRouterRoutes,E as scanNextAppRouterRoutesFromFiles};
@@ -0,0 +1,318 @@
1
+ import type { SiteEditOperationCommandResult } from "@vcp-prod/contracts";
2
+ import type { PreviewSiteEditEngineRuntime, PreviewSiteEditEngineRuntimeOptions } from "./types.js";
3
+ export declare class PreviewFileSystemSiteEditEngineRuntime implements PreviewSiteEditEngineRuntime {
4
+ private readonly options;
5
+ private readonly engine;
6
+ private readonly listeners;
7
+ constructor(options: PreviewSiteEditEngineRuntimeOptions);
8
+ get status(): PreviewSiteEditEngineRuntime["status"];
9
+ registerRoute(routeId: string, entryFile: string): void;
10
+ unregisterRoute(routeId: string): void;
11
+ setActiveRoute(routeId: string): Promise<void>;
12
+ getDocument(routeId: string): {
13
+ ok: true;
14
+ data: {
15
+ siteId: string;
16
+ snapshotId: string;
17
+ routeId: string;
18
+ version: number;
19
+ rootKeys: string[];
20
+ entries: {
21
+ key: string;
22
+ tag: string;
23
+ label: string;
24
+ parentKey: string | null;
25
+ childKeys: string[];
26
+ operationSummary: {
27
+ canUpdateText: boolean;
28
+ canInsertChild: boolean;
29
+ canMove: boolean;
30
+ canRemove: boolean;
31
+ };
32
+ }[];
33
+ };
34
+ };
35
+ getObjectSummary(key: string, routeId?: string): {
36
+ readonly ok: true;
37
+ readonly data: {
38
+ key: string;
39
+ tag: string;
40
+ label: string;
41
+ capabilities: {
42
+ constraints: {
43
+ kind: "component-boundary" | "repeat-region" | "conditional-region" | "opaque-region" | "void-element" | "read-only" | "cross-file-required" | "import-required";
44
+ message: string;
45
+ }[];
46
+ };
47
+ isOpaque: boolean;
48
+ ancestors: {
49
+ key: string;
50
+ label: string;
51
+ tag: string;
52
+ }[];
53
+ sourceLocator?: {
54
+ sourceFile: string;
55
+ componentName: string;
56
+ openingElementRange: {
57
+ startLine: number;
58
+ startColumn: number;
59
+ endLine: number;
60
+ endColumn: number;
61
+ };
62
+ structuralPath: string;
63
+ textPreview?: string | undefined;
64
+ } | undefined;
65
+ provenanceChain?: {
66
+ editMode: "direct" | "proxy" | "upstream" | "readonly" | "unsupported";
67
+ diagnostics: {
68
+ code: string;
69
+ message: string;
70
+ }[];
71
+ } | undefined;
72
+ };
73
+ };
74
+ getObjectEditContext(key: string, routeId?: string): {
75
+ readonly ok: true;
76
+ readonly data: {
77
+ key: string;
78
+ componentName: string;
79
+ sourceFile: string;
80
+ capabilities: {
81
+ key: string;
82
+ canUpdateText: boolean;
83
+ canInsertChild: boolean;
84
+ canMove: boolean;
85
+ canRemove: boolean;
86
+ constraints: {
87
+ kind: "component-boundary" | "repeat-region" | "conditional-region" | "opaque-region" | "void-element" | "read-only" | "cross-file-required" | "import-required";
88
+ message: string;
89
+ }[];
90
+ editModes?: {
91
+ updateText?: {
92
+ mode: "direct" | "proxy" | "upstream" | "readonly" | "unsupported";
93
+ reasonCode?: string | undefined;
94
+ } | undefined;
95
+ insertChild?: {
96
+ mode: "direct" | "proxy" | "upstream" | "readonly" | "unsupported";
97
+ reasonCode?: string | undefined;
98
+ } | undefined;
99
+ move?: {
100
+ mode: "direct" | "proxy" | "upstream" | "readonly" | "unsupported";
101
+ reasonCode?: string | undefined;
102
+ } | undefined;
103
+ remove?: {
104
+ mode: "direct" | "proxy" | "upstream" | "readonly" | "unsupported";
105
+ reasonCode?: string | undefined;
106
+ } | undefined;
107
+ } | undefined;
108
+ };
109
+ writeTarget: {
110
+ kind: "jsx-node" | "component-proxy" | "value-binding" | "route-export";
111
+ file: string;
112
+ componentName: string;
113
+ isProxy: boolean;
114
+ };
115
+ textSegments: {
116
+ index: number;
117
+ value: string;
118
+ editable: boolean;
119
+ source: {
120
+ kind: "literal" | "binding" | "imported-binding" | "repeat-template";
121
+ file: string;
122
+ expression: string;
123
+ bindingName?: string | undefined;
124
+ path?: (string | number)[] | undefined;
125
+ } | null;
126
+ }[];
127
+ boundaryKind: "component-boundary" | "repeat-region" | "conditional-region" | "fragment-region" | "opaque-region" | null;
128
+ children: {
129
+ key: string;
130
+ label: string;
131
+ tag: string;
132
+ }[];
133
+ siblings: {
134
+ key: string;
135
+ label: string;
136
+ tag: string;
137
+ }[];
138
+ effectiveWriteTarget?: {
139
+ kind: "jsx-node" | "route-export" | "value-path" | "external-entry";
140
+ isProxy: boolean;
141
+ file?: string | undefined;
142
+ displayPath?: string | undefined;
143
+ sourceType?: "api-field" | "cms-field" | "i18n-message" | "config-entry" | undefined;
144
+ sourceId?: string | undefined;
145
+ } | undefined;
146
+ provenanceChain?: {
147
+ finalSource: {
148
+ kind: "api-field" | "cms-field" | "i18n-message" | "config-entry" | "binding" | "imported-binding" | "repeat-template" | "jsx-literal" | "component-prop" | "object-field" | "array-item" | "conditional-branch";
149
+ file: string;
150
+ displayPath: string;
151
+ externalSource?: {
152
+ sourceType: "api-field" | "cms-field" | "i18n-message" | "config-entry";
153
+ sourceId: string;
154
+ adapterId?: string | undefined;
155
+ } | undefined;
156
+ } | null;
157
+ chain: {
158
+ kind: "api-field" | "cms-field" | "i18n-message" | "config-entry" | "binding" | "imported-binding" | "repeat-template" | "jsx-literal" | "component-prop" | "object-field" | "array-item" | "conditional-branch";
159
+ file: string;
160
+ displayName: string;
161
+ canEditHere: boolean;
162
+ }[];
163
+ confidence: "exact" | "safe-derived" | "partial" | "unknown";
164
+ editMode: "direct" | "proxy" | "upstream" | "readonly" | "unsupported";
165
+ diagnostics: {
166
+ code: string;
167
+ message: string;
168
+ }[];
169
+ } | undefined;
170
+ componentSemantic?: Record<string, unknown> | undefined;
171
+ };
172
+ };
173
+ getClassNameSource(key: string, routeId?: string): {
174
+ readonly ok: true;
175
+ readonly data: {
176
+ key: string;
177
+ routeId: string;
178
+ filePath: string;
179
+ componentName: string;
180
+ sourceKind: "missing" | "expression" | "stringLiteral";
181
+ attrRaw: string | null;
182
+ valueRaw: string | null;
183
+ attrRange: {
184
+ start: number;
185
+ end: number;
186
+ startLine?: number | undefined;
187
+ startColumn?: number | undefined;
188
+ endLine?: number | undefined;
189
+ endColumn?: number | undefined;
190
+ } | null;
191
+ valueRange: {
192
+ start: number;
193
+ end: number;
194
+ startLine?: number | undefined;
195
+ startColumn?: number | undefined;
196
+ endLine?: number | undefined;
197
+ endColumn?: number | undefined;
198
+ } | null;
199
+ openingElementRange: {
200
+ start: number;
201
+ end: number;
202
+ startLine?: number | undefined;
203
+ startColumn?: number | undefined;
204
+ endLine?: number | undefined;
205
+ endColumn?: number | undefined;
206
+ };
207
+ version: {
208
+ documentVersion: number;
209
+ contentHash: string;
210
+ parserVersion: string;
211
+ };
212
+ diagnostics: {
213
+ code: "missing-class-name" | "unsupported-attribute-name" | "source-locator-warning" | "invalid-new-attr" | "version-conflict" | "write-failed";
214
+ message: string;
215
+ }[];
216
+ styleContext?: {
217
+ revision: string;
218
+ entryCss: {
219
+ path: string;
220
+ content: string;
221
+ hash?: string | undefined;
222
+ };
223
+ stylesheets: {
224
+ path: string;
225
+ content: string;
226
+ hash?: string | undefined;
227
+ }[];
228
+ computedStyle?: Record<string, string> | undefined;
229
+ } | undefined;
230
+ };
231
+ };
232
+ refreshSourceForKey(key: string, routeId?: string): Promise<void>;
233
+ executeOperation(request: Parameters<PreviewSiteEditEngineRuntime["executeOperation"]>[0]): Promise<SiteEditOperationCommandResult>;
234
+ undo(): Promise<{
235
+ ok: false;
236
+ error: {
237
+ code: "NODE_NOT_FOUND" | "ROUTE_NOT_FOUND" | "CAPABILITY_REJECTED" | "CONSTRAINT_VIOLATED" | "INVALID_PARAMS" | "PLAN_FAILED" | "VERSION_STALE" | "AST_PARSE_ERROR" | "UNSUPPORTED_OPERATION" | "LOCATOR_FAILED" | "INVALID_TARGET" | "WRITE_IO_ERROR" | "CONCURRENT_MODIFIED" | "ROLLBACK_FAILED" | "INTERNAL_ERROR";
238
+ message: string;
239
+ };
240
+ data: {
241
+ requestId: string;
242
+ kind: "update-text" | "remove-node" | "insert-child" | "move-node" | "set-class-name-source" | "set-props" | "apply-style-draft";
243
+ target: {
244
+ kind: "node";
245
+ key: string;
246
+ } | {
247
+ kind: "route";
248
+ routeId: string;
249
+ };
250
+ resultVersion: number;
251
+ };
252
+ } | {
253
+ ok: true;
254
+ data: {
255
+ requestId: string;
256
+ kind: "update-text" | "remove-node" | "insert-child" | "move-node" | "set-class-name-source" | "set-props" | "apply-style-draft";
257
+ target: {
258
+ kind: "node";
259
+ key: string;
260
+ } | {
261
+ kind: "route";
262
+ routeId: string;
263
+ };
264
+ resultVersion: number;
265
+ affectedFiles?: string[] | undefined;
266
+ selectionRef?: {
267
+ key: string;
268
+ instanceIndex?: number | undefined;
269
+ instanceCount?: number | undefined;
270
+ } | undefined;
271
+ };
272
+ error?: undefined;
273
+ }>;
274
+ redo(): Promise<{
275
+ ok: false;
276
+ error: {
277
+ code: "NODE_NOT_FOUND" | "ROUTE_NOT_FOUND" | "CAPABILITY_REJECTED" | "CONSTRAINT_VIOLATED" | "INVALID_PARAMS" | "PLAN_FAILED" | "VERSION_STALE" | "AST_PARSE_ERROR" | "UNSUPPORTED_OPERATION" | "LOCATOR_FAILED" | "INVALID_TARGET" | "WRITE_IO_ERROR" | "CONCURRENT_MODIFIED" | "ROLLBACK_FAILED" | "INTERNAL_ERROR";
278
+ message: string;
279
+ };
280
+ data: {
281
+ requestId: string;
282
+ kind: "update-text" | "remove-node" | "insert-child" | "move-node" | "set-class-name-source" | "set-props" | "apply-style-draft";
283
+ target: {
284
+ kind: "node";
285
+ key: string;
286
+ } | {
287
+ kind: "route";
288
+ routeId: string;
289
+ };
290
+ resultVersion: number;
291
+ };
292
+ } | {
293
+ ok: true;
294
+ data: {
295
+ requestId: string;
296
+ kind: "update-text" | "remove-node" | "insert-child" | "move-node" | "set-class-name-source" | "set-props" | "apply-style-draft";
297
+ target: {
298
+ kind: "node";
299
+ key: string;
300
+ } | {
301
+ kind: "route";
302
+ routeId: string;
303
+ };
304
+ resultVersion: number;
305
+ affectedFiles?: string[] | undefined;
306
+ selectionRef?: {
307
+ key: string;
308
+ instanceIndex?: number | undefined;
309
+ instanceCount?: number | undefined;
310
+ } | undefined;
311
+ };
312
+ error?: undefined;
313
+ }>;
314
+ notifyFileChanged(file: string): void;
315
+ subscribe(listener: Parameters<PreviewSiteEditEngineRuntime["subscribe"]>[0]): () => void;
316
+ dispose(): void;
317
+ }
318
+ export declare function createPreviewSiteEditEngineRuntime(options: PreviewSiteEditEngineRuntimeOptions): PreviewSiteEditEngineRuntime;
@@ -0,0 +1,8 @@
1
+ export interface SiteEditProjectFileSystem {
2
+ readFile(file: string): Promise<string>;
3
+ writeFile(file: string, content: string): Promise<void>;
4
+ deleteFile(file: string): Promise<void>;
5
+ exists(file: string): Promise<boolean>;
6
+ getVersion(file: string): number;
7
+ bumpVersion(file: string): number;
8
+ }
@@ -0,0 +1,97 @@
1
+ import type { SiteEditOperationRequest, SiteEditOperationResult, SiteEditOperationType, SiteEditRenderDocument } from "@vcp-prod/contracts";
2
+ export declare const DEFAULT_SITE_EDIT_RUNTIME_READY_TIMEOUT_MS = 1500;
3
+ export declare const SITE_EDIT_RUNTIME_READY_POLL_INTERVAL_MS = 16;
4
+ export declare const SITE_EDIT_RUNTIME_ATTRIBUTES: {
5
+ readonly key: "data-vcp-edit-key";
6
+ readonly parentKey: "data-vcp-edit-parent-key";
7
+ readonly movable: "data-vcp-movable";
8
+ readonly removable: "data-vcp-removable";
9
+ readonly flags: "data-vcp-flags";
10
+ readonly publicUiComponent: "data-vcp-ui-component";
11
+ };
12
+ export type SiteEditRuntimeAttributes = {
13
+ readonly [key in keyof typeof SITE_EDIT_RUNTIME_ATTRIBUTES]: string;
14
+ };
15
+ export type SiteEditRenderDocumentDiff = {
16
+ addedKeys: string[];
17
+ removedKeys: string[];
18
+ retainedKeys: string[];
19
+ changed_parentKeys: string[];
20
+ changedChildOrderKeys: string[];
21
+ };
22
+ export type SiteEditRuntimeElementSnapshot = {
23
+ key: string;
24
+ instance_index?: number;
25
+ instance_count?: number;
26
+ tagName: string;
27
+ sourceKind?: string;
28
+ componentName?: string;
29
+ sourceFile?: string;
30
+ parentKey?: string;
31
+ text_preview?: string;
32
+ attributes: Record<string, string>;
33
+ runtimeFlags: {
34
+ editable: boolean;
35
+ movable: boolean;
36
+ removable: boolean;
37
+ text_editable: boolean;
38
+ container: boolean;
39
+ };
40
+ };
41
+ export type SiteEditRuntimeElementRef = {
42
+ key: string;
43
+ instance_index?: number;
44
+ instance_count?: number;
45
+ };
46
+ export type SiteEditQueryDocument = Pick<Document, "querySelector"> & Partial<Pick<Document, "querySelectorAll">>;
47
+ export type SiteEditRuntimeReadySuccess = {
48
+ ok: true;
49
+ version: number;
50
+ observed_keys: string[];
51
+ check: string;
52
+ };
53
+ export type SiteEditRuntimeReadyFailure = {
54
+ ok: false;
55
+ version: number;
56
+ reason: "missing-root" | "missing-target" | "removed-target-still-present" | "missing-added-key" | "missing-selected-key" | "text-mismatch" | "order-mismatch" | "unsupported-operation" | "timeout";
57
+ check: string;
58
+ message: string;
59
+ observed_keys?: string[];
60
+ };
61
+ export type SiteEditRuntimeReadyResult = SiteEditRuntimeReadySuccess | SiteEditRuntimeReadyFailure;
62
+ export type SiteEditRuntimeReadyInput = {
63
+ routeId: string;
64
+ previous_document: SiteEditRenderDocument;
65
+ next_document: SiteEditRenderDocument;
66
+ request?: SiteEditOperationRequest;
67
+ result: SiteEditOperationResult;
68
+ selectedKey?: string | null;
69
+ timeout_ms?: number;
70
+ };
71
+ export declare function diffSiteEditRenderDocuments(previous_document: SiteEditRenderDocument, next_document: SiteEditRenderDocument): SiteEditRenderDocumentDiff;
72
+ export declare function isSiteEditRuntimeSyncedOperation(kind: SiteEditOperationType): boolean;
73
+ export declare class SiteEditRuntimeDomAdapter {
74
+ private readonly documentLike;
75
+ private readonly attributes;
76
+ constructor(documentLike?: SiteEditQueryDocument | null, attributes?: SiteEditRuntimeAttributes);
77
+ getKeyFromElement(element: Element): string | null;
78
+ findEditableElement(element: Element | null): Element | null;
79
+ findElementByKey(key: string, document?: SiteEditRenderDocument | null): Element | null;
80
+ findElementByRef(ref: SiteEditRuntimeElementRef, document?: SiteEditRenderDocument | null): Element | null;
81
+ snapshot(element: Element): SiteEditRuntimeElementSnapshot;
82
+ private resolveInstancePosition;
83
+ private getKeySelector;
84
+ }
85
+ export declare class SiteEditRuntimeReadyProbe {
86
+ private readonly dom;
87
+ constructor(documentLike: SiteEditQueryDocument, attributes?: SiteEditRuntimeAttributes);
88
+ probe(input: SiteEditRuntimeReadyInput, diff?: SiteEditRenderDocumentDiff): SiteEditRuntimeReadyResult;
89
+ private checkOperationProjection;
90
+ private checkTextProjection;
91
+ private checkMovedNodeProjection;
92
+ private checkGenericDiffProjection;
93
+ private checkAddedKeys;
94
+ private isChildOrderReady;
95
+ }
96
+ export declare function getSiteEditNodeTargetKey(input?: Pick<SiteEditOperationRequest | SiteEditOperationResult, "target">): string | null;
97
+ export declare function hasSiteEditDocumentKey(document: SiteEditRenderDocument, key: string): boolean;
@@ -0,0 +1,222 @@
1
+ import type { SiteEditEngineRuntime, SiteEditEngineRuntimeOptions, SiteEditPlanOperationResult } from "./types.js";
2
+ export declare class SnapshotSiteEditEngineRuntime implements SiteEditEngineRuntime {
3
+ private readonly options;
4
+ private readonly engine;
5
+ private readonly fileSystem;
6
+ constructor(options: SiteEditEngineRuntimeOptions);
7
+ get status(): SiteEditEngineRuntime["status"];
8
+ setActiveRoute(routeId: string): Promise<void>;
9
+ getDocument(routeId: string): {
10
+ siteId: string;
11
+ snapshotId: string;
12
+ routeId: string;
13
+ version: number;
14
+ rootKeys: string[];
15
+ entries: {
16
+ key: string;
17
+ tag: string;
18
+ label: string;
19
+ parentKey: string | null;
20
+ childKeys: string[];
21
+ operationSummary: {
22
+ canUpdateText: boolean;
23
+ canInsertChild: boolean;
24
+ canMove: boolean;
25
+ canRemove: boolean;
26
+ };
27
+ }[];
28
+ };
29
+ getObjectSummary(key: string, routeId?: string): {
30
+ key: string;
31
+ tag: string;
32
+ label: string;
33
+ capabilities: {
34
+ constraints: {
35
+ kind: "component-boundary" | "repeat-region" | "conditional-region" | "opaque-region" | "void-element" | "read-only" | "cross-file-required" | "import-required";
36
+ message: string;
37
+ }[];
38
+ };
39
+ isOpaque: boolean;
40
+ ancestors: {
41
+ key: string;
42
+ label: string;
43
+ tag: string;
44
+ }[];
45
+ sourceLocator?: {
46
+ sourceFile: string;
47
+ componentName: string;
48
+ openingElementRange: {
49
+ startLine: number;
50
+ startColumn: number;
51
+ endLine: number;
52
+ endColumn: number;
53
+ };
54
+ structuralPath: string;
55
+ textPreview?: string | undefined;
56
+ } | undefined;
57
+ provenanceChain?: {
58
+ editMode: "direct" | "proxy" | "upstream" | "readonly" | "unsupported";
59
+ diagnostics: {
60
+ code: string;
61
+ message: string;
62
+ }[];
63
+ } | undefined;
64
+ };
65
+ getObjectEditContext(key: string, routeId?: string): {
66
+ key: string;
67
+ componentName: string;
68
+ sourceFile: string;
69
+ capabilities: {
70
+ key: string;
71
+ canUpdateText: boolean;
72
+ canInsertChild: boolean;
73
+ canMove: boolean;
74
+ canRemove: boolean;
75
+ constraints: {
76
+ kind: "component-boundary" | "repeat-region" | "conditional-region" | "opaque-region" | "void-element" | "read-only" | "cross-file-required" | "import-required";
77
+ message: string;
78
+ }[];
79
+ editModes?: {
80
+ updateText?: {
81
+ mode: "direct" | "proxy" | "upstream" | "readonly" | "unsupported";
82
+ reasonCode?: string | undefined;
83
+ } | undefined;
84
+ insertChild?: {
85
+ mode: "direct" | "proxy" | "upstream" | "readonly" | "unsupported";
86
+ reasonCode?: string | undefined;
87
+ } | undefined;
88
+ move?: {
89
+ mode: "direct" | "proxy" | "upstream" | "readonly" | "unsupported";
90
+ reasonCode?: string | undefined;
91
+ } | undefined;
92
+ remove?: {
93
+ mode: "direct" | "proxy" | "upstream" | "readonly" | "unsupported";
94
+ reasonCode?: string | undefined;
95
+ } | undefined;
96
+ } | undefined;
97
+ };
98
+ writeTarget: {
99
+ kind: "jsx-node" | "component-proxy" | "value-binding" | "route-export";
100
+ file: string;
101
+ componentName: string;
102
+ isProxy: boolean;
103
+ };
104
+ textSegments: {
105
+ index: number;
106
+ value: string;
107
+ editable: boolean;
108
+ source: {
109
+ kind: "literal" | "binding" | "imported-binding" | "repeat-template";
110
+ file: string;
111
+ expression: string;
112
+ bindingName?: string | undefined;
113
+ path?: (string | number)[] | undefined;
114
+ } | null;
115
+ }[];
116
+ boundaryKind: "component-boundary" | "repeat-region" | "conditional-region" | "fragment-region" | "opaque-region" | null;
117
+ children: {
118
+ key: string;
119
+ label: string;
120
+ tag: string;
121
+ }[];
122
+ siblings: {
123
+ key: string;
124
+ label: string;
125
+ tag: string;
126
+ }[];
127
+ effectiveWriteTarget?: {
128
+ kind: "jsx-node" | "route-export" | "value-path" | "external-entry";
129
+ isProxy: boolean;
130
+ file?: string | undefined;
131
+ displayPath?: string | undefined;
132
+ sourceType?: "api-field" | "cms-field" | "i18n-message" | "config-entry" | undefined;
133
+ sourceId?: string | undefined;
134
+ } | undefined;
135
+ provenanceChain?: {
136
+ finalSource: {
137
+ kind: "api-field" | "cms-field" | "i18n-message" | "config-entry" | "binding" | "imported-binding" | "repeat-template" | "jsx-literal" | "component-prop" | "object-field" | "array-item" | "conditional-branch";
138
+ file: string;
139
+ displayPath: string;
140
+ externalSource?: {
141
+ sourceType: "api-field" | "cms-field" | "i18n-message" | "config-entry";
142
+ sourceId: string;
143
+ adapterId?: string | undefined;
144
+ } | undefined;
145
+ } | null;
146
+ chain: {
147
+ kind: "api-field" | "cms-field" | "i18n-message" | "config-entry" | "binding" | "imported-binding" | "repeat-template" | "jsx-literal" | "component-prop" | "object-field" | "array-item" | "conditional-branch";
148
+ file: string;
149
+ displayName: string;
150
+ canEditHere: boolean;
151
+ }[];
152
+ confidence: "exact" | "safe-derived" | "partial" | "unknown";
153
+ editMode: "direct" | "proxy" | "upstream" | "readonly" | "unsupported";
154
+ diagnostics: {
155
+ code: string;
156
+ message: string;
157
+ }[];
158
+ } | undefined;
159
+ componentSemantic?: Record<string, unknown> | undefined;
160
+ };
161
+ getClassNameSource(key: string, routeId?: string): {
162
+ key: string;
163
+ routeId: string;
164
+ filePath: string;
165
+ componentName: string;
166
+ sourceKind: "missing" | "expression" | "stringLiteral";
167
+ attrRaw: string | null;
168
+ valueRaw: string | null;
169
+ attrRange: {
170
+ start: number;
171
+ end: number;
172
+ startLine?: number | undefined;
173
+ startColumn?: number | undefined;
174
+ endLine?: number | undefined;
175
+ endColumn?: number | undefined;
176
+ } | null;
177
+ valueRange: {
178
+ start: number;
179
+ end: number;
180
+ startLine?: number | undefined;
181
+ startColumn?: number | undefined;
182
+ endLine?: number | undefined;
183
+ endColumn?: number | undefined;
184
+ } | null;
185
+ openingElementRange: {
186
+ start: number;
187
+ end: number;
188
+ startLine?: number | undefined;
189
+ startColumn?: number | undefined;
190
+ endLine?: number | undefined;
191
+ endColumn?: number | undefined;
192
+ };
193
+ version: {
194
+ documentVersion: number;
195
+ contentHash: string;
196
+ parserVersion: string;
197
+ };
198
+ diagnostics: {
199
+ code: "missing-class-name" | "unsupported-attribute-name" | "source-locator-warning" | "invalid-new-attr" | "version-conflict" | "write-failed";
200
+ message: string;
201
+ }[];
202
+ styleContext?: {
203
+ revision: string;
204
+ entryCss: {
205
+ path: string;
206
+ content: string;
207
+ hash?: string | undefined;
208
+ };
209
+ stylesheets: {
210
+ path: string;
211
+ content: string;
212
+ hash?: string | undefined;
213
+ }[];
214
+ computedStyle?: Record<string, string> | undefined;
215
+ } | undefined;
216
+ };
217
+ planOperation(request: Parameters<SiteEditEngineRuntime["planOperation"]>[0]): Promise<SiteEditPlanOperationResult>;
218
+ dispose(): void;
219
+ private createEngine;
220
+ private getChangedRouteIds;
221
+ }
222
+ export declare function createSiteEditEngineRuntime(options: SiteEditEngineRuntimeOptions): SiteEditEngineRuntime;