@archie/devtools 0.0.35 → 0.0.36

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.
@@ -4085,6 +4085,46 @@ function DragOverlay2() {
4085
4085
  return /* @__PURE__ */ (0, import_jsx_runtime.jsx)(DragOverlay, { dropAnimation: null, children: renderContent() });
4086
4086
  }
4087
4087
 
4088
+ // src/client/dnd/design-mode/debug-trace.ts
4089
+ var MAX_ENTRIES = 800;
4090
+ function traceWindow() {
4091
+ return typeof window === "undefined" ? null : window;
4092
+ }
4093
+ function isVeDebugEnabled() {
4094
+ const w = traceWindow();
4095
+ if (!w) return false;
4096
+ if (w.__ARCHIE_VE_DEBUG__ === true || w._inspectorDebug === true) return true;
4097
+ try {
4098
+ return w.localStorage?.getItem("ARCHIE_VE_DEBUG") === "1";
4099
+ } catch {
4100
+ return false;
4101
+ }
4102
+ }
4103
+ function veTrace(layer, event, data) {
4104
+ const w = traceWindow();
4105
+ if (!w) return;
4106
+ let resolved;
4107
+ if (typeof data === "function") {
4108
+ try {
4109
+ resolved = data();
4110
+ } catch (error) {
4111
+ resolved = { __traceDataError: String(error) };
4112
+ }
4113
+ } else {
4114
+ resolved = data;
4115
+ }
4116
+ const entry = { t: Date.now(), layer, event, ...resolved === void 0 ? {} : { data: resolved } };
4117
+ const buffer = w.__ARCHIE_VE_TRACE__ ?? (w.__ARCHIE_VE_TRACE__ = []);
4118
+ buffer.push(entry);
4119
+ if (buffer.length > MAX_ENTRIES) buffer.splice(0, buffer.length - MAX_ENTRIES);
4120
+ if (!w.__ARCHIE_VE_TRACE_DUMP__) {
4121
+ w.__ARCHIE_VE_TRACE_DUMP__ = () => JSON.stringify(w.__ARCHIE_VE_TRACE__ ?? []);
4122
+ }
4123
+ if (isVeDebugEnabled()) {
4124
+ console.log(`[archie-ve:${layer}]`, event, resolved ?? "");
4125
+ }
4126
+ }
4127
+
4088
4128
  // src/client/dnd/design-mode/host-bridge.ts
