tmux-ide 2.9.2 → 2.9.3

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.
Files changed (263) hide show
  1. package/README.md +1 -1
  2. package/bin/cli.js +2071 -625
  3. package/package.json +14 -5
  4. package/packages/contracts/src/desktop-host.ts +3 -0
  5. package/packages/contracts/src/saved-machines.ts +19 -0
  6. package/packages/contracts/src/terminal-replica.ts +1 -1
  7. package/packages/core/package.json +3 -2
  8. package/packages/core/src/terminal-delivery.ts +51 -3
  9. package/packages/core/src/terminal-fnv64-wasm.ts +4 -3
  10. package/packages/core/src/terminal-replica-hash-cache.ts +129 -31
  11. package/packages/core/src/terminal-replica-owned-row.ts +27 -0
  12. package/packages/core/src/terminal-replica.ts +13 -28
  13. package/packages/daemon/dist/command-center/daemon-fleet-facts-observer.js +96 -10
  14. package/packages/daemon/dist/command-center/resources/saved-machine-route.js +40 -1
  15. package/packages/daemon/dist/command-center/ws-events.js +5 -24
  16. package/packages/daemon/dist/lib/canonical-daemon-bootstrap.js +8 -0
  17. package/packages/daemon/dist/lib/canonical-daemon.js +28 -2
  18. package/packages/daemon/dist/lib/daemon-embed.js +1 -1
  19. package/packages/daemon/dist/lib/daemon-service-manager.js +122 -0
  20. package/packages/daemon/dist/lib/daemon-service-plan.js +127 -0
  21. package/packages/daemon/dist/lib/daemon-service.js +259 -0
  22. package/packages/daemon/dist/lib/install-origin.js +2 -0
  23. package/packages/daemon/dist/lib/local-fleet-request.js +9 -3
  24. package/packages/daemon/dist/lib/log.js +6 -10
  25. package/packages/daemon/dist/lib/managed-installer-update.js +67 -0
  26. package/packages/daemon/dist/lib/{tui-download-lock.js → private-operation-lock.js} +11 -11
  27. package/packages/daemon/dist/lib/remote-daemon-info.js +3 -2
  28. package/packages/daemon/dist/lib/remote-daemon-lifecycle.js +4 -4
  29. package/packages/daemon/dist/lib/remote-tmux-command.js +10 -0
  30. package/packages/daemon/dist/lib/runtime-namespace.js +28 -16
  31. package/packages/daemon/dist/lib/saved-machines.js +40 -2
  32. package/packages/daemon/dist/lib/ssh-daemon-transport.js +24 -9
  33. package/packages/daemon/dist/lib/tmux-server-owner.js +1 -1
  34. package/packages/daemon/dist/lib/tmux-server-registration.js +21 -3
  35. package/packages/daemon/dist/lib/tui-binary.js +2 -2
  36. package/packages/daemon/dist/lib/update.js +18 -0
  37. package/packages/daemon/dist/lib/workspace-multiplexer-verbs.js +24 -1
  38. package/packages/daemon/dist/machines.js +40 -4
  39. package/packages/daemon/dist/native/TmuxIdeNotifier.app/Contents/Info.plist +2 -2
  40. package/packages/daemon/dist/native/TmuxIdeNotifier.app/Contents/MacOS/tmux-ide-notifier +0 -0
  41. package/packages/daemon/dist/native/TmuxIdeNotifier.app/Contents/Resources/Assets.car +0 -0
  42. package/packages/daemon/dist/native/TmuxIdeNotifier.app/Contents/_CodeSignature/CodeResources +2 -2
  43. package/packages/daemon/dist/terminal/attachments/direct-websocket.js +4 -1
  44. package/packages/daemon/dist/terminal/attachments/native-runtime.js +22 -13
  45. package/packages/daemon/dist/terminal/mirror/mirror-service.js +101 -3
  46. package/packages/daemon/dist/terminal/mirror/registered-window-guard.js +62 -0
  47. package/packages/daemon/dist/terminal/mirror/session-channel.js +75 -4
  48. package/packages/daemon/dist/terminal/mirror/shared-window-index.js +45 -0
  49. package/packages/daemon/dist/terminal/pane-stream/pane-stream-websocket.js +11 -1
  50. package/packages/daemon/dist/terminal/session-runtime/multiplexer-backend.js +1 -0
  51. package/packages/daemon/dist/terminal/session-runtime/registry.js +56 -7
  52. package/packages/daemon/dist/terminal/session-runtime/semantic-mutation-executor.js +3 -1
  53. package/packages/daemon/dist/tui/mirror/dialog-model.js +2 -35
  54. package/packages/daemon/dist/tui/mirror/runtime/application-daemon-authority-owner.js +8 -0
  55. package/packages/daemon/dist/tui/mirror/runtime/application-home-fleet.js +20 -2
  56. package/packages/daemon/dist/tui/mirror/runtime/application-machine-agents.js +7 -1
  57. package/packages/daemon/dist/tui/mirror/runtime/application-machine-authority.js +59 -9
  58. package/packages/daemon/dist/tui/mirror/runtime/application-machine-navigation.js +27 -19
  59. package/packages/daemon/dist/tui/mirror/runtime/application-machine-sidebar.jsx +23 -18
  60. package/packages/daemon/dist/tui/mirror/runtime/application-machine-startup.js +31 -2
  61. package/packages/daemon/dist/tui/mirror/runtime/application-palette-search-owner.js +7 -3
  62. package/packages/daemon/dist/tui/mirror/runtime/application-performance-log.js +3 -0
  63. package/packages/daemon/dist/tui/mirror/runtime/application-terminal-input-ingress.js +146 -2
  64. package/packages/daemon/dist/tui/mirror/runtime/application-terminal-interaction-controller.js +201 -50
  65. package/packages/daemon/dist/tui/mirror/runtime/bounded-performance-record-writer.js +50 -10
  66. package/packages/daemon/dist/tui/mirror/runtime/terminal-fast-lane-renderer-adapter.js +6 -5
  67. package/packages/daemon/dist/tui/mirror/runtime/terminal-pane-input-router.js +3 -0
  68. package/packages/daemon/dist/tui/mirror/runtime/workspace-terminal-fast-lane.js +8 -2
  69. package/packages/daemon/dist/tui/mirror/terminal-text.js +35 -0
  70. package/packages/daemon/dist/tui/mirror/workspace/connection-feedback.js +5 -3
  71. package/packages/daemon/src/command-center/daemon-fleet-facts-observer.ts +100 -10
  72. package/packages/daemon/src/command-center/resources/saved-machine-route.ts +48 -1
  73. package/packages/daemon/src/command-center/ws-events.ts +5 -25
  74. package/packages/daemon/src/lib/canonical-daemon-bootstrap.ts +12 -0
  75. package/packages/daemon/src/lib/canonical-daemon.ts +44 -2
  76. package/packages/daemon/src/lib/daemon-embed.ts +1 -0
  77. package/packages/daemon/src/lib/daemon-service-manager.ts +152 -0
  78. package/packages/daemon/src/lib/daemon-service-plan.ts +153 -0
  79. package/packages/daemon/src/lib/daemon-service.ts +301 -0
  80. package/packages/daemon/src/lib/install-origin.ts +5 -0
  81. package/packages/daemon/src/lib/local-fleet-request.ts +19 -3
  82. package/packages/daemon/src/lib/log.ts +13 -9
  83. package/packages/daemon/src/lib/managed-installer-update.ts +79 -0
  84. package/packages/daemon/src/lib/{tui-download-lock.ts → private-operation-lock.ts} +15 -11
  85. package/packages/daemon/src/lib/remote-daemon-info.ts +3 -3
  86. package/packages/daemon/src/lib/remote-daemon-lifecycle.ts +4 -4
  87. package/packages/daemon/src/lib/remote-tmux-command.ts +12 -0
  88. package/packages/daemon/src/lib/runtime-namespace.ts +27 -18
  89. package/packages/daemon/src/lib/saved-machines.ts +40 -1
  90. package/packages/daemon/src/lib/ssh-daemon-transport.ts +25 -7
  91. package/packages/daemon/src/lib/tmux-server-owner.ts +1 -0
  92. package/packages/daemon/src/lib/tmux-server-registration.ts +21 -3
  93. package/packages/daemon/src/lib/tui-binary.ts +2 -2
  94. package/packages/daemon/src/lib/update.ts +24 -0
  95. package/packages/daemon/src/lib/workspace-multiplexer-verbs.ts +22 -0
  96. package/packages/daemon/src/machines.ts +53 -5
  97. package/packages/daemon/src/terminal/attachments/direct-websocket.ts +8 -2
  98. package/packages/daemon/src/terminal/attachments/native-runtime.ts +28 -13
  99. package/packages/daemon/src/terminal/mirror/mirror-service.ts +105 -3
  100. package/packages/daemon/src/terminal/mirror/registered-window-guard.ts +66 -0
  101. package/packages/daemon/src/terminal/mirror/session-channel.ts +92 -4
  102. package/packages/daemon/src/terminal/mirror/shared-window-index.ts +42 -0
  103. package/packages/daemon/src/terminal/pane-stream/pane-stream-websocket.ts +12 -1
  104. package/packages/daemon/src/terminal/session-runtime/multiplexer-backend.ts +2 -0
  105. package/packages/daemon/src/terminal/session-runtime/registry.ts +70 -8
  106. package/packages/daemon/src/terminal/session-runtime/semantic-mutation-executor.ts +3 -1
  107. package/packages/daemon/src/tui/mirror/dialog-model.ts +2 -32
  108. package/packages/daemon/src/tui/mirror/runtime/application-daemon-authority-owner.ts +8 -0
  109. package/packages/daemon/src/tui/mirror/runtime/application-home-fleet.ts +19 -2
  110. package/packages/daemon/src/tui/mirror/runtime/application-machine-agents.ts +6 -1
  111. package/packages/daemon/src/tui/mirror/runtime/application-machine-authority.ts +60 -11
  112. package/packages/daemon/src/tui/mirror/runtime/application-machine-navigation.ts +39 -33
  113. package/packages/daemon/src/tui/mirror/runtime/application-machine-sidebar.tsx +31 -23
  114. package/packages/daemon/src/tui/mirror/runtime/application-machine-startup.ts +38 -2
  115. package/packages/daemon/src/tui/mirror/runtime/application-palette-search-owner.ts +7 -4
  116. package/packages/daemon/src/tui/mirror/runtime/application-performance-log.ts +3 -0
  117. package/packages/daemon/src/tui/mirror/runtime/application-root-v2.tsx +1 -1
  118. package/packages/daemon/src/tui/mirror/runtime/application-shell-view.tsx +47 -46
  119. package/packages/daemon/src/tui/mirror/runtime/application-terminal-input-ingress.ts +165 -2
  120. package/packages/daemon/src/tui/mirror/runtime/application-terminal-interaction-controller.ts +207 -53
  121. package/packages/daemon/src/tui/mirror/runtime/bounded-performance-record-writer.ts +49 -9
  122. package/packages/daemon/src/tui/mirror/runtime/terminal-fast-lane-renderer-adapter.ts +6 -5
  123. package/packages/daemon/src/tui/mirror/runtime/terminal-pane-input-router.ts +4 -0
  124. package/packages/daemon/src/tui/mirror/runtime/workspace-terminal-fast-lane.ts +8 -3
  125. package/packages/daemon/src/tui/mirror/terminal-text.ts +32 -0
  126. package/packages/daemon/src/tui/mirror/workspace/connection-feedback.ts +6 -3
  127. package/packages/daemon-client/src/fleet-connection-status.ts +10 -1
  128. package/packages/daemon-client/src/workspace-client.ts +4 -1
  129. package/packages/contracts/src/__tests__/actions-contract.test.ts +0 -119
  130. package/packages/contracts/src/__tests__/agent-graph-overlay.test.ts +0 -428
  131. package/packages/contracts/src/__tests__/app-window-mutation.test.ts +0 -51
  132. package/packages/contracts/src/__tests__/app-window-state.test.ts +0 -34
  133. package/packages/contracts/src/__tests__/application-shell.test.ts +0 -645
  134. package/packages/contracts/src/__tests__/automation-operations.test.ts +0 -78
  135. package/packages/contracts/src/__tests__/causal-cell.test.ts +0 -47
  136. package/packages/contracts/src/__tests__/client-view-state.test.ts +0 -115
  137. package/packages/contracts/src/__tests__/cohesion-fixture.test.ts +0 -106
  138. package/packages/contracts/src/__tests__/commands.test.ts +0 -86
  139. package/packages/contracts/src/__tests__/control.test.ts +0 -154
  140. package/packages/contracts/src/__tests__/daemon-events.test.ts +0 -405
  141. package/packages/contracts/src/__tests__/daemon-resources.test.ts +0 -143
  142. package/packages/contracts/src/__tests__/daemon-wire.test.ts +0 -149
  143. package/packages/contracts/src/__tests__/desktop-host.test.ts +0 -269
  144. package/packages/contracts/src/__tests__/desktop-missions.test.ts +0 -215
  145. package/packages/contracts/src/__tests__/experience-conformance.test.ts +0 -153
  146. package/packages/contracts/src/__tests__/experience-kernel-boundary.test.ts +0 -113
  147. package/packages/contracts/src/__tests__/experience-shell.test.ts +0 -65
  148. package/packages/contracts/src/__tests__/fixtures/daemon-wire-v2.json +0 -35
  149. package/packages/contracts/src/__tests__/fixtures/daemon-wire-v3.json +0 -35
  150. package/packages/contracts/src/__tests__/fixtures/daemon-wire-v4.json +0 -35
  151. package/packages/contracts/src/__tests__/fixtures/scoped-receipt.ts +0 -62
  152. package/packages/contracts/src/__tests__/fleet-agent-graph.test.ts +0 -231
  153. package/packages/contracts/src/__tests__/fleet-catalog.test.ts +0 -270
  154. package/packages/contracts/src/__tests__/fleet-lifecycle.test.ts +0 -62
  155. package/packages/contracts/src/__tests__/focus-overlay.test.ts +0 -110
  156. package/packages/contracts/src/__tests__/ide-config.test.ts +0 -64
  157. package/packages/contracts/src/__tests__/interaction-evidence.test.ts +0 -288
  158. package/packages/contracts/src/__tests__/interaction-receipt-v2.test.ts +0 -72
  159. package/packages/contracts/src/__tests__/issue-error.test.ts +0 -78
  160. package/packages/contracts/src/__tests__/mission-projections.test.ts +0 -186
  161. package/packages/contracts/src/__tests__/missions.test.ts +0 -272
  162. package/packages/contracts/src/__tests__/multiplexer-verbs.test.ts +0 -242
  163. package/packages/contracts/src/__tests__/pane-appearance.test.ts +0 -146
  164. package/packages/contracts/src/__tests__/pane-read-result.test.ts +0 -55
  165. package/packages/contracts/src/__tests__/pane-stream.test.ts +0 -536
  166. package/packages/contracts/src/__tests__/pane-widget-marker.test.ts +0 -327
  167. package/packages/contracts/src/__tests__/performance-metrics.test.ts +0 -73
  168. package/packages/contracts/src/__tests__/performance-qualification.test.ts +0 -137
  169. package/packages/contracts/src/__tests__/rich-card-widget.test.ts +0 -29
  170. package/packages/contracts/src/__tests__/session-runtime.test.ts +0 -512
  171. package/packages/contracts/src/__tests__/startup-readiness.test.ts +0 -409
  172. package/packages/contracts/src/__tests__/terminal-attachment-stream.test.ts +0 -72
  173. package/packages/contracts/src/__tests__/terminal-attachments.test.ts +0 -329
  174. package/packages/contracts/src/__tests__/terminal-delivery.test.ts +0 -88
  175. package/packages/contracts/src/__tests__/terminal-runtime-inventory.test.ts +0 -68
  176. package/packages/contracts/src/__tests__/terminals.test.ts +0 -87
  177. package/packages/contracts/src/__tests__/tmux-server-scope.test.ts +0 -166
  178. package/packages/contracts/src/__tests__/transport-contract-loading.test.ts +0 -91
  179. package/packages/contracts/src/__tests__/visual-tokens.test.ts +0 -224
  180. package/packages/contracts/src/__tests__/window-links.test.ts +0 -243
  181. package/packages/contracts/src/__tests__/workspace-changes-resource.test.ts +0 -317
  182. package/packages/contracts/src/__tests__/workspace-changes-view.test.ts +0 -122
  183. package/packages/contracts/src/__tests__/workspace-config.test.ts +0 -294
  184. package/packages/contracts/src/__tests__/workspace-files-resource.test.ts +0 -261
  185. package/packages/contracts/src/__tests__/workspace-files-tree.test.ts +0 -147
  186. package/packages/contracts/src/__tests__/workspace-pane-creation.test.ts +0 -249
  187. package/packages/contracts/src/__tests__/workspace-promotion.test.ts +0 -94
  188. package/packages/contracts/src/__tests__/workspace-resource-identity.test.ts +0 -90
  189. package/packages/contracts/src/daemon-resource-request.test.ts +0 -192
  190. package/packages/contracts/src/native-operation-identity.test.ts +0 -23
  191. package/packages/contracts/src/workspace-admission.test.ts +0 -21
  192. package/packages/contracts/src/workspace-catalog-resource.test.ts +0 -146
  193. package/packages/core/src/agent-provisioning.test.ts +0 -42
  194. package/packages/core/src/application-shell-session.test.ts +0 -105
  195. package/packages/core/src/interaction-evidence.test.ts +0 -134
  196. package/packages/core/src/interaction-flow.test.ts +0 -66
  197. package/packages/core/src/interaction-receipts.test.ts +0 -671
  198. package/packages/core/src/navigator.test.ts +0 -34
  199. package/packages/core/src/optimistic-projection-conformance.test.ts +0 -75
  200. package/packages/core/src/optimistic-projection.test.ts +0 -118
  201. package/packages/core/src/performance-metrics.test.ts +0 -121
  202. package/packages/core/src/performance-qualification.test.ts +0 -283
  203. package/packages/core/src/saved-machines.test.ts +0 -80
  204. package/packages/core/src/terminal-compact-cold.test.ts +0 -87
  205. package/packages/core/src/terminal-conformance.test.ts +0 -48
  206. package/packages/core/src/terminal-delivery-cache-lifetime.test.ts +0 -167
  207. package/packages/core/src/terminal-delivery-encode-cooperative.test.ts +0 -140
  208. package/packages/core/src/terminal-delivery-representation-hash.test.ts +0 -77
  209. package/packages/core/src/terminal-delivery.test.ts +0 -1471
  210. package/packages/core/src/terminal-fnv64-wasm.test.ts +0 -61
  211. package/packages/core/src/terminal-replica-cold.test.ts +0 -31
  212. package/packages/core/src/terminal-replica-cooperative.test.ts +0 -170
  213. package/packages/core/src/terminal-replica-hash-cache.test.ts +0 -283
  214. package/packages/core/src/terminal-replica.test.ts +0 -347
  215. package/packages/core/src/workspace-selection.test.ts +0 -63
  216. package/packages/daemon/dist/__tests__/support.js +0 -33
  217. package/packages/daemon/dist/lib/__tests__/fixtures/workspace-state-writer.js +0 -58
  218. package/packages/daemon/dist/lib/__tests__/installed-recovery-fixture.js +0 -400
  219. package/packages/daemon/dist/terminal/__tests__/MockPtyAdapter.js +0 -182
  220. package/packages/daemon/dist/terminal/mirror/__tests__/scripted-channel.js +0 -98
  221. package/packages/daemon/dist/terminal/mirror/__tests__/simulated-channel.js +0 -156
  222. package/packages/daemon/src/tui/mirror/__snapshots__/activity-surface-renderer.test.tsx.snap +0 -42
  223. package/packages/daemon/src/tui/mirror/__snapshots__/changes-terminal-surface-renderer.test.tsx.snap +0 -267
  224. package/packages/daemon/src/tui/mirror/__snapshots__/home-files-surface-renderer.test.tsx.snap +0 -267
  225. package/packages/daemon/src/tui/mirror/__snapshots__/missions-surface-renderer.test.tsx.snap +0 -134
  226. package/packages/daemon/src/tui/mirror/__snapshots__/recipes-gallery-renderer.test.tsx.snap +0 -141
  227. package/packages/daemon/src/tui/mirror/__snapshots__/shell-chrome-renderer.test.tsx.snap +0 -134
  228. package/packages/daemon/src/tui/mirror/runtime/__snapshots__/application-shell-view-renderer.test.tsx.snap +0 -87
  229. package/packages/daemon/src/tui/mirror/workspace/__snapshots__/agent-terminal-canvas-renderer.test.tsx.snap +0 -348
  230. package/packages/daemon/src/tui/mirror/workspace/__snapshots__/application-shell-renderer.test.tsx.snap +0 -134
  231. package/packages/daemon/src/tui/mirror/workspace/__snapshots__/command-palette-surface-renderer.test.tsx.snap +0 -255
  232. package/packages/daemon/src/tui/mirror/workspace/__snapshots__/pane-frame-renderer.test.tsx.snap +0 -525
  233. package/packages/daemon/src/tui/mirror/workspace/__snapshots__/terminal-pane-header-polish-renderer.test.tsx.snap +0 -31
  234. package/packages/daemon/src/tui/mirror/workspace/__snapshots__/workbench-shell-renderer.test.tsx.snap +0 -134
  235. package/packages/daemon-client/src/application-shell-session.test.ts +0 -196
  236. package/packages/daemon-client/src/automation-client.test.ts +0 -214
  237. package/packages/daemon-client/src/bootstrap-coordinator.test.ts +0 -145
  238. package/packages/daemon-client/src/connection-supervisor.test.ts +0 -109
  239. package/packages/daemon-client/src/direct-application-shell-transport.test.ts +0 -941
  240. package/packages/daemon-client/src/first-latest-coordinator.test.ts +0 -175
  241. package/packages/daemon-client/src/fleet-dial-scheduler.test.ts +0 -114
  242. package/packages/daemon-client/src/fleet-environments.test.ts +0 -40
  243. package/packages/daemon-client/src/generation-bound-store-timers.test.ts +0 -74
  244. package/packages/daemon-client/src/owner-action-client.test.ts +0 -245
  245. package/packages/daemon-client/src/pane-stream-client.test.ts +0 -2841
  246. package/packages/daemon-client/src/pane-stream-clock-calibration.test.ts +0 -207
  247. package/packages/daemon-client/src/pane-stream-loopback-benchmark.test.ts +0 -51
  248. package/packages/daemon-client/src/push-resource-session.test.ts +0 -509
  249. package/packages/daemon-client/src/resource-replica.test.ts +0 -186
  250. package/packages/daemon-client/src/runtime-resource-ledger.test.ts +0 -18
  251. package/packages/daemon-client/src/scoped-tmux-server-transport.test.ts +0 -114
  252. package/packages/daemon-client/src/terminal-fast-lane.test.ts +0 -835
  253. package/packages/daemon-client/src/tmux-server-client.test.ts +0 -279
  254. package/packages/daemon-client/src/tmux-server-interaction-events.test.ts +0 -230
  255. package/packages/daemon-client/src/workspace-catalog-v2.test.ts +0 -109
  256. package/packages/daemon-client/src/workspace-client-boundaries.test.ts +0 -59
  257. package/packages/daemon-client/src/workspace-client-operations.test.ts +0 -96
  258. package/packages/daemon-client/src/workspace-client.test.ts +0 -2912
  259. package/packages/daemon-client/src/workspace-event-supervisor.test.ts +0 -1086
  260. package/packages/daemon-client/src/workspace-pane-client.test.ts +0 -80
  261. package/packages/presentation/src/presentation-contract.test.ts +0 -63
  262. package/packages/tmux-bridge/src/runner.test.ts +0 -614
  263. package/packages/tmux-bridge/src/targeting.test.ts +0 -107
