dsh-openwrite 0.2.10 → 0.2.12

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.
@@ -2497,25 +2497,47 @@ window.__ModuleLoader__.load({
2497
2497
  //#endregion
2498
2498
  //#region src/client/sessionNavigation.ts
2499
2499
  const DEFAULT_SELECTION_TIMEOUT_MS = 2e3;
2500
+ function selected(sessions, id) {
2501
+ const snapshot = sessions.list.getSnapshot();
2502
+ if ("current" in snapshot) return snapshot.current === id;
2503
+ return ((snapshot.byId?.[id])?.retainedBy?.mainView ?? 0) > 0;
2504
+ }
2505
+ async function refreshInvocationCatalog(sessions, parent) {
2506
+ if (typeof sessions.refreshSubagents === "function") await sessions.refreshSubagents(parent);
2507
+ }
2500
2508
  /**
2501
2509
  * Select a persisted invocation session and confirm that DSH actually staged it.
2502
2510
  * Returns false only when neither the ordinary session list nor a refreshed
2503
2511
  * direct-parent catalog can address the target.
2504
2512
  */
2505
- async function openInvocationSession(sessions, rawSessionId, rawParentSessionId, timeoutMs = DEFAULT_SELECTION_TIMEOUT_MS) {
2513
+ async function openInvocationSession(sessions, rawSessionId, rawParentSessionId, timeoutMs = DEFAULT_SELECTION_TIMEOUT_MS, uiWorkspace) {
2506
2514
  const sessionId = rawSessionId;
2507
- if (sessions.list.getSnapshot().current === sessionId) return true;
2515
+ if (selected(sessions, sessionId)) return true;
2508
2516
  if (sessions.list.getSnapshot().ids.includes(sessionId)) {
2509
- await selectAndConfirm(sessions, sessionId, () => sessions.open(sessionId), timeoutMs);
2517
+ await selectAndConfirm(sessions, sessionId, () => {
2518
+ if (uiWorkspace) uiWorkspace.openSession(sessionId);
2519
+ else if (sessions.open) sessions.open(sessionId);
2520
+ else throw new Error("DSH exposes no session navigation API");
2521
+ }, timeoutMs);
2510
2522
  return true;
2511
2523
  }
2512
- let address = sessions.subagentAddress(sessionId);
2524
+ let address = sessions.subagentAddress?.(sessionId);
2513
2525
  if (address === void 0 && rawParentSessionId !== void 0) {
2514
- await sessions.refreshSubagents(rawParentSessionId);
2515
- address = sessions.subagentAddress(sessionId);
2526
+ await refreshInvocationCatalog(sessions, rawParentSessionId);
2527
+ address = sessions.subagentAddress?.(sessionId);
2528
+ if (!address && uiWorkspace) address = {
2529
+ parentSessionId: rawParentSessionId,
2530
+ childSessionId: sessionId,
2531
+ mode: "continuable"
2532
+ };
2516
2533
  }
2517
2534
  if (address === void 0) return false;
2518
- await selectAndConfirm(sessions, sessionId, () => sessions.openSubagent(address), timeoutMs);
2535
+ const target = address;
2536
+ await selectAndConfirm(sessions, sessionId, () => {
2537
+ if (uiWorkspace) uiWorkspace.openSession(target);
2538
+ else if (sessions.openSubagent) sessions.openSubagent(target);
2539
+ else throw new Error("DSH exposes no subagent navigation API");
2540
+ }, timeoutMs);
2519
2541
  return true;
2520
2542
  }
2521
2543
  async function selectAndConfirm(sessions, sessionId, select, timeoutMs) {
@@ -2531,7 +2553,7 @@ window.__ModuleLoader__.load({
2531
2553
  else reject(error);
2532
2554
  };
2533
2555
  const confirm = () => {
2534
- if (sessions.list.getSnapshot().current === sessionId) finish();
2556
+ if (selected(sessions, sessionId)) finish();
2535
2557
  };
2536
2558
  const timer = setTimeout(() => {
2537
2559
  finish(/* @__PURE__ */ new Error(`DSH did not select session ${sessionId} within ${timeoutMs} ms`));
@@ -2805,6 +2827,46 @@ window.__ModuleLoader__.load({
2805
2827
  .dog-launcher, .dog-node, .dog-backdrop, .dog-dialog, .dog-runtime-pulse { animation: none; transition: none; }
2806
2828
  }
2807
2829
  `;
2830
+ //#endregion
2831
+ //#region src/client/sessionState.ts
2832
+ /** DSH 0.2 folds pending interactions into the unified session status source. */
2833
+ function debuggerSessionState(sessions, uiSession) {
2834
+ const status = uiSession.sessionStatus;
2835
+ const source = status ?? uiSession.pendingInteractions;
2836
+ if (!source || typeof source.getSnapshot !== "function" || typeof source.subscribe !== "function") throw new Error("DSH session UI exposes neither sessionStatus nor pendingInteractions");
2837
+ let lastSessions;
2838
+ let lastStatus;
2839
+ let combined;
2840
+ return {
2841
+ getSnapshot() {
2842
+ const next = sessions.getSnapshot();
2843
+ const pending = source.getSnapshot();
2844
+ if (next !== lastSessions || pending !== lastStatus) {
2845
+ lastSessions = next;
2846
+ lastStatus = pending;
2847
+ const interactions = status ? new Map([...status.getSnapshot()].flatMap(([id, value]) => value.pendingInteraction === void 0 ? [] : [[id, value.pendingInteraction]])) : pending;
2848
+ combined = {
2849
+ ...next,
2850
+ pendingInteractions: interactions
2851
+ };
2852
+ }
2853
+ return combined;
2854
+ },
2855
+ subscribe(listener) {
2856
+ const stopSessions = sessions.subscribe(listener);
2857
+ try {
2858
+ const stopStatus = source.subscribe(listener);
2859
+ return () => {
2860
+ stopStatus();
2861
+ stopSessions();
2862
+ };
2863
+ } catch (error) {
2864
+ stopSessions();
2865
+ throw error;
2866
+ }
2867
+ }
2868
+ };
2869
+ }
2808
2870
  //#endregion
2809
2871
  //#region src/client/index.tsx
2810
2872
  /** The overlay uses the shared trusted RPC transport and canonical session navigator. */
@@ -2812,10 +2874,18 @@ window.__ModuleLoader__.load({
2812
2874
  "slots",
2813
2875
  "sessions",
2814
2876
  "connection",
2815
- "uiSession"
2877
+ "uiSession",
2878
+ "uiWorkspace"
2816
2879
  ];
2817
2880
  /** Register the debugger beside other frame-wide overlays without replacing shipped UI. */
2818
2881
  function apply(ctx) {
2882
+ try {
2883
+ ctx.effect(() => install(ctx), "openwrite-dog: client activation");
2884
+ } catch (error) {
2885
+ console.error("[OpenWrite/DoG] Debugger disabled: client activation failed", error);
2886
+ }
2887
+ }
2888
+ function* install(ctx) {
2819
2889
  const connection = ctx.get("connection");
2820
2890
  const sessions = ctx.get("sessions");
2821
2891
  const call = async (endpoint, payload, signal) => {
@@ -2823,34 +2893,9 @@ window.__ModuleLoader__.load({
2823
2893
  if (!result.ok) throw new Error(result.error.message);
2824
2894
  return result.value;
2825
2895
  };
2826
- const openSession = (sessionId, parentSessionId) => openInvocationSession(sessions, sessionId, parentSessionId);
2827
- let lastSessions = sessions.list.getSnapshot();
2828
- let lastPending = ctx.uiSession.pendingInteractions.getSnapshot();
2829
- let combined = {
2830
- ...lastSessions,
2831
- pendingInteractions: lastPending
2832
- };
2833
- const getSessionState = () => {
2834
- const next = sessions.list.getSnapshot();
2835
- const pending = ctx.uiSession.pendingInteractions.getSnapshot();
2836
- if (next !== lastSessions || pending !== lastPending) {
2837
- lastSessions = next;
2838
- lastPending = pending;
2839
- combined = {
2840
- ...next,
2841
- pendingInteractions: pending
2842
- };
2843
- }
2844
- return combined;
2845
- };
2846
- const subscribeSessions = (listener) => {
2847
- const stopSession = sessions.list.subscribe(listener);
2848
- const stopPending = ctx.uiSession.pendingInteractions.subscribe(listener);
2849
- return () => {
2850
- stopSession();
2851
- stopPending();
2852
- };
2853
- };
2896
+ const openSession = (sessionId, parentSessionId) => openInvocationSession(sessions, sessionId, parentSessionId, void 0, typeof ctx.uiWorkspace.openSession === "function" ? ctx.uiWorkspace : void 0);
2897
+ const state = debuggerSessionState(sessions.list, ctx.uiSession);
2898
+ state.getSnapshot();
2854
2899
  const DogDebuggerHost = () => {
2855
2900
  const [request, setRequest] = (0, react.useState)(0);
2856
2901
  (0, react.useEffect)(() => {
@@ -2867,17 +2912,24 @@ window.__ModuleLoader__.load({
2867
2912
  goalId
2868
2913
  }, signal),
2869
2914
  openSession,
2870
- getSessionState,
2871
- subscribeSessions,
2872
- refreshAgentCatalog: (parentSessionId) => sessions.refreshSubagents(parentSessionId)
2915
+ getSessionState: state.getSnapshot,
2916
+ subscribeSessions: state.subscribe,
2917
+ refreshAgentCatalog: (parentSessionId) => refreshInvocationCatalog(sessions, parentSessionId)
2873
2918
  }, request);
2874
2919
  };
2875
- ctx.effect(installStyles, "dog-debugger: styles");
2876
- ctx.slots.inject("shell.overlay", () => ctx.slots.register({
2877
- name: "shell.overlay",
2878
- id: "openwrite.dog-debugger",
2879
- order: 80
2880
- }, DogDebuggerHost));
2920
+ yield ctx.effect(installStyles, "dog-debugger: styles");
2921
+ yield ctx.slots.inject("shell.overlay", () => {
2922
+ try {
2923
+ return ctx.slots.register({
2924
+ name: "shell.overlay",
2925
+ id: "openwrite.dog-debugger",
2926
+ order: 80
2927
+ }, DogDebuggerHost);
2928
+ } catch (error) {
2929
+ console.error("[OpenWrite/DoG] Debugger disabled: overlay registration failed", error);
2930
+ return () => {};
2931
+ }
2932
+ });
2881
2933
  }
2882
2934
  function installStyles() {
2883
2935
  if (document.querySelector(`style[data-plugin-css="@dsh-external/dsh-dog/debugger"]`) !== null) return () => void 0;