4089
4129
  var DEFAULT_INSPECTOR_THEME = {
4090
4130
  accent: "#8b5cf6",
@@ -4094,8 +4134,80 @@ var DEFAULT_INSPECTOR_THEME = {
4094
4134
  };
4095
4135
  var HOST_COMMAND_EVENT = "archie:editor-host-command";
4096
4136
  var DND_RUNTIME_EVENT = "archie:dnd-runtime-event";
4137
+ function summarizeIdentity(identity2) {
4138
+ if (!identity2) return null;
4139
+ return {
4140
+ nodeId: identity2.nodeId,
4141
+ nodeKey: identity2.nodeKey,
4142
+ ref: identity2.inspectorRef ? `${identity2.inspectorRef.relativePath}:${identity2.inspectorRef.line}:${identity2.inspectorRef.column}` : null,
4143
+ ...identity2.effectiveNodeId && identity2.effectiveNodeId !== identity2.nodeId ? { effectiveNodeId: identity2.effectiveNodeId } : {}
4144
+ };
4145
+ }
4146
+ function summarizeRuntimeEvent(detail) {
4147
+ switch (detail.type) {
4148
+ case "element-moved":
4149
+ return {
4150
+ operationId: detail.operationId,
4151
+ commandType: detail.commandType,
4152
+ selected: summarizeIdentity(detail.selected),
4153
+ anchor: summarizeIdentity(detail.anchor),
4154
+ container: summarizeIdentity(detail.container),
4155
+ beforeSibling: summarizeIdentity(detail.beforeSibling),
4156
+ sourceContainer: summarizeIdentity(detail.sourceContainer),
4157
+ diagnostics: detail.diagnostics ?? null
4158
+ };
4159
+ case "element-resized":
4160
+ return {
4161
+ operationId: detail.operationId,
4162
+ selected: summarizeIdentity(detail.selected),
4163
+ anchor: summarizeIdentity(detail.anchor),
4164
+ resize: {
4165
+ mode: detail.resize.mode,
4166
+ selectedNodeKey: detail.resize.selectedNodeKey,
4167
+ targetNodeKey: detail.resize.targetNodeKey,
4168
+ targetNodeId: detail.resize.targetNodeId,
4169
+ width: detail.resize.width,
4170
+ height: detail.resize.height
4171
+ }
4172
+ };
4173
+ case "element-inserted":
4174
+ return {
4175
+ operationId: detail.operationId,
4176
+ nodeId: detail.nodeId,
4177
+ nodeKey: detail.nodeKey,
4178
+ displayName: detail.displayName,
4179
+ container: summarizeIdentity(detail.container),
4180
+ index: detail.index,
4181
+ beforeSibling: summarizeIdentity(detail.beforeSibling),
4182
+ hasTsxCode: !!detail.tsxCode,
4183
+ htmlLength: detail.html?.length ?? 0
4184
+ };
4185
+ case "arrange-session-changed":
4186
+ return {
4187
+ mode: detail.session.mode,
4188
+ canUndo: detail.session.canUndo,
4189
+ changeCount: detail.session.changes.length,
4190
+ changes: detail.session.changes.map((c) => ({
4191
+ id: c.id,
4192
+ kind: c.kind,
4193
+ operationId: c.operationId,
4194
+ nodeKey: c.nodeKey,
4195
+ ref: c.inspectorRef ? `${c.inspectorRef.relativePath}:${c.inspectorRef.line}:${c.inspectorRef.column}` : null
4196
+ }))
4197
+ };
4198
+ case "arrange-undo-applied":
4199
+ return { success: detail.success, updatedAt: detail.updatedAt };
4200
+ case "design-mode-changed":
4201
+ return { mode: detail.mode };
4202
+ case "design-mode-error":
4203
+ return { error: detail.error };
4204
+ default:
4205
+ return null;
4206
+ }
4207
+ }
4097
4208
  function dispatchRuntimeEvent(detail) {
4098
4209
  if (typeof window === "undefined") return;
4210
+ veTrace("dnd", `runtime-event:${detail.type}`, () => summarizeRuntimeEvent(detail));
4099
4211
  window.dispatchEvent(new CustomEvent(DND_RUNTIME_EVENT, { detail }));
4100
4212
  }
4101
4213
  function resolveRowBinding(el) {
@@ -8196,8 +8308,23 @@ function useDragLifecycle({
8196
8308
  if (refs.resizeSessionRef.current || Date.now() < refs.resizeDragBlockUntilRef.current) return;
8197
8309
  const activeId = active.id;
8198
8310
  const found = refs.draggableNodeMapRef.current.get(activeId) ?? refs.nodeMapRef.current.get(activeId);
8199
- if (!found) return;
8200
- if (!isEligibleForDrag(found)) return;
8311
+ if (!found) {
8312
+ veTrace("dnd", "drag:start-rejected", { nodeId: activeId, reason: "not-scanned" });
8313
+ return;
8314
+ }
8315
+ if (!isEligibleForDrag(found)) {
8316
+ veTrace("dnd", "drag:start-rejected", {
8317
+ nodeId: activeId,
8318
+ reason: "not-eligible",
8319
+ eligibilitySource: found.eligibilitySource ?? "editor-meta",
8320
+ draggable: found.draggable
8321
+ });
8322
+ return;
8323
+ }
8324
+ veTrace("dnd", "drag:start", {
8325
+ nodeId: activeId,
8326
+ eligibilitySource: found.eligibilitySource ?? "editor-meta"
8327
+ });
8201
8328
  refs.lastIntentRef.current = null;
8202
8329
  refs.visualIntentRef.current = null;
8203
8330
  refs.targetPlaneRef.current = "lane";
@@ -8256,6 +8383,16 @@ function useDragLifecycle({
8256
8383
  const pointer = refs.mouseRef.current;
8257
8384
  const safeZone = refs.safeZoneRef.current;
8258
8385
  const blockedByGuard = isPointerOutsideSafeZone(pointer.x, pointer.y, safeZone) || isPointerInHardPageEdgeZone(pointer.x, pointer.y);
8386
+ veTrace("dnd", "drag:end", () => ({
8387
+ selectedNodeId,
8388
+ anchorNodeId,
8389
+ blockedByGuard,
8390
+ intent: refs.visualIntentRef.current ? {
8391
+ mode: refs.visualIntentRef.current.mode,
8392
+ containerId: refs.visualIntentRef.current.containerId,
8393
+ index: refs.visualIntentRef.current.index
8394
+ } : null
8395
+ }));
8259
8396
  let sourcePos = refs.dragStartPositionRef.current ?? getCurrentCommitPlacement(anchorNodeId, refs.sourceContainerIdRef.current);
8260
8397
  if (!sourcePos && activeEl && activeEl.parentElement) {
8261
8398
  const parentEl = activeEl.parentElement;
@@ -8354,6 +8491,7 @@ function useDragLifecycle({
8354
8491
  syncHistoryAvailability();
8355
8492
  }, [applyCommand, classifyCommandType, clearDragState, getCurrentCommitPlacement, recordMoveChange, resolveNodeElement, selectElement, syncHistoryAvailability]);
8356
8493
  const handleDragCancel = (0, import_react13.useCallback)(() => {
8494
+ veTrace("dnd", "drag:cancel");
8357
8495
  clearDragState();
8358
8496
  }, [clearDragState]);
8359
8497
  return { activeDrag, handleDragStart, handleDragEnd, handleDragCancel };
@@ -8415,6 +8553,17 @@ function useResizeSession({
8415
8553
  beforeStyles,
8416
8554
  hasMoved: false
8417
8555
  };
8556
+ veTrace("dnd", "resize:start", {
8557
+ dir,
8558
+ mode,
8559
+ selectedNodeId: nodeId,
8560
+ selectedNodeKey,
8561
+ targetNodeId,
8562
+ targetNodeKey,
8563
+ retargeted: resizeTargetEl !== selectedEl,
8564
+ startW: Math.round(rect.width),
8565
+ startH: Math.round(rect.height)
8566
+ });
8418
8567
  pointerTarget?.setPointerCapture?.(e.pointerId);
8419
8568
  }, []);
8420
8569
  const handleResizePointerMove = (0, import_react14.useCallback)((e) => {
@@ -8477,6 +8626,7 @@ function useResizeSession({
8477
8626
  const afterStyles = readStyleSnapshot(element, ["width", "height", "grid-column", "grid-column-end", "grid-row", "grid-row-end"]);
8478
8627
  const unchanged = mode === "grid-span" ? afterColSpan === startColSpan && afterRowSpan === startRowSpan : afterW === Math.round(startW) && afterH === Math.round(startH);
8479
8628
  if (unchanged) {
8629
+ veTrace("dnd", "resize:noop", { selectedNodeId, targetNodeId });
8480
8630
  syncHistoryAvailability();
8481
8631
  return;
8482
8632
  }
@@ -8538,6 +8688,10 @@ function useResizeSession({
8538
8688
  const session = refs.resizeSessionRef.current;
8539
8689
  if (!session || session.pointerId !== e.pointerId) return;
8540
8690
  if (session.pointerTarget?.hasPointerCapture?.(e.pointerId)) session.pointerTarget.releasePointerCapture(e.pointerId);
8691
+ veTrace("dnd", "resize:cancel", {
8692
+ selectedNodeId: session.selectedNodeId,
8693
+ targetNodeId: session.targetNodeId
8694
+ });
8541
8695
  for (const [prop, value] of Object.entries(session.beforeStyles)) {
8542
8696
  if (value === null) session.element.style.removeProperty(prop);
8543
8697
  else session.element.style.setProperty(prop, value);
@@ -9328,6 +9482,13 @@ function DndProvider({ children }) {
9328
9482
  const handleHostCommand = (event) => {
9329
9483
  const detail = event.detail;
9330
9484
  if (!detail || typeof detail !== "object") return;
9485
+ if (detail.type !== "external-drag-move") {
9486
+ veTrace(
9487
+ "dnd",
9488
+ `host-command:${detail.type}`,
9489
+ () => detail.type === "external-drag-start" ? { displayName: detail.component.displayName, category: detail.component.category } : detail.type === "sync-editor-state" ? { mode: detail.mode ?? null, historyMode: detail.historyMode ?? null } : detail.type === "set-design-mode" ? { enabled: detail.enabled } : void 0
9490
+ );
9491
+ }
9331
9492
  switch (detail.type) {
9332
9493
  case "sync-editor-state":
9333
9494
  if (detail.mode === "design") {
@@ -4050,6 +4050,46 @@ function DragOverlay2() {
4050
4050
  return /* @__PURE__ */ jsx(DragOverlay, { dropAnimation: null, children: renderContent() });
4051
4051
  }
4052
4052
 
4053
+ // src/client/dnd/design-mode/debug-trace.ts
4054
+ var MAX_ENTRIES = 800;
4055
+ function traceWindow() {
4056
+ return typeof window === "undefined" ? null : window;
4057
+ }
4058
+ function isVeDebugEnabled() {
4059
+ const w = traceWindow();
4060
+ if (!w) return false;
4061
+ if (w.__ARCHIE_VE_DEBUG__ === true || w._inspectorDebug === true) return true;
4062
+ try {
4063
+ return w.localStorage?.getItem("ARCHIE_VE_DEBUG") === "1";
4064
+ } catch {
4065
+ return false;
4066
+ }
4067
+ }
4068
+ function veTrace(layer, event, data) {
4069
+ const w = traceWindow();
4070
+ if (!w) return;
4071
+ let resolved;
4072
+ if (typeof data === "function") {
4073
+ try {
4074
+ resolved = data();
4075
+ } catch (error) {
4076
+ resolved = { __traceDataError: String(error) };
4077
+ }
4078
+ } else {
4079
+ resolved = data;
4080
+ }
4081
+ const entry = { t: Date.now(), layer, event, ...resolved === void 0 ? {} : { data: resolved } };
4082
+ const buffer = w.__ARCHIE_VE_TRACE__ ?? (w.__ARCHIE_VE_TRACE__ = []);
4083
+ buffer.push(entry);
4084
+ if (buffer.length > MAX_ENTRIES) buffer.splice(0, buffer.length - MAX_ENTRIES);
4085
+ if (!w.__ARCHIE_VE_TRACE_DUMP__) {
4086
+ w.__ARCHIE_VE_TRACE_DUMP__ = () => JSON.stringify(w.__ARCHIE_VE_TRACE__ ?? []);
4087
+ }
4088
+ if (isVeDebugEnabled()) {
4089
+ console.log(`[archie-ve:${layer}]`, event, resolved ?? "");
4090
+ }
4091
+ }
4092
+
4053
4093
  // src/client/dnd/design-mode/host-bridge.ts
4054
4094
  var DEFAULT_INSPECTOR_THEME = {
4055
4095
  accent: "#8b5cf6",
@@ -4059,8 +4099,80 @@ var DEFAULT_INSPECTOR_THEME = {
4059
4099
  };
4060
4100
  var HOST_COMMAND_EVENT = "archie:editor-host-command";
4061
4101
  var DND_RUNTIME_EVENT = "archie:dnd-runtime-event";
4102
+ function summarizeIdentity(identity2) {
4103
+ if (!identity2) return null;
4104
+ return {
4105
+ nodeId: identity2.nodeId,
4106
+ nodeKey: identity2.nodeKey,
4107
+ ref: identity2.inspectorRef ? `${identity2.inspectorRef.relativePath}:${identity2.inspectorRef.line}:${identity2.inspectorRef.column}` : null,
4108
+ ...identity2.effectiveNodeId && identity2.effectiveNodeId !== identity2.nodeId ? { effectiveNodeId: identity2.effectiveNodeId } : {}
4109
+ };
4110
+ }
4111
+ function summarizeRuntimeEvent(detail) {
4112
+ switch (detail.type) {
4113
+ case "element-moved":
4114
+ return {
4115
+ operationId: detail.operationId,
4116
+ commandType: detail.commandType,
4117
+ selected: summarizeIdentity(detail.selected),
4118
+ anchor: summarizeIdentity(detail.anchor),
4119
+ container: summarizeIdentity(detail.container),
4120
+ beforeSibling: summarizeIdentity(detail.beforeSibling),
4121
+ sourceContainer: summarizeIdentity(detail.sourceContainer),
4122
+ diagnostics: detail.diagnostics ?? null
4123
+ };
4124
+ case "element-resized":
4125
+ return {
4126
+ operationId: detail.operationId,
4127
+ selected: summarizeIdentity(detail.selected),
4128
+ anchor: summarizeIdentity(detail.anchor),
4129
+ resize: {
4130
+ mode: detail.resize.mode,
4131
+ selectedNodeKey: detail.resize.selectedNodeKey,
4132
+ targetNodeKey: detail.resize.targetNodeKey,
4133
+ targetNodeId: detail.resize.targetNodeId,
4134
+ width: detail.resize.width,
4135
+ height: detail.resize.height
4136
+ }
4137
+ };
4138
+ case "element-inserted":
4139
+ return {
4140
+ operationId: detail.operationId,
4141
+ nodeId: detail.nodeId,
4142
+ nodeKey: detail.nodeKey,
4143
+ displayName: detail.displayName,
4144
+ container: summarizeIdentity(detail.container),
4145
+ index: detail.index,
4146
+ beforeSibling: summarizeIdentity(detail.beforeSibling),
4147
+ hasTsxCode: !!detail.tsxCode,
4148
+ htmlLength: detail.html?.length ?? 0
4149
+ };
4150
+ case "arrange-session-changed":
4151
+ return {
4152
+ mode: detail.session.mode,
4153
+ canUndo: detail.session.canUndo,
4154
+ changeCount: detail.session.changes.length,
4155
+ changes: detail.session.changes.map((c) => ({
4156
+ id: c.id,
4157
+ kind: c.kind,
4158
+ operationId: c.operationId,
4159
+ nodeKey: c.nodeKey,
4160
+ ref: c.inspectorRef ? `${c.inspectorRef.relativePath}:${c.inspectorRef.line}:${c.inspectorRef.column}` : null
4161
+ }))
4162
+ };
4163
+ case "arrange-undo-applied":
4164
+ return { success: detail.success, updatedAt: detail.updatedAt };
4165
+ case "design-mode-changed":
4166
+ return { mode: detail.mode };
4167
+ case "design-mode-error":
4168
+ return { error: detail.error };
4169
+ default:
4170
+ return null;
4171
+ }
4172
+ }
4062
4173
  function dispatchRuntimeEvent(detail) {
4063
4174
  if (typeof window === "undefined") return;
4175
+ veTrace("dnd", `runtime-event:${detail.type}`, () => summarizeRuntimeEvent(detail));
4064
4176
  window.dispatchEvent(new CustomEvent(DND_RUNTIME_EVENT, { detail }));
4065
4177
  }
4066
4178
  function resolveRowBinding(el) {
@@ -8161,8 +8273,23 @@ function useDragLifecycle({
8161
8273
  if (refs.resizeSessionRef.current || Date.now() < refs.resizeDragBlockUntilRef.current) return;
8162
8274
  const activeId = active.id;
8163
8275
  const found = refs.draggableNodeMapRef.current.get(activeId) ?? refs.nodeMapRef.current.get(activeId);
8164
- if (!found) return;
8165
- if (!isEligibleForDrag(found)) return;
8276
+ if (!found) {
8277
+ veTrace("dnd", "drag:start-rejected", { nodeId: activeId, reason: "not-scanned" });
8278
+ return;
8279
+ }
8280
+ if (!isEligibleForDrag(found)) {
8281
+ veTrace("dnd", "drag:start-rejected", {
8282
+ nodeId: activeId,
8283
+ reason: "not-eligible",
8284
+ eligibilitySource: found.eligibilitySource ?? "editor-meta",
8285
+ draggable: found.draggable
8286
+ });
8287
+ return;
8288
+ }
8289
+ veTrace("dnd", "drag:start", {
8290
+ nodeId: activeId,
8291
+ eligibilitySource: found.eligibilitySource ?? "editor-meta"
8292
+ });
8166
8293
  refs.lastIntentRef.current = null;
8167
8294
  refs.visualIntentRef.current = null;
8168
8295
  refs.targetPlaneRef.current = "lane";
@@ -8221,6 +8348,16 @@ function useDragLifecycle({
8221
8348
  const pointer = refs.mouseRef.current;
8222
8349
  const safeZone = refs.safeZoneRef.current;
8223
8350
  const blockedByGuard = isPointerOutsideSafeZone(pointer.x, pointer.y, safeZone) || isPointerInHardPageEdgeZone(pointer.x, pointer.y);
8351
+ veTrace("dnd", "drag:end", () => ({
8352
+ selectedNodeId,
8353
+ anchorNodeId,
8354
+ blockedByGuard,
8355
+ intent: refs.visualIntentRef.current ? {
8356
+ mode: refs.visualIntentRef.current.mode,
8357
+ containerId: refs.visualIntentRef.current.containerId,
8358
+ index: refs.visualIntentRef.current.index
8359
+ } : null
8360
+ }));
8224
8361
  let sourcePos = refs.dragStartPositionRef.current ?? getCurrentCommitPlacement(anchorNodeId, refs.sourceContainerIdRef.current);
8225
8362
  if (!sourcePos && activeEl && activeEl.parentElement) {
8226
8363
  const parentEl = activeEl.parentElement;
@@ -8319,6 +8456,7 @@ function useDragLifecycle({
8319
8456
  syncHistoryAvailability();
8320
8457
  }, [applyCommand, classifyCommandType, clearDragState, getCurrentCommitPlacement, recordMoveChange, resolveNodeElement, selectElement, syncHistoryAvailability]);
8321
8458
  const handleDragCancel = useCallback6(() => {
8459
+ veTrace("dnd", "drag:cancel");
8322
8460
  clearDragState();
8323
8461
  }, [clearDragState]);
8324
8462
  return { activeDrag, handleDragStart, handleDragEnd, handleDragCancel };
@@ -8380,6 +8518,17 @@ function useResizeSession({
8380
8518
  beforeStyles,
8381
8519
  hasMoved: false
8382
8520
  };
8521
+ veTrace("dnd", "resize:start", {
8522
+ dir,
8523
+ mode,
8524
+ selectedNodeId: nodeId,
8525
+ selectedNodeKey,
8526
+ targetNodeId,
8527
+ targetNodeKey,
8528
+ retargeted: resizeTargetEl !== selectedEl,
8529
+ startW: Math.round(rect.width),
8530
+ startH: Math.round(rect.height)
8531
+ });
8383
8532
  pointerTarget?.setPointerCapture?.(e.pointerId);
8384
8533
  }, []);
8385
8534
  const handleResizePointerMove = useCallback7((e) => {
@@ -8442,6 +8591,7 @@ function useResizeSession({
8442
8591
  const afterStyles = readStyleSnapshot(element, ["width", "height", "grid-column", "grid-column-end", "grid-row", "grid-row-end"]);
8443
8592
  const unchanged = mode === "grid-span" ? afterColSpan === startColSpan && afterRowSpan === startRowSpan : afterW === Math.round(startW) && afterH === Math.round(startH);
8444
8593
  if (unchanged) {
8594
+ veTrace("dnd", "resize:noop", { selectedNodeId, targetNodeId });
8445
8595
  syncHistoryAvailability();
8446
8596
  return;
8447
8597
  }
@@ -8503,6 +8653,10 @@ function useResizeSession({
8503
8653
  const session = refs.resizeSessionRef.current;
8504
8654
  if (!session || session.pointerId !== e.pointerId) return;
8505
8655
  if (session.pointerTarget?.hasPointerCapture?.(e.pointerId)) session.pointerTarget.releasePointerCapture(e.pointerId);
8656
+ veTrace("dnd", "resize:cancel", {
8657
+ selectedNodeId: session.selectedNodeId,
8658
+ targetNodeId: session.targetNodeId
8659
+ });
8506
8660
  for (const [prop, value] of Object.entries(session.beforeStyles)) {
8507
8661
  if (value === null) session.element.style.removeProperty(prop);
8508
8662
  else session.element.style.setProperty(prop, value);
@@ -9293,6 +9447,13 @@ function DndProvider({ children }) {
9293
9447
  const handleHostCommand = (event) => {
9294
9448
  const detail = event.detail;
9295
9449
  if (!detail || typeof detail !== "object") return;
9450
+ if (detail.type !== "external-drag-move") {
9451
+ veTrace(
9452
+ "dnd",
9453
+ `host-command:${detail.type}`,
9454
+ () => detail.type === "external-drag-start" ? { displayName: detail.component.displayName, category: detail.component.category } : detail.type === "sync-editor-state" ? { mode: detail.mode ?? null, historyMode: detail.historyMode ?? null } : detail.type === "set-design-mode" ? { enabled: detail.enabled } : void 0
9455
+ );
9456
+ }
9296
9457
  switch (detail.type) {
9297
9458
  case "sync-editor-state":
9298
9459
  if (detail.mode === "design") {
@@ -1258,6 +1258,11 @@
1258
1258
  // make this redundant for new indexes, but an already-built index may
1259
1259
  // still hold a stale group.)
1260
1260
  if (isInsertedSubtreeElement(inspectTarget)) {
1261
+ veTrace("shared-targets", {
1262
+ via: "inserted-subtree",
1263
+ count: 1,
1264
+ nodeId: inspectTarget.getAttribute("data-dnd-node-id") || null,
1265
+ })
1261
1266
  return [inspectTarget]
1262
1267
  }
1263
1268
 
@@ -1268,14 +1273,32 @@
1268
1273
  inspectTarget,
1269
1274
  sharedTargetIndex.sharedBySignature.get(signature) || []
1270
1275
  )
1271
- if (sharedTargets.length > 0) return sharedTargets
1276
+ if (sharedTargets.length > 0) {
1277
+ veTrace("shared-targets", {
1278
+ via: "signature",
1279
+ signature: String(signature).slice(0, 160),
1280
+ count: sharedTargets.length,
1281
+ nodeId: inspectTarget.getAttribute("data-dnd-node-id") || null,
1282
+ })
1283
+ return sharedTargets
1284
+ }
1272
1285
  }
1273
1286
 
1274
1287
  var legacyTargets = resolveLegacySharedTargets(inspectTarget)
1275
1288
  if (legacyTargets.length > 0) {
1289
+ veTrace("shared-targets", {
1290
+ via: "legacy",
1291
+ count: legacyTargets.length,
1292
+ nodeId: inspectTarget.getAttribute("data-dnd-node-id") || null,
1293
+ })
1276
1294
  return legacyTargets
1277
1295
  }
1278
1296
 
1297
+ veTrace("shared-targets", {
1298
+ via: "self-only",
1299
+ count: 1,
1300
+ nodeId: inspectTarget.getAttribute("data-dnd-node-id") || null,
1301
+ })
1279
1302
  return [inspectTarget]
1280
1303
  }
1281
1304
 
@@ -1379,10 +1402,24 @@
1379
1402
 
1380
1403
  syncBridgeStateFromWindow()
1381
1404
  if (!bridgeState.targetOrigin || bridgeState.targetOrigin === "*") {
1405
+ if (msg && msg.type && msg.type !== "ELEMENT_POSITION_UPDATE") {
1406
+ veTrace("out:" + msg.type + ":queued", {
1407
+ requestId: (msg && msg.requestId) || null,
1408
+ })
1409
+ }
1382
1410
  bridgeState.pendingParentMessages.push(msg)
1383
1411
  return
1384
1412
  }
1385
1413
 
1414
+ if (msg && msg.type && msg.type !== "ELEMENT_POSITION_UPDATE") {
1415
+ veTrace("out:" + msg.type, {
1416
+ requestId: (msg && msg.requestId) || null,
1417
+ operationId:
1418
+ (msg && msg.operationId) ||
1419
+ (msg && msg.payload && msg.payload.operationId) ||
1420
+ null,
1421
+ })
1422
+ }
1386
1423
  window.parent.postMessage(msg, bridgeState.targetOrigin)
1387
1424
  }
1388
1425
 
@@ -1455,6 +1492,41 @@
1455
1492
  }
1456
1493
  }
1457
1494
 
1495
+ /**
1496
+ * Always-on trace ring buffer, shared shape with the design-mode engine
1497
+ * (`debug-trace.ts`): reproduce a broken gesture, then read
1498
+ * `window.__ARCHIE_VE_TRACE__` / `window.__ARCHIE_VE_TRACE_DUMP__()` in
1499
+ * THIS frame's console. Console echo only with `_inspectorDebug` /
1500
+ * `__ARCHIE_VE_DEBUG__`. Payloads must be small summaries — ids, types,
1501
+ * refs — never elements or full HTML.
1502
+ */
1503
+ var VE_TRACE_MAX = 800
1504
+ function veTrace(event, data) {
1505
+ try {
1506
+ var buffer = window.__ARCHIE_VE_TRACE__
1507
+ if (!buffer) {
1508
+ buffer = window.__ARCHIE_VE_TRACE__ = []
1509
+ }
1510
+ var entry = { t: Date.now(), layer: "inspector", event: event }
1511
+ if (typeof data !== "undefined") entry.data = data
1512
+ buffer.push(entry)
1513
+ if (buffer.length > VE_TRACE_MAX) {
1514
+ buffer.splice(0, buffer.length - VE_TRACE_MAX)
1515
+ }
1516
+ if (!window.__ARCHIE_VE_TRACE_DUMP__) {
1517
+ window.__ARCHIE_VE_TRACE_DUMP__ = function () {
1518
+ return JSON.stringify(window.__ARCHIE_VE_TRACE__ || [])
1519
+ }
1520
+ }
1521
+ if (window._inspectorDebug || window.__ARCHIE_VE_DEBUG__ === true) {
1522
+ // eslint-disable-next-line no-console
1523
+ console.log("[archie-ve:inspector]", event, data || "")
1524
+ }
1525
+ } catch (e) {
1526
+ // Tracing must never break the inspector.
1527
+ }
1528
+ }
1529
+
1458
1530
  postMessageToParent({
1459
1531
  type: "INSPECTOR_SCRIPT_LOADED",
1460
1532
  timestamp: Date.now(),
@@ -2658,6 +2730,31 @@
2658
2730
  } catch (e) {}
2659
2731
  }
2660
2732
 
2733
+ veTrace("resolve-mutation-element", {
2734
+ selector: hasSelector ? selector : null,
2735
+ inspectorSource:
2736
+ inspectorSource && typeof inspectorSource === "object"
2737
+ ? (inspectorSource.file || "") +
2738
+ ":" +
2739
+ (inspectorSource.line || "") +
2740
+ ":" +
2741
+ (inspectorSource.column || "")
2742
+ : null,
2743
+ matchedSelector: !!selectorElement,
2744
+ resolvedVia: !element
2745
+ ? "none"
2746
+ : element === selectorElement
2747
+ ? "selector"
2748
+ : "inspector-source-or-fallback",
2749
+ resolvedNodeId: element
2750
+ ? element.getAttribute("data-dnd-node-id") || null
2751
+ : null,
2752
+ resolvedSourceRef: element
2753
+ ? element.getAttribute("data-archie-source-ref") || null
2754
+ : null,
2755
+ resolvedTag: element ? String(element.tagName || "").toLowerCase() : null,
2756
+ })
2757
+
2661
2758
  return element
2662
2759
  }
2663
2760
 
@@ -3207,6 +3304,10 @@
3207
3304
  return
3208
3305
  }
3209
3306
 
3307
+ veTrace("runtime-event:" + detail.type, {
3308
+ operationId: detail.operationId || null,
3309
+ })
3310
+
3210
3311
  if (detail.type === "design-mode-changed") {
3211
3312
  // In unified inspect the arrange overlay flips its internal
3212
3313
  // design-mode store as a side effect ("design" on mount, "off" on
@@ -3216,6 +3317,9 @@
3216
3317
  // only needs runtime-originated mode changes in the legacy
3217
3318
  // design-only flow.
3218
3319
  if (hostCommandedEditorMode === "inspect") {
3320
+ veTrace("runtime-event:design-mode-changed:suppressed", {
3321
+ hostCommandedEditorMode: hostCommandedEditorMode,
3322
+ })
3219
3323
  return
3220
3324
  }
3221
3325
  postMessageToParent({
@@ -3304,6 +3408,12 @@
3304
3408
  event.data.type,
3305
3409
  event.data
3306
3410
  )
3411
+ if (event.data.type !== "EXTERNAL_DRAG_MOVE") {
3412
+ veTrace("in:" + event.data.type, {
3413
+ requestId: event.data.requestId || null,
3414
+ selector: event.data.selector || null,
3415
+ })
3416
+ }
3307
3417
  }
3308
3418
 
3309
3419
  if (event.data && event.data.type === "SET_EDITOR_MODE") {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@archie/devtools",
3
- "version": "0.0.35",
3
+ "version": "0.0.36",
4
4
  "description": "DevTools for Archie generated applications - Route synchronization and editor communication",
5
5
  "repository": {
6
6
  "type": "git",