@@ -1,249 +0,0 @@
1
- import { describe, expect, it } from "vitest";
2
-
3
- import {
4
- WORKSPACE_PANE_CREATE_COMMAND_DESCRIPTOR,
5
- WORKSPACE_PANE_CREATE_COMMAND_ID,
6
- WorkspacePaneCreateInvocationSchemaZ,
7
- WorkspacePaneCreateHostResultSchemaZ,
8
- WorkspacePaneCreateMutationRequestSchemaZ,
9
- WorkspacePaneCreateMutationResultSchemaZ,
10
- WorkspacePaneCreationReferenceSchemaZ,
11
- WorkspacePaneCreationWorkspaceNameSchemaZ,
12
- workspacePaneCreateInvocation,
13
- } from "../workspace-pane-creation.ts";
14
-
15
- describe("semantic workspace pane creation command", () => {
16
- it("publishes one daemon-owned descriptor for every host surface", () => {
17
- expect(WORKSPACE_PANE_CREATE_COMMAND_DESCRIPTOR).toEqual({
18
- version: 1,
19
- id: WORKSPACE_PANE_CREATE_COMMAND_ID,
20
- owner: "daemon",
21
- label: "Create terminal or agent",
22
- description:
23
- "Ask the daemon to create a tmux-backed terminal or harness-backed agent from semantic workspace resources.",
24
- category: "workspace",
25
- schemas: {
26
- input: "workspace.pane.create.input.v1",
27
- result: "workspace.pane.create.result.v1",
28
- },
29
- dangerous: false,
30
- confirmation: "none",
31
- });
32
- expect(Object.isFrozen(WORKSPACE_PANE_CREATE_COMMAND_DESCRIPTOR)).toBe(true);
33
- });
34
-
35
- it("keeps host retry metadata outside renderer-authored semantic intent", () => {
36
- const request = WorkspacePaneCreateMutationRequestSchemaZ.parse({
37
- operationId: "10000000-0000-4000-8000-000000000001",
38
- expectedDaemonInstanceId: "20000000-0000-4000-8000-000000000002",
39
- intent: {
40
- kind: "agent",
41
- workspaceName: "tmux-ide",
42
- displayTitle: "Implementer",
43
- harnessProfileId: "codex",
44
- role: "implementer",
45
- },
46
- });
47
- expect(request.intent).not.toHaveProperty("operationId");
48
- expect(request.intent).not.toHaveProperty("expectedDaemonInstanceId");
49
- expect(
50
- WorkspacePaneCreateMutationRequestSchemaZ.safeParse({
51
- ...request,
52
- cwd: "/tmp/project",
53
- }).success,
54
- ).toBe(false);
55
- });
56
-
57
- it("returns stable semantic resource identity without daemon-private runtime facts", () => {
58
- const result = WorkspacePaneCreateMutationResultSchemaZ.parse({
59
- operationId: "10000000-0000-4000-8000-000000000001",
60
- daemonInstanceId: "20000000-0000-4000-8000-000000000002",
61
- outcome: "created",
62
- resource: {
63
- resourceVersion: 1,
64
- workspaceName: "tmux-ide",
65
- semanticPaneId: "pane.10000000000040008000000000000001",
66
- kind: "terminal",
67
- displayTitle: "Terminal",
68
- harnessProfileId: null,
69
- role: null,
70
- missionId: null,
71
- },
72
- });
73
- for (const forbidden of ["paneId", "windowId", "sessionName", "cwd", "argv", "env"]) {
74
- expect(JSON.stringify(result)).not.toContain(`"${forbidden}"`);
75
- }
76
- expect(WorkspacePaneCreateHostResultSchemaZ.parse({ status: "ok", result })).toEqual({
77
- status: "ok",
78
- result,
79
- });
80
- });
81
-
82
- it("round-trips a terminal request containing presentation identity only", () => {
83
- const invocation = workspacePaneCreateInvocation(
84
- {
85
- kind: "terminal",
86
- workspaceName: "tmux-ide/docs",
87
- displayTitle: "Release shell",
88
- },
89
- { kind: "palette", surface: "command-palette" },
90
- );
91
-
92
- expect(
93
- WorkspacePaneCreateInvocationSchemaZ.parse(JSON.parse(JSON.stringify(invocation))),
94
- ).toEqual(invocation);
95
- expect(invocation.args).not.toHaveProperty("cwd");
96
- expect(invocation.args).not.toHaveProperty("argv");
97
- expect(Object.isFrozen(invocation.args)).toBe(true);
98
- });
99
-
100
- it("round-trips an agent request using an exposed harness and mission identity", () => {
101
- expect(
102
- workspacePaneCreateInvocation(
103
- {
104
- kind: "agent",
105
- workspaceName: "tmux-ide",
106
- harnessProfileId: "codex-implementer",
107
- role: "implementer",
108
- missionId: "mis_gloomberb_parity",
109
- },
110
- { kind: "mouse", surface: "create-pane-dialog" },
111
- ),
112
- ).toMatchObject({
113
- id: WORKSPACE_PANE_CREATE_COMMAND_ID,
114
- args: {
115
- kind: "agent",
116
- harnessProfileId: "codex-implementer",
117
- role: "implementer",
118
- missionId: "mis_gloomberb_parity",
119
- },
120
- });
121
- });
122
-
123
- it("accepts split placement only through a durable semantic target", () => {
124
- const invocation = workspacePaneCreateInvocation(
125
- {
126
- kind: "agent",
127
- workspaceName: "tmux-ide",
128
- harnessProfileId: "codex",
129
- role: "implementer",
130
- placement: {
131
- kind: "split",
132
- direction: "right",
133
- targetSemanticPaneId: "pane.editor",
134
- },
135
- },
136
- { kind: "keyboard", surface: "terminals" },
137
- );
138
- expect(invocation.args.placement).toEqual({
139
- kind: "split",
140
- direction: "right",
141
- targetSemanticPaneId: "pane.editor",
142
- });
143
- expect(
144
- WorkspacePaneCreateInvocationSchemaZ.safeParse({
145
- ...invocation,
146
- args: {
147
- ...invocation.args,
148
- placement: { kind: "split", direction: "right", targetSemanticPaneId: "%42" },
149
- },
150
- }).success,
151
- ).toBe(false);
152
- });
153
-
154
- const forbiddenRuntimeFields = [
155
- ["cwd", "/Users/example/project"],
156
- ["argv", ["codex", "--yolo"]],
157
- ["command", "claude"],
158
- ["sessionName", "tmux-ide"],
159
- ["paneId", "%42"],
160
- ["token", "renderer-secret"],
161
- ["executable", "/usr/local/bin/codex"],
162
- ["env", { SECRET: "value" }],
163
- ["model", "provider-owned-model"],
164
- ] as const;
165
-
166
- it.each(forbiddenRuntimeFields)(
167
- "rejects terminal renderer-owned runtime field %s",
168
- (field, value) => {
169
- expect(
170
- WorkspacePaneCreateInvocationSchemaZ.safeParse({
171
- version: 1,
172
- id: WORKSPACE_PANE_CREATE_COMMAND_ID,
173
- source: { kind: "mouse", surface: "create-pane-dialog" },
174
- args: { kind: "terminal", workspaceName: "tmux-ide", [field]: value },
175
- }).success,
176
- ).toBe(false);
177
- },
178
- );
179
-
180
- it.each(forbiddenRuntimeFields)(
181
- "rejects agent renderer-owned runtime field %s",
182
- (field, value) => {
183
- expect(
184
- WorkspacePaneCreateInvocationSchemaZ.safeParse({
185
- version: 1,
186
- id: WORKSPACE_PANE_CREATE_COMMAND_ID,
187
- source: { kind: "mouse", surface: "create-pane-dialog" },
188
- args: {
189
- kind: "agent",
190
- workspaceName: "tmux-ide",
191
- harnessProfileId: "codex",
192
- role: "implementer",
193
- [field]: value,
194
- },
195
- }).success,
196
- ).toBe(false);
197
- },
198
- );
199
-
200
- it.each([
201
- ["token", "renderer-secret"],
202
- ["daemonUrl", "http://127.0.0.1:9999"],
203
- ["sessionName", "tmux-ide"],
204
- ["paneId", "%42"],
205
- ])("rejects invocation-level runtime field %s", (field, value) => {
206
- expect(
207
- WorkspacePaneCreateInvocationSchemaZ.safeParse({
208
- version: 1,
209
- id: WORKSPACE_PANE_CREATE_COMMAND_ID,
210
- source: { kind: "mouse", surface: "create-pane-dialog" },
211
- args: { kind: "terminal", workspaceName: "tmux-ide" },
212
- [field]: value,
213
- }).success,
214
- ).toBe(false);
215
- });
216
-
217
- it("uses canonical desktop workspace names losslessly, including slash names", () => {
218
- expect(WorkspacePaneCreationWorkspaceNameSchemaZ.parse("docs/site")).toBe("docs/site");
219
- expect(WorkspacePaneCreationWorkspaceNameSchemaZ.safeParse(" docs/site ").success).toBe(false);
220
- expect(WorkspacePaneCreationWorkspaceNameSchemaZ.safeParse("\u0000docs").success).toBe(false);
221
- });
222
-
223
- it.each(["%42", "$session", "@window", "/tmp/project", "folder\\project", " padded "])(
224
- "rejects raw runtime or path-shaped reference %s",
225
- (reference) => {
226
- expect(WorkspacePaneCreationReferenceSchemaZ.safeParse(reference).success).toBe(false);
227
- },
228
- );
229
-
230
- it("rejects C0, DEL, and C1 controls from titles and semantic references", () => {
231
- for (const control of ["\u0009", "\u007f", "\u0085"]) {
232
- expect(WorkspacePaneCreationReferenceSchemaZ.safeParse(`agent${control}one`).success).toBe(
233
- false,
234
- );
235
- expect(
236
- WorkspacePaneCreateInvocationSchemaZ.safeParse({
237
- version: 1,
238
- id: WORKSPACE_PANE_CREATE_COMMAND_ID,
239
- source: { kind: "mouse" },
240
- args: {
241
- kind: "terminal",
242
- workspaceName: "tmux-ide",
243
- displayTitle: `Terminal${control}one`,
244
- },
245
- }).success,
246
- ).toBe(false);
247
- }
248
- });
249
- });
@@ -1,94 +0,0 @@
1
- import { describe, expect, it } from "vitest";
2
-
3
- import {
4
- WorkspacePromoteArgumentsSchemaZ,
5
- WorkspacePromoteMutationRequestSchemaZ,
6
- WorkspacePromoteMutationResultSchemaZ,
7
- WorkspacePromotedResourceSchemaZ,
8
- } from "../workspace-promotion.ts";
9
-
10
- const DAEMON = "20000000-0000-4000-8000-000000000002";
11
- const OPERATION = "10000000-0000-4000-8000-000000000001";
12
-
13
- describe("workspace promotion contract", () => {
14
- it("accepts an opaque fleet session id as the promotion target", () => {
15
- const parsed = WorkspacePromoteArgumentsSchemaZ.parse({
16
- sessionId: "session.0123456789abcdef0123",
17
- });
18
- expect(parsed.sessionId).toBe("session.0123456789abcdef0123");
19
- });
20
-
21
- it("rejects a raw tmux session name or id as the target", () => {
22
- expect(WorkspacePromoteArgumentsSchemaZ.safeParse({ sessionId: "$3" }).success).toBe(false);
23
- expect(WorkspacePromoteArgumentsSchemaZ.safeParse({ sessionId: "my session" }).success).toBe(
24
- false,
25
- );
26
- expect(
27
- WorkspacePromoteArgumentsSchemaZ.safeParse({ sessionId: "/home/user/project" }).success,
28
- ).toBe(false);
29
- });
30
-
31
- it("requires the operation and daemon-generation envelope", () => {
32
- const request = WorkspacePromoteMutationRequestSchemaZ.parse({
33
- operationId: OPERATION,
34
- expectedDaemonInstanceId: DAEMON,
35
- intent: { sessionId: "session.0123456789abcdef0123" },
36
- });
37
- expect(request.operationId).toBe(OPERATION);
38
- expect(
39
- WorkspacePromoteMutationRequestSchemaZ.safeParse({
40
- operationId: "not-a-uuid",
41
- expectedDaemonInstanceId: DAEMON,
42
- intent: { sessionId: "session.0123456789abcdef0123" },
43
- }).success,
44
- ).toBe(false);
45
- });
46
-
47
- it("carries only the workspace name in the wire-safe result", () => {
48
- const result = WorkspacePromoteMutationResultSchemaZ.parse({
49
- operationId: OPERATION,
50
- daemonInstanceId: DAEMON,
51
- outcome: "promoted",
52
- resource: {
53
- resourceVersion: 1,
54
- workspaceName: "fleet-alpha-0123456789abcdef0123456789abcdef",
55
- },
56
- });
57
- expect(result.outcome).toBe("promoted");
58
- // The resource is strictly the version + workspace name — no path or id keys.
59
- expect(Object.keys(result.resource).sort()).toEqual(["resourceVersion", "workspaceName"]);
60
- });
61
-
62
- it("only permits the promoted and replayed outcomes", () => {
63
- for (const outcome of ["promoted", "replayed"] as const) {
64
- expect(
65
- WorkspacePromoteMutationResultSchemaZ.safeParse({
66
- operationId: OPERATION,
67
- daemonInstanceId: DAEMON,
68
- outcome,
69
- resource: { resourceVersion: 1, workspaceName: "w" },
70
- }).success,
71
- ).toBe(true);
72
- }
73
- for (const outcome of ["created", "reopened"]) {
74
- expect(
75
- WorkspacePromoteMutationResultSchemaZ.safeParse({
76
- operationId: OPERATION,
77
- daemonInstanceId: DAEMON,
78
- outcome,
79
- resource: { resourceVersion: 1, workspaceName: "w" },
80
- }).success,
81
- ).toBe(false);
82
- }
83
- });
84
-
85
- it("rejects an extra key on the promoted resource", () => {
86
- expect(
87
- WorkspacePromotedResourceSchemaZ.safeParse({
88
- resourceVersion: 1,
89
- workspaceName: "w",
90
- projectDir: "/home/user/project",
91
- }).success,
92
- ).toBe(false);
93
- });
94
- });
@@ -1,90 +0,0 @@
1
- import { describe, expect, it } from "vitest";
2
- import {
3
- WorkspaceChangeResourceIdSchemaZ,
4
- WorkspaceChangesRevisionSchemaZ,
5
- WorkspaceFileResourceIdSchemaZ,
6
- WorkspaceFilesRevisionSchemaZ,
7
- WorkspaceRelativeDisplayPathSchemaZ,
8
- WorkspaceResourceNameSchemaZ,
9
- WorkspaceResourceOpaqueTokenSchemaZ,
10
- WorkspaceResourceWorkspaceNameSchemaZ,
11
- } from "../workspace-resource-identity.ts";
12
-
13
- const NUL = String.fromCharCode(0);
14
- const BELL = String.fromCharCode(7);
15
- const TAB = String.fromCharCode(9);
16
- const DEL = String.fromCharCode(127);
17
-
18
- describe("workspace resource identity", () => {
19
- it("accepts prefixed opaque ids and rejects path-shaped or reserved values", () => {
20
- expect(WorkspaceFileResourceIdSchemaZ.safeParse("file.0123456789abcdef").success).toBe(true);
21
- expect(WorkspaceChangeResourceIdSchemaZ.safeParse("change.0123456789abcdef").success).toBe(
22
- true,
23
- );
24
- expect(WorkspaceFilesRevisionSchemaZ.safeParse("files-rev.0123456789abcdef").success).toBe(
25
- true,
26
- );
27
- expect(WorkspaceChangesRevisionSchemaZ.safeParse("changes-rev.0123456789abcdef").success).toBe(
28
- true,
29
- );
30
-
31
- // Wrong prefix, missing prefix, and cross-prefix are all rejected.
32
- expect(WorkspaceFileResourceIdSchemaZ.safeParse("change.0123456789abcdef").success).toBe(false);
33
- expect(WorkspaceFileResourceIdSchemaZ.safeParse("0123456789abcdef").success).toBe(false);
34
- // A path separator can never appear inside an opaque id.
35
- expect(WorkspaceFileResourceIdSchemaZ.safeParse("file.../etc/passwd").success).toBe(false);
36
- expect(WorkspaceFileResourceIdSchemaZ.safeParse("file.a/b0123456789abcd").success).toBe(false);
37
- // Reserved record keys cannot masquerade as an id.
38
- expect(WorkspaceFileResourceIdSchemaZ.safeParse("__proto__").success).toBe(false);
39
- expect(WorkspaceFileResourceIdSchemaZ.safeParse("file.__proto__").success).toBe(false);
40
- // Length bounds: too short, and past the 64-char token ceiling.
41
- expect(WorkspaceFileResourceIdSchemaZ.safeParse("file.short").success).toBe(false);
42
- expect(WorkspaceFileResourceIdSchemaZ.safeParse(`file.${"a".repeat(65)}`).success).toBe(false);
43
- });
44
-
45
- it("bounds the bare opaque token", () => {
46
- expect(WorkspaceResourceOpaqueTokenSchemaZ.safeParse("0123456789abcdef").success).toBe(true);
47
- expect(WorkspaceResourceOpaqueTokenSchemaZ.safeParse("short").success).toBe(false);
48
- expect(WorkspaceResourceOpaqueTokenSchemaZ.safeParse("has/slash012345678").success).toBe(false);
49
- });
50
-
51
- it("treats a resource name as a single sanitized path segment", () => {
52
- expect(WorkspaceResourceNameSchemaZ.safeParse("index.ts").success).toBe(true);
53
- expect(WorkspaceResourceNameSchemaZ.safeParse(".gitignore").success).toBe(true);
54
-
55
- expect(WorkspaceResourceNameSchemaZ.safeParse(".").success).toBe(false);
56
- expect(WorkspaceResourceNameSchemaZ.safeParse("..").success).toBe(false);
57
- expect(WorkspaceResourceNameSchemaZ.safeParse("").success).toBe(false);
58
- expect(WorkspaceResourceNameSchemaZ.safeParse("a/b").success).toBe(false);
59
- expect(WorkspaceResourceNameSchemaZ.safeParse("a\\b").success).toBe(false);
60
- expect(WorkspaceResourceNameSchemaZ.safeParse(`a${NUL}b`).success).toBe(false);
61
- expect(WorkspaceResourceNameSchemaZ.safeParse(`a${BELL}b`).success).toBe(false);
62
- expect(WorkspaceResourceNameSchemaZ.safeParse(`a${DEL}b`).success).toBe(false);
63
- expect(WorkspaceResourceNameSchemaZ.safeParse("a".repeat(256)).success).toBe(false);
64
- });
65
-
66
- it("keeps display paths relative, forward-slashed, and control-free", () => {
67
- expect(WorkspaceRelativeDisplayPathSchemaZ.safeParse("src/index.ts").success).toBe(true);
68
- expect(WorkspaceRelativeDisplayPathSchemaZ.safeParse("README.md").success).toBe(true);
69
-
70
- expect(WorkspaceRelativeDisplayPathSchemaZ.safeParse("/etc/passwd").success).toBe(false);
71
- expect(WorkspaceRelativeDisplayPathSchemaZ.safeParse("../secret").success).toBe(false);
72
- expect(WorkspaceRelativeDisplayPathSchemaZ.safeParse("src/../secret").success).toBe(false);
73
- expect(WorkspaceRelativeDisplayPathSchemaZ.safeParse("a//b").success).toBe(false);
74
- expect(WorkspaceRelativeDisplayPathSchemaZ.safeParse("src\\index.ts").success).toBe(false);
75
- expect(WorkspaceRelativeDisplayPathSchemaZ.safeParse("src/.").success).toBe(false);
76
- expect(WorkspaceRelativeDisplayPathSchemaZ.safeParse(`a${TAB}b`).success).toBe(false);
77
- expect(WorkspaceRelativeDisplayPathSchemaZ.safeParse(`a${DEL}b`).success).toBe(false);
78
- expect(WorkspaceRelativeDisplayPathSchemaZ.safeParse("a".repeat(1_025)).success).toBe(false);
79
- });
80
-
81
- it("accepts a semantic workspace name but rejects control characters", () => {
82
- expect(WorkspaceResourceWorkspaceNameSchemaZ.safeParse("tmux-ide").success).toBe(true);
83
- expect(WorkspaceResourceWorkspaceNameSchemaZ.parse(" spaced name ")).toBe("spaced name");
84
-
85
- expect(WorkspaceResourceWorkspaceNameSchemaZ.safeParse("").success).toBe(false);
86
- expect(WorkspaceResourceWorkspaceNameSchemaZ.safeParse(`with${NUL}nul`).success).toBe(false);
87
- expect(WorkspaceResourceWorkspaceNameSchemaZ.safeParse(`with${DEL}del`).success).toBe(false);
88
- expect(WorkspaceResourceWorkspaceNameSchemaZ.safeParse("a".repeat(161)).success).toBe(false);
89
- });
90
- });
@@ -1,192 +0,0 @@
1
- import { describe, expect, it, vi } from "vitest";
2
-
3
- import {
4
- DAEMON_RESOURCE_KINDS,
5
- DAEMON_RESOURCE_RESULT_SCHEMAS,
6
- DAEMON_WORKSPACE_ROUTE_KEYS,
7
- DaemonResourceRequestSchemaZ,
8
- createDaemonResourceMethods,
9
- daemonWorkspaceRouteName,
10
- isDaemonResourceKind,
11
- type DaemonResourceRequest,
12
- } from "./daemon-resource-request.ts";
13
-
14
- const WORKSPACE = "product";
15
- const FILE_ID = "file.00112233445566778899aabbccddeeff";
16
- const CHANGE_ID = "change.00112233445566778899aabbccddeeff";
17
-
18
- /** One valid request per variant: the round-trip corpus. */
19
- const REQUESTS: readonly DaemonResourceRequest[] = [
20
- { resource: "capabilities" },
21
- { resource: "refreshConnection" },
22
- { resource: "listWorkspaces" },
23
- { resource: "fetchFleetCatalog" },
24
- { resource: "fetchWorkspaceCatalog" },
25
- { resource: "fetchWidgetAsset", request: { assetId: "a".repeat(64) } },
26
- { resource: "startupReadiness" },
27
- { resource: "fetchApplicationShell", request: { workspaceName: WORKSPACE } },
28
- { resource: "fetchWorkspaceFiles", request: { workspaceName: WORKSPACE } },
29
- {
30
- resource: "fetchWorkspaceFilePreview",
31
- request: { workspaceName: WORKSPACE, fileId: FILE_ID },
32
- },
33
- { resource: "fetchWorkspaceChanges", request: { workspaceName: WORKSPACE } },
34
- { resource: "fetchWorkspaceMissions", request: { workspaceName: WORKSPACE } },
35
- {
36
- resource: "fetchWorkspaceChangeDiff",
37
- request: { workspaceName: WORKSPACE, changeId: CHANGE_ID },
38
- },
39
- {
40
- resource: "promoteWorkspace",
41
- request: { sessionId: "session.00112233445566778899aabbccddeeff" },
42
- },
43
- {
44
- resource: "createWorkspacePane",
45
- request: {
46
- version: 1,
47
- id: "workspace.pane.create",
48
- source: { kind: "mouse", surface: "create-pane-dialog" },
49
- args: { kind: "terminal", workspaceName: WORKSPACE },
50
- },
51
- },
52
- {
53
- resource: "mutateAppWindow",
54
- request: {
55
- intent: {
56
- workspaceName: WORKSPACE,
57
- expectedDocumentRevision: 4,
58
- command: { type: "window.move", windowId: "window.worker", x: 10, y: 20 },
59
- },
60
- },
61
- },
62
- {
63
- resource: "invokeVerb",
64
- request: {
65
- verbId: "pane.split.right",
66
- intent: {
67
- verb: "workspace.window.split",
68
- workspaceName: WORKSPACE,
69
- semanticPaneId: "pane.worker",
70
- direction: "right",
71
- },
72
- },
73
- },
74
- {
75
- resource: "issueTerminalAttachment",
76
- request: {
77
- protocolVersion: 1,
78
- target: { workspaceName: WORKSPACE, semanticPaneId: "pane.worker" },
79
- viewerMode: "interactive",
80
- geometryOwnership: "passive",
81
- viewport: { cols: 120, rows: 40 },
82
- },
83
- },
84
- {
85
- resource: "issuePaneStream",
86
- request: {
87
- protocolVersion: 2,
88
- workspaceName: WORKSPACE,
89
- panes: ["pane.worker"],
90
- viewerMode: "read-only",
91
- },
92
- },
93
- ];
94
-
95
- describe("daemon resource request union", () => {
96
- it("covers every declared resource exactly once", () => {
97
- expect([...REQUESTS].map((request) => request.resource).sort()).toEqual(
98
- [...DAEMON_RESOURCE_KINDS].sort(),
99
- );
100
- expect(Object.keys(DAEMON_RESOURCE_RESULT_SCHEMAS).sort()).toEqual(
101
- [...DAEMON_RESOURCE_KINDS].sort(),
102
- );
103
- });
104
-
105
- it("round-trips every variant unchanged", () => {
106
- for (const request of REQUESTS) {
107
- const parsed = DaemonResourceRequestSchemaZ.parse(JSON.parse(JSON.stringify(request)));
108
- expect(parsed).toEqual(request);
109
- }
110
- });
111
-
112
- it("refuses an unknown tag, a missing tag, and a payload on a payload-free resource", () => {
113
- expect(DaemonResourceRequestSchemaZ.safeParse({ resource: "readEverything" }).success).toBe(
114
- false,
115
- );
116
- expect(DaemonResourceRequestSchemaZ.safeParse({}).success).toBe(false);
117
- expect(DaemonResourceRequestSchemaZ.safeParse(null).success).toBe(false);
118
- expect(
119
- DaemonResourceRequestSchemaZ.safeParse({
120
- resource: "capabilities",
121
- request: { escalate: true },
122
- }).success,
123
- ).toBe(false);
124
- });
125
-
126
- it("refuses a payload borrowed from another variant", () => {
127
- expect(
128
- DaemonResourceRequestSchemaZ.safeParse({
129
- resource: "fetchWorkspaceChangeDiff",
130
- request: { workspaceName: WORKSPACE },
131
- }).success,
132
- ).toBe(false);
133
- });
134
-
135
- it("names a resource kind only for declared resources", () => {
136
- for (const kind of DAEMON_RESOURCE_KINDS) expect(isDaemonResourceKind(kind)).toBe(true);
137
- expect(isDaemonResourceKind("subscribe")).toBe(false);
138
- expect(isDaemonResourceKind("toString")).toBe(false);
139
- expect(isDaemonResourceKind(undefined)).toBe(false);
140
- });
141
-
142
- it("keys the application-shell route on the session name and the rest on the workspace", () => {
143
- const entry = { workspaceName: "product", sessionName: "tmux-product" };
144
- expect(daemonWorkspaceRouteName("fetchApplicationShell", entry)).toBe("tmux-product");
145
- for (const resource of ["fetchWorkspaceFiles", "fetchWorkspaceChangeDiff"] as const) {
146
- expect(daemonWorkspaceRouteName(resource, entry)).toBe("product");
147
- }
148
- // The table is the only declaration of the fork; every workspace-keyed
149
- // resource must appear in it.
150
- expect(Object.keys(DAEMON_WORKSPACE_ROUTE_KEYS).sort()).toEqual([
151
- "fetchApplicationShell",
152
- "fetchWorkspaceChangeDiff",
153
- "fetchWorkspaceChanges",
154
- "fetchWorkspaceFilePreview",
155
- "fetchWorkspaceFiles",
156
- "fetchWorkspaceMissions",
157
- ]);
158
- });
159
-
160
- it("builds one method per resource over a single dispatcher", async () => {
161
- const seen: DaemonResourceRequest[] = [];
162
- const methods = createDaemonResourceMethods(async (request) => {
163
- seen.push(request);
164
- return { status: "error", error: { code: "disposed", reason: "test" } };
165
- });
166
- for (const kind of DAEMON_RESOURCE_KINDS) {
167
- expect(typeof methods[kind]).toBe("function");
168
- }
169
- await methods.listWorkspaces();
170
- await methods.fetchWorkspaceCatalog();
171
- await methods.fetchWorkspaceChanges({ workspaceName: WORKSPACE });
172
- expect(seen).toEqual([
173
- { resource: "listWorkspaces" },
174
- { resource: "fetchWorkspaceCatalog" },
175
- { resource: "fetchWorkspaceChanges", request: { workspaceName: WORKSPACE } },
176
- ]);
177
- });
178
-
179
- it("preserves the one-argument dispatcher contract when no signal is supplied", async () => {
180
- const dispatch = vi.fn(async () => ({
181
- status: "error",
182
- error: { code: "disposed", reason: "test" },
183
- }));
184
- const methods = createDaemonResourceMethods(dispatch);
185
- await methods.capabilities();
186
- await methods.fetchWorkspaceFiles({ workspaceName: WORKSPACE });
187
- expect(dispatch.mock.calls[0]).toEqual([{ resource: "capabilities" }]);
188
- expect(dispatch.mock.calls[1]).toEqual([
189
- { resource: "fetchWorkspaceFiles", request: { workspaceName: WORKSPACE } },
190
- ]);
191
- });
192
- });
@@ -1,23 +0,0 @@
1
- import { expect, it } from "vitest";
2
- import { NativeOperationIdentitySchemaZ } from "./native-operation-identity.ts";
3
- const ack = {
4
- schemaVersion: 2,
5
- type: "operation-identity",
6
- serverEpoch: "00000000-0000-4000-8000-000000000001",
7
- operationId: "00000000-0000-4000-8000-000000000002",
8
- connectionId: "1",
9
- wrapperCommandId: "18446744073709551615",
10
- };
11
- it("accepts only bounded positive native identity and strict metadata", () => {
12
- expect(NativeOperationIdentitySchemaZ.parse(ack)).toEqual(ack);
13
- for (const bad of [
14
- { connectionId: "0" },
15
- { wrapperCommandId: "0" },
16
- { wrapperCommandId: "18446744073709551616" },
17
- { connectionId: "01" },
18
- { text: "secret" },
19
- { serverEpoch: "invalid" },
20
- { operationId: "invalid" },
21
- ])
22
- expect(NativeOperationIdentitySchemaZ.safeParse({ ...ack, ...bad }).success).toBe(false);
23
- });
@@ -1,21 +0,0 @@
1
- import { expect, it } from "vitest";
2
- import { WorkspaceAdmissionSnapshotSchemaZ } from "./workspace-admission.ts";
3
- const snapshot = {
4
- pending: 0,
5
- limit: 128,
6
- disposed: false,
7
- retained: 128,
8
- retentionLimit: 128,
9
- retentionMayBlock: false,
10
- };
11
- it("keeps admission separate from retained history and validates bounded diagnostic fields", () => {
12
- expect(WorkspaceAdmissionSnapshotSchemaZ.parse(snapshot)).toEqual(snapshot);
13
- for (const invalid of [
14
- { ...snapshot, pending: -1 },
15
- { ...snapshot, pending: Number.POSITIVE_INFINITY },
16
- { ...snapshot, retained: Number.MAX_SAFE_INTEGER + 1 },
17
- { ...snapshot, limit: 0 },
18
- { ...snapshot, authToken: "secret" },
19
- ])
20
- expect(WorkspaceAdmissionSnapshotSchemaZ.safeParse(invalid).success).toBe(false);
21
- });