@ours.network/fleet 1.2.0-nightly.34 → 1.2.0-nightly.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.
- package/README.md +28 -49
- package/dist/application/codex-models.d.ts +15 -0
- package/dist/application/codex-models.js +56 -0
- package/dist/build-info.json +4 -4
- package/dist/cli.js +11 -41
- package/dist/config.d.ts +2 -0
- package/dist/config.js +1 -1
- package/dist/docs.d.ts +1 -1
- package/dist/docs.js +10 -15
- package/dist/harness/codex-runtime.d.ts +11 -1
- package/dist/harness/codex-runtime.js +31 -4
- package/dist/harness/codex.js +4 -2
- package/dist/init-wizard.js +2 -1
- package/dist/minimal-setup.js +2 -1
- package/dist/paths.d.ts +2 -0
- package/dist/paths.js +2 -0
- package/dist/rooms-tasks/config.d.ts +1 -1
- package/dist/rooms-tasks/config.js +8 -3
- package/dist/subscriptions/cli.d.ts +15 -2
- package/dist/subscriptions/cli.js +41 -4
- package/dist/web/auth.d.ts +1 -1
- package/dist/web/auth.js +2 -5
- package/dist/web/control.d.ts +1 -2
- package/dist/web/control.js +0 -2
- package/dist/web/prefix-gateway.js +2 -7
- package/dist/web/runtime.d.ts +0 -2
- package/dist/web/runtime.js +3 -18
- package/dist/web/server.d.ts +3 -1
- package/dist/web/server.js +14 -35
- package/dist/workspace-enrollment.d.ts +17 -0
- package/dist/workspace-enrollment.js +117 -9
- package/package.json +2 -3
- package/presets/fleet/agent_templates/Critic.yaml +1 -1
- package/presets/fleet/agent_templates/Developer.yaml +1 -1
- package/presets/fleet/agent_templates/Engineer.yaml +1 -1
- package/presets/fleet/agent_templates/LocalCoordinator.yaml +1 -1
- package/presets/fleet/agents/FleetCoordinator.yaml +1 -1
- package/presets/fleet/roles/Coordinator.yaml +6 -0
- package/presets/manifest.json +1 -1
- package/dist/web-app/assets/FleetApp-D58F4xje.css +0 -1
- package/dist/web-app/assets/FleetApp-Gjz3h8uS.js +0 -302
- package/dist/web-app/assets/FleetApp-Gjz3h8uS.js.map +0 -1
- package/dist/web-app/assets/abnfDiagram-VCTEODGH-t4h5V8Cs.js +0 -2
- package/dist/web-app/assets/abnfDiagram-VCTEODGH-t4h5V8Cs.js.map +0 -1
- package/dist/web-app/assets/arc-DbufDTF6.js +0 -2
- package/dist/web-app/assets/arc-DbufDTF6.js.map +0 -1
- package/dist/web-app/assets/architectureDiagram-5GKGNRK7-D6K8jMN5.js +0 -37
- package/dist/web-app/assets/architectureDiagram-5GKGNRK7-D6K8jMN5.js.map +0 -1
- package/dist/web-app/assets/blockDiagram-I7D4REHJ-CWvkET2x.js +0 -130
- package/dist/web-app/assets/blockDiagram-I7D4REHJ-CWvkET2x.js.map +0 -1
- package/dist/web-app/assets/browser-B7y08DsC.js +0 -9
- package/dist/web-app/assets/browser-B7y08DsC.js.map +0 -1
- package/dist/web-app/assets/c4Diagram-7LVT6UL2-RNWA7VnD.js +0 -39
- package/dist/web-app/assets/c4Diagram-7LVT6UL2-RNWA7VnD.js.map +0 -1
- package/dist/web-app/assets/channel-BF3U9sI8.js +0 -2
- package/dist/web-app/assets/channel-BF3U9sI8.js.map +0 -1
- package/dist/web-app/assets/chunk-2Q5K7J3B-pdEuY4vj.js +0 -2
- package/dist/web-app/assets/chunk-2Q5K7J3B-pdEuY4vj.js.map +0 -1
- package/dist/web-app/assets/chunk-5VM5RSS4-DuAUtdUC.js +0 -16
- package/dist/web-app/assets/chunk-5VM5RSS4-DuAUtdUC.js.map +0 -1
- package/dist/web-app/assets/chunk-F27PBJKO-6kpb80Xt.js +0 -2
- package/dist/web-app/assets/chunk-F27PBJKO-6kpb80Xt.js.map +0 -1
- package/dist/web-app/assets/chunk-IMKFNOWR-DWC84P6A.js +0 -232
- package/dist/web-app/assets/chunk-IMKFNOWR-DWC84P6A.js.map +0 -1
- package/dist/web-app/assets/chunk-JWPE2WC7-FHO-M3vi.js +0 -2
- package/dist/web-app/assets/chunk-JWPE2WC7-FHO-M3vi.js.map +0 -1
- package/dist/web-app/assets/chunk-POPQ4Y6H-CjnlKvmR.js +0 -2
- package/dist/web-app/assets/chunk-POPQ4Y6H-CjnlKvmR.js.map +0 -1
- package/dist/web-app/assets/chunk-SVP7TREG-WHYWJ6xq.js +0 -89
- package/dist/web-app/assets/chunk-SVP7TREG-WHYWJ6xq.js.map +0 -1
- package/dist/web-app/assets/chunk-TICWLB2K-POupMpyL.js +0 -207
- package/dist/web-app/assets/chunk-TICWLB2K-POupMpyL.js.map +0 -1
- package/dist/web-app/assets/chunk-XXDRQBXY-Cw5HHqH-.js +0 -2
- package/dist/web-app/assets/chunk-XXDRQBXY-Cw5HHqH-.js.map +0 -1
- package/dist/web-app/assets/classDiagram-ZZMXUADV-1hdMzIme.js +0 -2
- package/dist/web-app/assets/classDiagram-ZZMXUADV-1hdMzIme.js.map +0 -1
- package/dist/web-app/assets/classDiagram-v2-VYDZK3BY-1hdMzIme.js +0 -2
- package/dist/web-app/assets/classDiagram-v2-VYDZK3BY-1hdMzIme.js.map +0 -1
- package/dist/web-app/assets/cose-bilkent-JH36ORCC-Cp6Hjine.js +0 -2
- package/dist/web-app/assets/cose-bilkent-JH36ORCC-Cp6Hjine.js.map +0 -1
- package/dist/web-app/assets/cynefin-OW5HDTMX-DI-DeNUk.js +0 -179
- package/dist/web-app/assets/cynefin-OW5HDTMX-DI-DeNUk.js.map +0 -1
- package/dist/web-app/assets/cynefinDiagram-5FMLGOSQ-todBCANI.js +0 -63
- package/dist/web-app/assets/cynefinDiagram-5FMLGOSQ-todBCANI.js.map +0 -1
- package/dist/web-app/assets/cytoscape.esm-CtNdOvlO.js +0 -332
- package/dist/web-app/assets/cytoscape.esm-CtNdOvlO.js.map +0 -1
- package/dist/web-app/assets/dagre-GXQ25YYZ-BvIVo7eh.js +0 -5
- package/dist/web-app/assets/dagre-GXQ25YYZ-BvIVo7eh.js.map +0 -1
- package/dist/web-app/assets/defaultLocale-DX6XiGOO.js +0 -2
- package/dist/web-app/assets/defaultLocale-DX6XiGOO.js.map +0 -1
- package/dist/web-app/assets/diagram-S7CK7UJ4-k9vDGlB5.js +0 -31
- package/dist/web-app/assets/diagram-S7CK7UJ4-k9vDGlB5.js.map +0 -1
- package/dist/web-app/assets/diagram-UQ7AKVKN-Bv7BT1dE.js +0 -42
- package/dist/web-app/assets/diagram-UQ7AKVKN-Bv7BT1dE.js.map +0 -1
- package/dist/web-app/assets/diagram-VSXAHHWV-m9I9AumX.js +0 -4
- package/dist/web-app/assets/diagram-VSXAHHWV-m9I9AumX.js.map +0 -1
- package/dist/web-app/assets/diagram-VX7I27RA-4VJ2qozS.js +0 -25
- package/dist/web-app/assets/diagram-VX7I27RA-4VJ2qozS.js.map +0 -1
- package/dist/web-app/assets/diagram-Z3DM3KII-CvH8JIEd.js +0 -25
- package/dist/web-app/assets/diagram-Z3DM3KII-CvH8JIEd.js.map +0 -1
- package/dist/web-app/assets/ebnfDiagram-PWID7BFC-DAGs23hd.js +0 -2
- package/dist/web-app/assets/ebnfDiagram-PWID7BFC-DAGs23hd.js.map +0 -1
- package/dist/web-app/assets/erDiagram-RLTQ6QDP-CEMyWKIa.js +0 -100
- package/dist/web-app/assets/erDiagram-RLTQ6QDP-CEMyWKIa.js.map +0 -1
- package/dist/web-app/assets/flowDiagram-HODETNUW-BnraxJTV.js +0 -169
- package/dist/web-app/assets/flowDiagram-HODETNUW-BnraxJTV.js.map +0 -1
- package/dist/web-app/assets/ganttDiagram-EL5Y4UJY-V6d4ICW0.js +0 -293
- package/dist/web-app/assets/ganttDiagram-EL5Y4UJY-V6d4ICW0.js.map +0 -1
- package/dist/web-app/assets/gitGraphDiagram-WWUBYQGX-Bj_gqcba.js +0 -107
- package/dist/web-app/assets/gitGraphDiagram-WWUBYQGX-Bj_gqcba.js.map +0 -1
- package/dist/web-app/assets/index-C4BdeFB9.css +0 -1
- package/dist/web-app/assets/index-i9rKiqYX.js +0 -430
- package/dist/web-app/assets/index-i9rKiqYX.js.map +0 -1
- package/dist/web-app/assets/infoDiagram-27XIBGKW-Dfm89NLl.js +0 -3
- package/dist/web-app/assets/infoDiagram-27XIBGKW-Dfm89NLl.js.map +0 -1
- package/dist/web-app/assets/init-Gi6I4Gst.js +0 -2
- package/dist/web-app/assets/init-Gi6I4Gst.js.map +0 -1
- package/dist/web-app/assets/ishikawaDiagram-5VMMS53U-D-ISiJTS.js +0 -71
- package/dist/web-app/assets/ishikawaDiagram-5VMMS53U-D-ISiJTS.js.map +0 -1
- package/dist/web-app/assets/jetbrains-mono-cyrillic-wght-normal-D73BlboJ.woff2 +0 -0
- package/dist/web-app/assets/jetbrains-mono-greek-wght-normal-Bw9x6K1M.woff2 +0 -0
- package/dist/web-app/assets/jetbrains-mono-latin-ext-wght-normal-DBQx-q_a.woff2 +0 -0
- package/dist/web-app/assets/jetbrains-mono-latin-wght-normal-B9CIFXIH.woff2 +0 -0
- package/dist/web-app/assets/jetbrains-mono-vietnamese-wght-normal-Bt-aOZkq.woff2 +0 -0
- package/dist/web-app/assets/journeyDiagram-3NMN7TZE-TTySrzws.js +0 -140
- package/dist/web-app/assets/journeyDiagram-3NMN7TZE-TTySrzws.js.map +0 -1
- package/dist/web-app/assets/kanban-definition-UXKFOSKX-BxntsBft.js +0 -90
- package/dist/web-app/assets/kanban-definition-UXKFOSKX-BxntsBft.js.map +0 -1
- package/dist/web-app/assets/katex-HP8lGamR.js +0 -258
- package/dist/web-app/assets/katex-HP8lGamR.js.map +0 -1
- package/dist/web-app/assets/layout-0sZak8Ho.js +0 -2
- package/dist/web-app/assets/layout-0sZak8Ho.js.map +0 -1
- package/dist/web-app/assets/linear-D4xk4kUi.js +0 -2
- package/dist/web-app/assets/linear-D4xk4kUi.js.map +0 -1
- package/dist/web-app/assets/mermaid.core-CNKolAgz.js +0 -313
- package/dist/web-app/assets/mermaid.core-CNKolAgz.js.map +0 -1
- package/dist/web-app/assets/mindmap-definition-YA3MSWOX-DLJijY_l.js +0 -97
- package/dist/web-app/assets/mindmap-definition-YA3MSWOX-DLJijY_l.js.map +0 -1
- package/dist/web-app/assets/ordinal-Cboi1Yqb.js +0 -2
- package/dist/web-app/assets/ordinal-Cboi1Yqb.js.map +0 -1
- package/dist/web-app/assets/pegDiagram-XKGWAZYB-xjrh9rBd.js +0 -2
- package/dist/web-app/assets/pegDiagram-XKGWAZYB-xjrh9rBd.js.map +0 -1
- package/dist/web-app/assets/pieDiagram-E7YTZNPT-CHE8ZMXN.js +0 -40
- package/dist/web-app/assets/pieDiagram-E7YTZNPT-CHE8ZMXN.js.map +0 -1
- package/dist/web-app/assets/quadrantDiagram-AXDQQJYC-CDlEe9sg.js +0 -8
- package/dist/web-app/assets/quadrantDiagram-AXDQQJYC-CDlEe9sg.js.map +0 -1
- package/dist/web-app/assets/railroadDiagram-O6MQD6OU-Dv7lFZ_v.js +0 -2
- package/dist/web-app/assets/railroadDiagram-O6MQD6OU-Dv7lFZ_v.js.map +0 -1
- package/dist/web-app/assets/requirementDiagram-BXWQKSXE-BetEel-k.js +0 -85
- package/dist/web-app/assets/requirementDiagram-BXWQKSXE-BetEel-k.js.map +0 -1
- package/dist/web-app/assets/sankeyDiagram-P5KCCOFB-DCQgLfvK.js +0 -41
- package/dist/web-app/assets/sankeyDiagram-P5KCCOFB-DCQgLfvK.js.map +0 -1
- package/dist/web-app/assets/sequenceDiagram-WJ2MYXX4-CsGOoqu_.js +0 -163
- package/dist/web-app/assets/sequenceDiagram-WJ2MYXX4-CsGOoqu_.js.map +0 -1
- package/dist/web-app/assets/sizeCapture-INFHLROL-CLQRMiEc.js +0 -2
- package/dist/web-app/assets/sizeCapture-INFHLROL-CLQRMiEc.js.map +0 -1
- package/dist/web-app/assets/stateDiagram-D77RDMKH-D2MRdC5Q.js +0 -2
- package/dist/web-app/assets/stateDiagram-D77RDMKH-D2MRdC5Q.js.map +0 -1
- package/dist/web-app/assets/stateDiagram-v2-MP3YSRHH-CToAT5fD.js +0 -2
- package/dist/web-app/assets/stateDiagram-v2-MP3YSRHH-CToAT5fD.js.map +0 -1
- package/dist/web-app/assets/swimlanes-42K2YHIH-BGjHfR8x.js +0 -2
- package/dist/web-app/assets/swimlanes-42K2YHIH-BGjHfR8x.js.map +0 -1
- package/dist/web-app/assets/swimlanesDiagram-VR7AAH4N-bLHg88Vk.js +0 -9
- package/dist/web-app/assets/swimlanesDiagram-VR7AAH4N-bLHg88Vk.js.map +0 -1
- package/dist/web-app/assets/timeline-definition-24CTP7MA-DhGtHQ0p.js +0 -121
- package/dist/web-app/assets/timeline-definition-24CTP7MA-DhGtHQ0p.js.map +0 -1
- package/dist/web-app/assets/vennDiagram-4TSXK5OY-Dv5irf00.js +0 -35
- package/dist/web-app/assets/vennDiagram-4TSXK5OY-Dv5irf00.js.map +0 -1
- package/dist/web-app/assets/wardleyDiagram-VM6X3IG4-JGiUTj5x.js +0 -79
- package/dist/web-app/assets/wardleyDiagram-VM6X3IG4-JGiUTj5x.js.map +0 -1
- package/dist/web-app/assets/xychartDiagram-S5SC5T6Z-Dw5ev7_Q.js +0 -8
- package/dist/web-app/assets/xychartDiagram-S5SC5T6Z-Dw5ev7_Q.js.map +0 -1
- package/dist/web-app/fleet-index.html +0 -19
- package/dist/web-app/fleet.webmanifest +0 -37
- package/dist/web-app/icons/apple-touch-icon.png +0 -0
- package/dist/web-app/icons/favicon-16.png +0 -0
- package/dist/web-app/icons/favicon-32.png +0 -0
- package/dist/web-app/icons/icon-192-maskable.png +0 -0
- package/dist/web-app/icons/icon-192.png +0 -0
- package/dist/web-app/icons/icon-512-maskable.png +0 -0
- package/dist/web-app/icons/icon-512.png +0 -0
- package/dist/web-app/index.html +0 -19
- package/dist/web-app/manifest.webmanifest +0 -17
- package/dist/web-app/sw.js +0 -221
- package/dist/web-app/version.json +0 -1
- package/dist/web-app/workspace-install.sh +0 -148
- package/dist/web-app/workspace-tunnel.sh +0 -40
package/README.md
CHANGED
|
@@ -139,76 +139,55 @@ the caller's owner channel with the caller and spawned-role details. This is an
|
|
|
139
139
|
honest-actor convenience and attribution path, not a security boundary; host
|
|
140
140
|
shells and deliberately bypassed absolute binaries retain direct behavior.
|
|
141
141
|
|
|
142
|
-
## Local
|
|
142
|
+
## Local HTTP service
|
|
143
143
|
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
The interactive console is packaged with `@ours.network/fleet` and binds to
|
|
149
|
-
IPv4 loopback by default. Remote or proxy exposure is always explicit:
|
|
144
|
+
Fleet is an HTTP backend. It serves no pages, bundles no frontend and opens no
|
|
145
|
+
browser: every screen belongs to the App, which calls this API with a device
|
|
146
|
+
credential. Any address outside `/api/` answers JSON `404`.
|
|
150
147
|
|
|
151
148
|
```sh
|
|
152
|
-
|
|
153
|
-
ours-fleet
|
|
149
|
+
ours-fleet setup-tunnel # connect this host to your App workspace
|
|
150
|
+
ours-fleet link-device # connect another browser or device
|
|
154
151
|
# choose a free port for an isolated test:
|
|
155
|
-
ours-fleet web serve --port 0
|
|
156
|
-
# nginx/TLS terminates at the declared
|
|
152
|
+
ours-fleet web serve --port 0
|
|
153
|
+
# nginx/TLS terminates at the declared origin; fleet remains loopback-bound
|
|
157
154
|
ours-fleet web install --public-origin https://fleet.example.com --password-file /secure/fleet-password
|
|
158
|
-
# Intentional no-password mode, for example when nginx already authenticates:
|
|
159
|
-
ours-fleet web install --public-origin https://fleet.example.com --no-password
|
|
160
155
|
```
|
|
161
156
|
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
157
|
+
`ours-fleet web` installs or updates an owner-level native service and starts
|
|
158
|
+
it on stable `127.0.0.1:49271`. Linux uses a systemd user unit and macOS uses a
|
|
159
|
+
LaunchAgent; both restart after process failures and send logs to the native
|
|
160
|
+
supervisor. Service management is explicit through
|
|
161
|
+
`ours-fleet web install|start|stop|restart|status|uninstall`. Use
|
|
162
|
+
`ours-fleet web serve` for a foreground development process. `--no-open` is
|
|
163
|
+
still accepted because installed service units pass it; it has no effect. Linux
|
|
164
|
+
login persistence requires linger; the installer reports when it is missing but
|
|
169
165
|
never enables it or requests root privileges.
|
|
170
166
|
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
browser, or `ours-fleet web revoke-all` to revoke every trusted browser and
|
|
178
|
-
active web session.
|
|
179
|
-
|
|
180
|
-
Only a domain-separated SHA-256 device-secret hash and bounded timestamps are
|
|
181
|
-
stored in the owner-private fleet state directory (`0700` directory, `0600`
|
|
182
|
-
atomic file). The re-pair and revoke controls use an owner-private Unix socket;
|
|
183
|
-
local processes running as the same OS user are therefore inside the trust
|
|
184
|
-
boundary.
|
|
167
|
+
Use `ours-fleet web revoke-all` to revoke every linked device and active
|
|
168
|
+
session. Only a domain-separated SHA-256 device-secret hash and bounded
|
|
169
|
+
timestamps are stored in the owner-private fleet state directory (`0700`
|
|
170
|
+
directory, `0600` atomic file). The link and revoke controls use an
|
|
171
|
+
owner-private Unix socket; local processes running as the same OS user are
|
|
172
|
+
therefore inside the trust boundary.
|
|
185
173
|
|
|
186
174
|
On first setup, the CLI requires an explicit access choice: `--password-file`
|
|
187
175
|
or `--pairing` for protected access, or `--no-password` for intentional
|
|
188
176
|
unprotected access. `--password-file` stores only a salted scrypt verifier in
|
|
189
|
-
the owner-private web state; the source file remains operator-managed.
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
who can reach that origin can control the fleet.
|
|
177
|
+
the owner-private web state; the source file remains operator-managed.
|
|
178
|
+
`--no-password` is deliberately named and prints a warning: anyone who can
|
|
179
|
+
reach that origin can control the fleet.
|
|
193
180
|
|
|
194
181
|
For nginx on a VPS, keep the default loopback bind and set the exact external
|
|
195
182
|
`--public-origin` (scheme, hostname, optional port). nginx should proxy HTTP and
|
|
196
183
|
WebSocket upgrades to `127.0.0.1:49271` and provide TLS; rewriting the upstream
|
|
197
|
-
Host is not required because the declared
|
|
184
|
+
Host is not required because the declared Origin remains authoritative. To listen beyond
|
|
198
185
|
loopback, add an explicit `--bind`; fleet refuses a non-loopback bind without a
|
|
199
186
|
public origin. Host and Origin validation use that declaration rather than
|
|
200
187
|
trusting forwarded headers. `localhost` and `127.0.0.1` both work in normal
|
|
201
|
-
local mode; an unconfigured hostname
|
|
202
|
-
of raw internal Host-header JSON.
|
|
203
|
-
|
|
204
|
-
The console is installable as a standalone PWA. Its service worker caches only
|
|
205
|
-
the data-free offline page and successful content-hashed JavaScript/CSS assets.
|
|
206
|
-
HTML stays network-first and no API, authentication, bootstrap, device,
|
|
207
|
-
WebSocket, terminal, event, audit, log, session, query-bearing, or error response
|
|
208
|
-
is cached. When the local daemon is unavailable, the PWA shows an explicit
|
|
209
|
-
offline shell and no stale fleet state.
|
|
188
|
+
local mode; an unconfigured hostname is refused with a JSON error.
|
|
210
189
|
|
|
211
|
-
The
|
|
190
|
+
The API provides evidence-separated inventory and status, ACP activity and
|
|
212
191
|
permission controls, redacted logs, typed text send, confirmed lifecycle
|
|
213
192
|
actions, and transactional permanent/temporary creation. Identity is fixed to
|
|
214
193
|
the role name. Creation uses the authenticated
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import { type OfferedModels } from '../subscriptions/cli.js';
|
|
2
|
+
export interface CodexModelDiscoveryDeps {
|
|
3
|
+
/** The Codex executable ACP sessions will run, and its version. */
|
|
4
|
+
runtime(): Promise<{
|
|
5
|
+
executable: string;
|
|
6
|
+
version: string;
|
|
7
|
+
}>;
|
|
8
|
+
ask(executable: string, env: NodeJS.ProcessEnv): Promise<OfferedModels>;
|
|
9
|
+
now(): number;
|
|
10
|
+
}
|
|
11
|
+
/**
|
|
12
|
+
* The models offered to the active Codex account by the runtime that sessions will actually use.
|
|
13
|
+
* An answer is reused only for the same executable, version, profile and sign-in.
|
|
14
|
+
*/
|
|
15
|
+
export declare function createCodexModelDiscovery(overrides?: Partial<CodexModelDiscoveryDeps>): () => Promise<OfferedModels>;
|
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
import { statSync } from 'node:fs';
|
|
2
|
+
import { join } from 'node:path';
|
|
3
|
+
import { resolveBundledAcpAgent } from '../harness/acp-agent.js';
|
|
4
|
+
import { probeCodexRuntime } from '../harness/codex-runtime.js';
|
|
5
|
+
import { codexOfferedModels, profileEnv } from '../subscriptions/cli.js';
|
|
6
|
+
import { profileHome, readSubscriptionState } from '../subscriptions/store.js';
|
|
7
|
+
const KNOWN_FOR_MS = 5 * 60_000;
|
|
8
|
+
const UNKNOWN_FOR_MS = 10_000;
|
|
9
|
+
/** When the profile's sign-in last changed; a new sign-in must not reuse another account's answer. */
|
|
10
|
+
function signInStamp(home) {
|
|
11
|
+
try {
|
|
12
|
+
return statSync(join(home, 'auth.json')).mtimeMs;
|
|
13
|
+
}
|
|
14
|
+
catch {
|
|
15
|
+
return 0;
|
|
16
|
+
}
|
|
17
|
+
}
|
|
18
|
+
/**
|
|
19
|
+
* The models offered to the active Codex account by the runtime that sessions will actually use.
|
|
20
|
+
* An answer is reused only for the same executable, version, profile and sign-in.
|
|
21
|
+
*/
|
|
22
|
+
export function createCodexModelDiscovery(overrides = {}) {
|
|
23
|
+
const deps = {
|
|
24
|
+
runtime: () => probeCodexRuntime(resolveBundledAcpAgent('@agentclientprotocol/codex-acp', 'codex-acp', 'codex-acp'), process.env),
|
|
25
|
+
ask: codexOfferedModels,
|
|
26
|
+
now: Date.now,
|
|
27
|
+
...overrides,
|
|
28
|
+
};
|
|
29
|
+
let cached;
|
|
30
|
+
let pending;
|
|
31
|
+
return async () => {
|
|
32
|
+
let key, executable, env;
|
|
33
|
+
try {
|
|
34
|
+
const profileId = readSubscriptionState().providers.codex.activeProfileId;
|
|
35
|
+
const profile = profileHome('codex', profileId);
|
|
36
|
+
const runtime = await deps.runtime();
|
|
37
|
+
executable = runtime.executable;
|
|
38
|
+
env = profileEnv('CODEX_HOME', profileId, profile);
|
|
39
|
+
key = [runtime.executable, runtime.version, profileId, signInStamp(profile)].join('\n');
|
|
40
|
+
}
|
|
41
|
+
catch (error) {
|
|
42
|
+
return { state: 'unknown', reason: error instanceof Error ? error.message : String(error) };
|
|
43
|
+
}
|
|
44
|
+
if (cached && cached.key === key && cached.until > deps.now())
|
|
45
|
+
return cached.value;
|
|
46
|
+
if (pending?.key === key)
|
|
47
|
+
return pending.answer;
|
|
48
|
+
const answer = deps.ask(executable, env).then(value => {
|
|
49
|
+
cached = { key, until: deps.now() + (value.state === 'known' ? KNOWN_FOR_MS : UNKNOWN_FOR_MS), value };
|
|
50
|
+
return value;
|
|
51
|
+
}).finally(() => { if (pending?.key === key)
|
|
52
|
+
pending = undefined; });
|
|
53
|
+
pending = { key, answer };
|
|
54
|
+
return answer;
|
|
55
|
+
};
|
|
56
|
+
}
|
package/dist/build-info.json
CHANGED
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
{
|
|
2
|
-
"version": "1.2.0-nightly.
|
|
3
|
-
"buildId": "
|
|
4
|
-
"commit": "
|
|
2
|
+
"version": "1.2.0-nightly.36",
|
|
3
|
+
"buildId": "63df63bcda45",
|
|
4
|
+
"commit": "b4575c95acd1ae2fee42f8f8871bfe9d816a1b1a",
|
|
5
5
|
"dirty": true,
|
|
6
|
-
"builtAt": "2026-10-
|
|
6
|
+
"builtAt": "2026-10-02T18:04:01.351Z",
|
|
7
7
|
"capabilities": [
|
|
8
8
|
"workspace.enroll.preserve-profile-v1",
|
|
9
9
|
"cowork.http-management-v1",
|
package/dist/cli.js
CHANGED
|
@@ -1,10 +1,10 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
import { ensureMinimalSetup } from './minimal-setup.js';
|
|
3
|
-
import {
|
|
3
|
+
import { confirmWorkspaceTarget } from './workspace-enrollment.js';
|
|
4
4
|
import { clearPendingTunnelSetup, readPendingTunnelSetup, requiredPortAfterExpiry, savePendingTunnelSetup, setupTunnelPreflight } from './setup-tunnel-preflight.js';
|
|
5
5
|
import { availableWebPort } from './web/available-port.js';
|
|
6
6
|
import QRCode from 'qrcode';
|
|
7
|
-
import { readWorkspacePayload, enrollWorkspace } from './workspace-enrollment.js';
|
|
7
|
+
import { readWorkspacePayload, enrollWorkspace, checkWorkspaceConfiguration } from './workspace-enrollment.js';
|
|
8
8
|
import { waitForRoleDaemon } from './startup-readiness.js';
|
|
9
9
|
import { SupervisorOursTools } from './application/supervisor-ours-tools.js';
|
|
10
10
|
import { runTempSupervisor, TEMP_RECYCLE_EXIT } from './temp-supervisor-recovery.js';
|
|
@@ -1394,7 +1394,7 @@ cOpt(program.command('migrate-role-defaults')
|
|
|
1394
1394
|
die(error);
|
|
1395
1395
|
}
|
|
1396
1396
|
});
|
|
1397
|
-
const webCommand = cOpt(program.command('web').description('start
|
|
1397
|
+
const webCommand = cOpt(program.command('web').description('start the Fleet HTTP service used by the App'))
|
|
1398
1398
|
.enablePositionalOptions()
|
|
1399
1399
|
.option('--port <port>', 'loopback service port (default: 49271)', value => {
|
|
1400
1400
|
const port = Number(value);
|
|
@@ -1402,7 +1402,7 @@ const webCommand = cOpt(program.command('web').description('start or open the se
|
|
|
1402
1402
|
throw new Error('invalid port');
|
|
1403
1403
|
return port;
|
|
1404
1404
|
})
|
|
1405
|
-
.option('--no-open', '
|
|
1405
|
+
.option('--no-open', 'accepted for existing service units; Fleet opens no browser')
|
|
1406
1406
|
.option('--bind <address>', 'explicit listen address (default: 127.0.0.1)')
|
|
1407
1407
|
.option('--public-origin <url>', 'browser origin served by an explicit reverse proxy')
|
|
1408
1408
|
.option('--password-file <path>', 'configure password protection from an owner-readable file')
|
|
@@ -1419,12 +1419,7 @@ const webCommand = cOpt(program.command('web').description('start or open the se
|
|
|
1419
1419
|
if (accessNotice)
|
|
1420
1420
|
process.stdout.write(accessNotice + '\n');
|
|
1421
1421
|
await manager.start();
|
|
1422
|
-
|
|
1423
|
-
await requestWebControlWhenReady('open');
|
|
1424
|
-
process.stdout.write('Control-panel authentication opened in the browser.\n');
|
|
1425
|
-
}
|
|
1426
|
-
else
|
|
1427
|
-
process.stdout.write('Web service started; run `ours-fleet web open` to pair a browser.\n');
|
|
1422
|
+
process.stdout.write('Fleet service started.\n');
|
|
1428
1423
|
}
|
|
1429
1424
|
catch (e) {
|
|
1430
1425
|
die(e);
|
|
@@ -1437,7 +1432,7 @@ const webPort = (command) => cOpt(command)
|
|
|
1437
1432
|
throw new Error('invalid port');
|
|
1438
1433
|
return port;
|
|
1439
1434
|
});
|
|
1440
|
-
const webServe = cOpt(webCommand.command('serve').description('run the
|
|
1435
|
+
const webServe = cOpt(webCommand.command('serve').description('run the Fleet HTTP service in the foreground'))
|
|
1441
1436
|
.option('--port <port>', 'loopback port (default: 49271; 0 chooses a free port)', value => {
|
|
1442
1437
|
const port = Number(value);
|
|
1443
1438
|
if (!Number.isInteger(port) || port < 0 || port > 65_535)
|
|
@@ -1445,7 +1440,7 @@ const webServe = cOpt(webCommand.command('serve').description('run the web conso
|
|
|
1445
1440
|
return port;
|
|
1446
1441
|
});
|
|
1447
1442
|
webServe
|
|
1448
|
-
.option('--no-open', '
|
|
1443
|
+
.option('--no-open', 'accepted for existing service units; Fleet opens no browser')
|
|
1449
1444
|
.option('--bind <address>', 'explicit listen address (default: 127.0.0.1)')
|
|
1450
1445
|
.option('--public-origin <url>', 'browser origin served by an explicit reverse proxy')
|
|
1451
1446
|
.option('--password-file <path>', 'configure password protection from an owner-readable file')
|
|
@@ -1456,15 +1451,12 @@ webServe
|
|
|
1456
1451
|
const accessNotice = configureWebAccess(opts);
|
|
1457
1452
|
const consoleServer = await startWebConsole({
|
|
1458
1453
|
configPath: opts.configuration, port: opts.port,
|
|
1459
|
-
|
|
1454
|
+
binPath, bind: opts.bind, publicOrigin: opts.publicOrigin,
|
|
1460
1455
|
log: line => process.stderr.write(line + '\n'),
|
|
1461
1456
|
});
|
|
1462
1457
|
if (accessNotice)
|
|
1463
1458
|
process.stdout.write(accessNotice + '\n');
|
|
1464
1459
|
process.stdout.write(`ours-fleet web listening on ${consoleServer.address}\n`);
|
|
1465
|
-
process.stdout.write(opts.open !== false
|
|
1466
|
-
? 'Control-panel authentication opened in the browser.\n'
|
|
1467
|
-
: 'Run `ours-fleet web open` to authenticate a browser.\n');
|
|
1468
1460
|
const shutdown = async () => { await consoleServer.close(); process.exit(0); };
|
|
1469
1461
|
process.once('SIGINT', () => { void shutdown(); });
|
|
1470
1462
|
process.once('SIGTERM', () => { void shutdown(); });
|
|
@@ -1523,16 +1515,6 @@ webCommand.command('uninstall').description('stop and uninstall the owner web se
|
|
|
1523
1515
|
die(e);
|
|
1524
1516
|
}
|
|
1525
1517
|
});
|
|
1526
|
-
webCommand.command('open').description('securely open or re-pair a browser with the running console')
|
|
1527
|
-
.action(async () => {
|
|
1528
|
-
try {
|
|
1529
|
-
await requestWebControl('open');
|
|
1530
|
-
process.stdout.write('Control-panel authentication opened in the browser.\n');
|
|
1531
|
-
}
|
|
1532
|
-
catch (e) {
|
|
1533
|
-
die(e);
|
|
1534
|
-
}
|
|
1535
|
-
});
|
|
1536
1518
|
async function workspaceEnrollmentCommand(opts, setupTunnel = false) {
|
|
1537
1519
|
try {
|
|
1538
1520
|
if (setupTunnel && opts.check && opts.resume)
|
|
@@ -1541,6 +1523,7 @@ async function workspaceEnrollmentCommand(opts, setupTunnel = false) {
|
|
|
1541
1523
|
throw Error('--check and --resume take no payload file or migration flag');
|
|
1542
1524
|
if (setupTunnel && opts.check) {
|
|
1543
1525
|
await setupTunnelPreflight();
|
|
1526
|
+
await checkWorkspaceConfiguration(opts.configuration ?? defaultConfigPath());
|
|
1544
1527
|
process.stdout.write('Tunnel setup prerequisites are available.\n');
|
|
1545
1528
|
return;
|
|
1546
1529
|
}
|
|
@@ -1557,6 +1540,7 @@ async function workspaceEnrollmentCommand(opts, setupTunnel = false) {
|
|
|
1557
1540
|
const payload = readWorkspacePayload(opts.file);
|
|
1558
1541
|
if (setupTunnel) {
|
|
1559
1542
|
await setupTunnelPreflight();
|
|
1543
|
+
await checkWorkspaceConfiguration(opts.configuration ?? defaultConfigPath());
|
|
1560
1544
|
await ensureMinimalSetup(opts.configuration ?? defaultConfigPath());
|
|
1561
1545
|
}
|
|
1562
1546
|
const result = await enrollWorkspace(payload, opts.configuration, { migrateAppOrigin: opts.migrateAppOrigin, preserveProfile: setupTunnel || opts.preserveProfile });
|
|
@@ -1629,7 +1613,7 @@ async function finishWorkspaceService(pending, configuration, record) {
|
|
|
1629
1613
|
pending = { ...pending, requestedPorts: [...(pending.requestedPorts ?? []), bound.port] };
|
|
1630
1614
|
savePendingTunnelSetup(pending);
|
|
1631
1615
|
}
|
|
1632
|
-
await
|
|
1616
|
+
await confirmWorkspaceTarget(pending, pending.hostWorkspaceId, pending.rootCid, bound.port, error => { process.stderr.write(`The enrollment contact could not be removed from Messenger (${error instanceof Error ? error.message : String(error)}); it can be removed there by hand.\n`); });
|
|
1633
1617
|
}
|
|
1634
1618
|
else if (bound.port !== requiredPort)
|
|
1635
1619
|
throw Error(`The setup window has expired and the tunnel points at port ${requiredPort}, but this host could only bind port ${bound.port}. Free port ${requiredPort} on this host`);
|
|
@@ -1669,20 +1653,6 @@ webCommand.command('revoke-all').description('revoke all trusted browsers and ac
|
|
|
1669
1653
|
die(e);
|
|
1670
1654
|
}
|
|
1671
1655
|
});
|
|
1672
|
-
async function requestWebControlWhenReady(command) {
|
|
1673
|
-
let last;
|
|
1674
|
-
for (let attempt = 0; attempt < 40; attempt++) {
|
|
1675
|
-
try {
|
|
1676
|
-
await requestWebControl(command, undefined, 500);
|
|
1677
|
-
return;
|
|
1678
|
-
}
|
|
1679
|
-
catch (error) {
|
|
1680
|
-
last = error;
|
|
1681
|
-
await new Promise(resolve => setTimeout(resolve, 125));
|
|
1682
|
-
}
|
|
1683
|
-
}
|
|
1684
|
-
throw last;
|
|
1685
|
-
}
|
|
1686
1656
|
function configureWebAccess(opts) {
|
|
1687
1657
|
if (opts.publicOrigin)
|
|
1688
1658
|
validatePublicOrigin(opts.publicOrigin);
|
package/dist/config.d.ts
CHANGED
|
@@ -311,6 +311,8 @@ export declare function loadConfig(configPath?: string, options?: {
|
|
|
311
311
|
temporary?: boolean;
|
|
312
312
|
};
|
|
313
313
|
skipWatchdogs?: boolean;
|
|
314
|
+
/** The one Owner invitation file that tunnel setup writes itself and that may therefore still be absent. */
|
|
315
|
+
deferredOwnerInviteFile?: string;
|
|
314
316
|
}): FleetConfig;
|
|
315
317
|
/** Full read-only Agent resolution used by launch dry-runs and room plan validation. */
|
|
316
318
|
export declare function resolveAgentDefinitionDryRun(configPath: string, id: string, definition: AgentDefinition): ResolvedRole;
|
package/dist/config.js
CHANGED
|
@@ -764,7 +764,7 @@ export function loadConfig(configPath, options = {}) {
|
|
|
764
764
|
if (doc.rooms !== undefined) {
|
|
765
765
|
if (rooms)
|
|
766
766
|
throw new ConfigError(`rooms: defined in multiple files; last: ${file}`);
|
|
767
|
-
const validated = validateRoomsConfig(deepSub(doc.rooms, vars), vars, file);
|
|
767
|
+
const validated = validateRoomsConfig(deepSub(doc.rooms, vars), vars, file, options.deferredOwnerInviteFile);
|
|
768
768
|
ownerInviteFingerprint = validated._invite?.fingerprint;
|
|
769
769
|
ownerInvite = validated._invite?.value;
|
|
770
770
|
const { _invite: _, ...clean } = validated;
|