@tangle-network/sandbox-ui 0.104.0 → 0.104.1

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.
@@ -1,6 +1,6 @@
1
1
  import {
2
2
  usePtySession
3
- } from "./chunk-KEYPUGS3.js";
3
+ } from "./chunk-7KB22BLB.js";
4
4
 
5
5
  // src/terminal/terminal-view.tsx
6
6
  import "@xterm/xterm/css/xterm.css";
@@ -41,6 +41,8 @@ function TerminalView({
41
41
  subtitle = "Connected to PTY session",
42
42
  isActive = true,
43
43
  connectionId,
44
+ incarnationId,
45
+ control,
44
46
  fontSize = 13
45
47
  }) {
46
48
  const resolvedTheme = useMemo(
@@ -71,7 +73,9 @@ function TerminalView({
71
73
  apiUrl,
72
74
  token,
73
75
  onData,
74
- connectionId
76
+ connectionId,
77
+ incarnationId,
78
+ control
75
79
  });
76
80
  useEffect(() => {
77
81
  if (!containerRef.current) return;
@@ -37,7 +37,14 @@ function createTerminalConnectionId() {
37
37
  }
38
38
  return `terminal-${Date.now().toString(36)}-${Math.random().toString(36).slice(2)}`;
39
39
  }
40
- function usePtySession({ apiUrl, token, onData, connectionId: providedConnectionId }) {
40
+ function usePtySession({
41
+ apiUrl,
42
+ token,
43
+ onData,
44
+ connectionId: providedConnectionId,
45
+ incarnationId,
46
+ control
47
+ }) {
41
48
  const [isConnected, setIsConnected] = useState(false);
42
49
  const [error, setError] = useState(null);
43
50
  const sessionIdRef = useRef(null);
@@ -48,6 +55,11 @@ function usePtySession({ apiUrl, token, onData, connectionId: providedConnection
48
55
  const mountedRef = useRef(true);
49
56
  const onDataRef = useRef(onData);
50
57
  const tokenRef = useRef(token);
58
+ const incarnationIdRef = useRef(incarnationId);
59
+ const controlRef = useRef(control);
60
+ const exactAttachRequiredRef = useRef(
61
+ incarnationId !== void 0 || control !== void 0
62
+ );
51
63
  const connectStreamRef = useRef(null);
52
64
  const reconnectRef = useRef(null);
53
65
  const shouldDeleteSessionRef = useRef(false);
@@ -177,8 +189,17 @@ function usePtySession({ apiUrl, token, onData, connectionId: providedConnection
177
189
  pendingWsRef.current = null;
178
190
  if (options.initOnOpen) {
179
191
  try {
192
+ const initIncarnationId = incarnationIdRef.current;
193
+ const initControl = controlRef.current;
194
+ if (exactAttachRequiredRef.current && (!initIncarnationId || !initControl)) {
195
+ throw new Error(
196
+ "Interactive terminal identity is incomplete"
197
+ );
198
+ }
180
199
  ws.send(JSON.stringify({
181
200
  type: "init",
201
+ ...initIncarnationId !== void 0 ? { incarnationId: initIncarnationId } : {},
202
+ ...initControl !== void 0 ? { control: initControl } : {},
182
203
  cols: colsRef.current,
183
204
  rows: rowsRef.current
184
205
  }));
@@ -267,6 +288,11 @@ function usePtySession({ apiUrl, token, onData, connectionId: providedConnection
267
288
  });
268
289
  }, [apiUrl]);
269
290
  const connectStream = useCallback(async (sessionId) => {
291
+ if (exactAttachRequiredRef.current) {
292
+ throw new Error(
293
+ "Interactive terminal requires an exact WebSocket attachment"
294
+ );
295
+ }
270
296
  abortStream();
271
297
  setError(null);
272
298
  try {
@@ -354,12 +380,19 @@ function usePtySession({ apiUrl, token, onData, connectionId: providedConnection
354
380
  }, [apiUrl, abortStream]);
355
381
  onDataRef.current = onData;
356
382
  tokenRef.current = token;
383
+ incarnationIdRef.current = incarnationId;
384
+ controlRef.current = control;
385
+ exactAttachRequiredRef.current = incarnationId !== void 0 || control !== void 0;
357
386
  connectStreamRef.current = connectStream;
358
387
  const connect = useCallback(async () => {
359
388
  cleanup();
360
389
  const myGen = ++connectGenRef.current;
361
390
  retryCountRef.current = 0;
362
391
  setError(null);
392
+ if (exactAttachRequiredRef.current && (!incarnationIdRef.current || !controlRef.current)) {
393
+ setError("Interactive terminal identity is incomplete");
394
+ return;
395
+ }
363
396
  try {
364
397
  const connectionId = providedConnectionId ?? createTerminalConnectionId();
365
398
  if (!mountedRef.current) return;
@@ -373,6 +406,11 @@ function usePtySession({ apiUrl, token, onData, connectionId: providedConnection
373
406
  if (directWsOk) {
374
407
  return;
375
408
  }
409
+ if (exactAttachRequiredRef.current) {
410
+ throw new Error(
411
+ "Interactive terminal WebSocket attach failed; exact identity was not accepted"
412
+ );
413
+ }
376
414
  sessionIdRef.current = null;
377
415
  transportReadyRef.current = false;
378
416
  if (inputAbortRef.current) {
@@ -434,6 +472,11 @@ function usePtySession({ apiUrl, token, onData, connectionId: providedConnection
434
472
  console.warn("Terminal resize over WS failed; falling back to HTTP", err);
435
473
  }
436
474
  }
475
+ if (exactAttachRequiredRef.current) {
476
+ throw new Error(
477
+ "Interactive terminal is not attached with its exact identity"
478
+ );
479
+ }
437
480
  try {
438
481
  const res = await fetch(`${apiUrl}/terminals/${sid}`, {
439
482
  method: "PATCH",
@@ -469,6 +512,16 @@ function usePtySession({ apiUrl, token, onData, connectionId: providedConnection
469
512
  }
470
513
  continue;
471
514
  }
515
+ if (exactAttachRequiredRef.current) {
516
+ for (const w of batch.waiters) {
517
+ w.reject(
518
+ new Error(
519
+ "Interactive terminal is not attached with its exact identity"
520
+ )
521
+ );
522
+ }
523
+ continue;
524
+ }
472
525
  try {
473
526
  const res = await fetch(`${apiUrl}/terminals/${sid}/input`, {
474
527
  method: "POST",
@@ -6,7 +6,7 @@ import {
6
6
  } from "./chunk-K4Q4E7D7.js";
7
7
  import {
8
8
  TerminalView
9
- } from "./chunk-WYMAC3T3.js";
9
+ } from "./chunk-4VLVVKQZ.js";
10
10
  import {
11
11
  cn
12
12
  } from "./chunk-EI44GEQ5.js";
package/dist/hooks.d.ts CHANGED
@@ -1,11 +1,11 @@
1
1
  export { AgentStreamEvent, AppendUserMessageOptions, ApplySdkEventOptions, AuthUser, AutomationStreamEvent, BeginAssistantMessageOptions, BotStreamEvent, CompleteAssistantMessageOptions, ConnectionState, RealtimeSessionOptions, RealtimeSessionRegistry, RealtimeSessionRegistryProps, RealtimeSessionState, RealtimeSessionTarget, SSEEvent, SdkSessionAttachment, SdkSessionEvent, SdkSessionSeed, TaskStreamEvent, TerminalStreamEvent, UseAuthOptions, UseAuthResult, UseRunGroupsOptions, UseSSEStreamOptions, UseSSEStreamResult, UseSdkSessionOptions, UseSdkSessionReturn, UseToolCallStreamReturn, createAuthFetcher, useApiKey, useAuth, useAutoScroll, useDropdownMenu, useLiveTime, useRealtimeSession, useRunCollapseState, useRunGroups, useSSEStream, useSdkSession, useToolCallStream } from '@tangle-network/ui/hooks';
2
+ import { AgentInteractiveSessionControlClaim } from '@tangle-network/agent-interface';
2
3
  import * as _tanstack_react_query from '@tanstack/react-query';
3
4
  import { Session } from './types.js';
4
5
  export { e as SESSION_STREAM_RECONNECT_DELAY_MS, f as SendMessageOptions, S as SessionInfo, g as SessionStreamError, a as SidecarAuth, U as UseSessionStreamOptions, b as UseSessionStreamResult, c as UseSidecarAuthOptions, u as useSessionStream, d as useSidecarAuth } from './sdk-hooks-Cjt_Wq7g.js';
5
6
  import '@tangle-network/ui/types';
6
7
  import '@tangle-network/ui/stores';
7
8
  import '@tangle-network/ui/sdk-hooks';
8
- import '@tangle-network/agent-interface';
9
9
 
10
10
  interface UsePtySessionOptions {
11
11
  /** Base URL of the sidecar (e.g. "http://localhost:9100"). */
@@ -22,6 +22,13 @@ interface UsePtySessionOptions {
22
22
  * so the session does not survive a remount.
23
23
  */
24
24
  connectionId?: string;
25
+ /**
26
+ * Exact incarnation issued for an interactive agent session. When present,
27
+ * it must be sent with `control` on every WebSocket init frame.
28
+ */
29
+ incarnationId?: string;
30
+ /** Write claim for the exact interactive agent session. */
31
+ control?: AgentInteractiveSessionControlClaim;
25
32
  }
26
33
  interface UsePtySessionReturn {
27
34
  /** Whether the underlying transport is connected and receiving data. */
@@ -58,7 +65,7 @@ interface UsePtySessionReturn {
58
65
  * preserved as a fallback so the hook keeps working against
59
66
  * deployments that have not yet shipped the WS endpoint.
60
67
  */
61
- declare function usePtySession({ apiUrl, token, onData, connectionId: providedConnectionId }: UsePtySessionOptions): UsePtySessionReturn;
68
+ declare function usePtySession({ apiUrl, token, onData, connectionId: providedConnectionId, incarnationId, control, }: UsePtySessionOptions): UsePtySessionReturn;
62
69
 
63
70
  /**
64
71
  * Sandbox-level telemetry collected by the sidecar from cgroup v2
package/dist/hooks.js CHANGED
@@ -26,7 +26,7 @@ import {
26
26
  } from "./chunk-3GX5BSD4.js";
27
27
  import {
28
28
  usePtySession
29
- } from "./chunk-KEYPUGS3.js";
29
+ } from "./chunk-7KB22BLB.js";
30
30
  import "./chunk-CZ7CSFO4.js";
31
31
  export {
32
32
  RealtimeSessionRegistry,
package/dist/index.js CHANGED
@@ -153,7 +153,7 @@ import {
153
153
  buildUnifiedPatch,
154
154
  computeDiffStats,
155
155
  resolveLanguage
156
- } from "./chunk-K5RMJOH6.js";
156
+ } from "./chunk-NAWEV5UJ.js";
157
157
  import {
158
158
  FileArtifactPane,
159
159
  FilePreview,
@@ -238,10 +238,10 @@ import {
238
238
  UsageChart,
239
239
  formatPrice
240
240
  } from "./chunk-OMUIPJQZ.js";
241
- import "./chunk-WYMAC3T3.js";
241
+ import "./chunk-4VLVVKQZ.js";
242
242
  import {
243
243
  usePtySession
244
- } from "./chunk-KEYPUGS3.js";
244
+ } from "./chunk-7KB22BLB.js";
245
245
  import {
246
246
  Avatar,
247
247
  AvatarFallback,
@@ -1,4 +1,5 @@
1
1
  import * as React from 'react';
2
+ import { AgentInteractiveSessionControlClaim } from '@tangle-network/agent-interface';
2
3
 
3
4
  interface TerminalTheme {
4
5
  background: string;
@@ -52,8 +53,12 @@ interface TerminalViewProps {
52
53
  * session per mount.
53
54
  */
54
55
  connectionId?: string;
56
+ /** Exact incarnation issued for an interactive agent session. */
57
+ incarnationId?: string;
58
+ /** Write claim for the exact interactive agent session. */
59
+ control?: AgentInteractiveSessionControlClaim;
55
60
  }
56
61
  declare const DEFAULT_TERMINAL_THEME: TerminalTheme;
57
- declare function TerminalView({ apiUrl, token, theme, title, subtitle, isActive, connectionId, fontSize, }: TerminalViewProps): React.JSX.Element;
62
+ declare function TerminalView({ apiUrl, token, theme, title, subtitle, isActive, connectionId, incarnationId, control, fontSize, }: TerminalViewProps): React.JSX.Element;
58
63
 
59
64
  export { DEFAULT_TERMINAL_THEME, type TerminalTheme, TerminalView, type TerminalViewProps };
package/dist/terminal.js CHANGED
@@ -1,8 +1,8 @@
1
1
  import {
2
2
  DEFAULT_TERMINAL_THEME,
3
3
  TerminalView
4
- } from "./chunk-WYMAC3T3.js";
5
- import "./chunk-KEYPUGS3.js";
4
+ } from "./chunk-4VLVVKQZ.js";
5
+ import "./chunk-7KB22BLB.js";
6
6
  import "./chunk-CZ7CSFO4.js";
7
7
  export {
8
8
  DEFAULT_TERMINAL_THEME,
package/dist/workbench.js CHANGED
@@ -12,12 +12,12 @@ import {
12
12
  buildUnifiedPatch,
13
13
  computeDiffStats,
14
14
  resolveLanguage
15
- } from "./chunk-K5RMJOH6.js";
15
+ } from "./chunk-NAWEV5UJ.js";
16
16
  import "./chunk-PZVUIUUW.js";
17
17
  import "./chunk-K4Q4E7D7.js";
18
18
  import "./chunk-OMUIPJQZ.js";
19
- import "./chunk-WYMAC3T3.js";
20
- import "./chunk-KEYPUGS3.js";
19
+ import "./chunk-4VLVVKQZ.js";
20
+ import "./chunk-7KB22BLB.js";
21
21
  import "./chunk-2XPJ2XF7.js";
22
22
  import "./chunk-RQZRXKMR.js";
23
23
  import "./chunk-BGVEHENC.js";
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@tangle-network/sandbox-ui",
3
- "version": "0.104.0",
3
+ "version": "0.104.1",
4
4
  "description": "Unified UI component library for Tangle Sandbox — primitives, chat, dashboard, terminal, editor, and workspace components",
5
5
  "repository": {
6
6
  "type": "git",