@madarco/agentbox 0.6.0 → 0.8.0

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 (75) hide show
  1. package/dist/_cloud-attach-T727ZPRV.js +13 -0
  2. package/dist/chunk-67N47KUS.js +1640 -0
  3. package/dist/chunk-67N47KUS.js.map +1 -0
  4. package/dist/chunk-6OZDFNBF.js +8114 -0
  5. package/dist/chunk-6OZDFNBF.js.map +1 -0
  6. package/dist/chunk-BGK32PZE.js +455 -0
  7. package/dist/chunk-BGK32PZE.js.map +1 -0
  8. package/dist/chunk-FODMEHD3.js +1200 -0
  9. package/dist/chunk-FODMEHD3.js.map +1 -0
  10. package/dist/chunk-G3H2L3O2.js +288 -0
  11. package/dist/chunk-G3H2L3O2.js.map +1 -0
  12. package/dist/chunk-I24B6AXR.js +600 -0
  13. package/dist/chunk-I24B6AXR.js.map +1 -0
  14. package/dist/chunk-LEV3KICD.js +738 -0
  15. package/dist/chunk-LEV3KICD.js.map +1 -0
  16. package/dist/cloud-poller-SUNA6ZQC-2RG5WPRN.js +10 -0
  17. package/dist/dist-L4LCG5SJ.js +293 -0
  18. package/dist/dist-L4LCG5SJ.js.map +1 -0
  19. package/dist/dist-LOZBWMBF.js +447 -0
  20. package/dist/dist-ZODPD2I6.js +1407 -0
  21. package/dist/dist-ZODPD2I6.js.map +1 -0
  22. package/dist/index.js +7281 -2134
  23. package/dist/index.js.map +1 -1
  24. package/dist/prepared-state-CL4CWXQA-ME4HSKDE.js +18 -0
  25. package/package.json +8 -3
  26. package/runtime/daytona/custom-system-CLAUDE.md +39 -0
  27. package/runtime/docker/Dockerfile.box +120 -14
  28. package/runtime/docker/apps/cli/share/agentbox-setup/SKILL.md +15 -8
  29. package/runtime/docker/packages/ctl/dist/bin.cjs +11310 -816
  30. package/runtime/docker/packages/sandbox-docker/scripts/agentbox-codex-hooks.json +68 -0
  31. package/runtime/docker/packages/sandbox-docker/scripts/agentbox-open +9 -9
  32. package/runtime/docker/packages/sandbox-docker/scripts/claude-managed-settings.json +62 -1
  33. package/runtime/docker/packages/sandbox-docker/scripts/custom-system-CLAUDE.md +15 -4
  34. package/runtime/docker/packages/sandbox-docker/scripts/gh-shim +263 -0
  35. package/runtime/docker/packages/sandbox-docker/scripts/git-shim +131 -0
  36. package/runtime/docker/packages/sandbox-docker/scripts/opencode-agentbox-plugin.js +76 -0
  37. package/runtime/hetzner/agentbox-checkpoint-cleanup +52 -0
  38. package/runtime/hetzner/agentbox-codex-hooks.json +68 -0
  39. package/runtime/hetzner/agentbox-dockerd-start +132 -0
  40. package/runtime/hetzner/agentbox-open +28 -0
  41. package/runtime/hetzner/agentbox-setup-skill.md +196 -0
  42. package/runtime/hetzner/agentbox-vnc-start +77 -0
  43. package/runtime/hetzner/claude-managed-settings.json +115 -0
  44. package/runtime/hetzner/ctl.cjs +23397 -0
  45. package/runtime/hetzner/custom-system-CLAUDE.md +39 -0
  46. package/runtime/hetzner/gh-shim +263 -0
  47. package/runtime/hetzner/git-shim +131 -0
  48. package/runtime/hetzner/opencode-agentbox-plugin.js +76 -0
  49. package/runtime/hetzner/scripts/install-box.sh +374 -0
  50. package/runtime/relay/bin.cjs +10017 -817
  51. package/share/agentbox-setup/SKILL.md +15 -8
  52. package/share/host-skills/agentbox/SKILL.md +29 -0
  53. package/share/host-skills/agentbox-info/SKILL.md +211 -0
  54. package/share/host-skills/codex/agentbox.md +35 -0
  55. package/share/host-skills/opencode/agentbox.md +26 -0
  56. package/dist/chunk-BBZMA2K6.js +0 -238
  57. package/dist/chunk-BBZMA2K6.js.map +0 -1
  58. package/dist/chunk-HHMWQNLF.js +0 -1709
  59. package/dist/chunk-HHMWQNLF.js.map +0 -1
  60. package/dist/chunk-HPZMD5DE.js +0 -106
  61. package/dist/chunk-HPZMD5DE.js.map +0 -1
  62. package/dist/chunk-HTTKML3C.js +0 -2655
  63. package/dist/chunk-HTTKML3C.js.map +0 -1
  64. package/dist/chunk-KJNZP6I3.js +0 -586
  65. package/dist/chunk-KJNZP6I3.js.map +0 -1
  66. package/dist/chunk-M7I247BK.js +0 -525
  67. package/dist/chunk-M7I247BK.js.map +0 -1
  68. package/dist/create-6PWXI6HO-OWAMHBAK.js +0 -15
  69. package/dist/lifecycle-EMXR46DI-DUVBXNTV.js +0 -38
  70. package/dist/state-KD7M46ZP-KHFTHFUS.js +0 -26
  71. package/dist/stats-SZXOJE3D-N7OODCHW.js +0 -19
  72. /package/dist/{create-6PWXI6HO-OWAMHBAK.js.map → _cloud-attach-T727ZPRV.js.map} +0 -0
  73. /package/dist/{lifecycle-EMXR46DI-DUVBXNTV.js.map → cloud-poller-SUNA6ZQC-2RG5WPRN.js.map} +0 -0
  74. /package/dist/{state-KD7M46ZP-KHFTHFUS.js.map → dist-LOZBWMBF.js.map} +0 -0
  75. /package/dist/{stats-SZXOJE3D-N7OODCHW.js.map → prepared-state-CL4CWXQA-ME4HSKDE.js.map} +0 -0
@@ -0,0 +1,18 @@
1
+ #!/usr/bin/env node
2
+ import {
3
+ DOCKERFILE_PATH,
4
+ computeDockerContextFingerprint,
5
+ preparedMatches,
6
+ readPreparedDockerState,
7
+ resolveContextFiles,
8
+ writePreparedDockerState
9
+ } from "./chunk-BGK32PZE.js";
10
+ export {
11
+ DOCKERFILE_PATH,
12
+ computeDockerContextFingerprint,
13
+ preparedMatches,
14
+ readPreparedDockerState,
15
+ resolveContextFiles,
16
+ writePreparedDockerState
17
+ };
18
+ //# sourceMappingURL=prepared-state-CL4CWXQA-ME4HSKDE.js.map
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@madarco/agentbox",
3
- "version": "0.6.0",
3
+ "version": "0.8.0",
4
4
  "description": "Launch Claude Code, Codex, and other coding agents in isolated sandboxes",
5
5
  "license": "MIT",
6
6
  "author": "Marco D'Alia",
@@ -41,6 +41,7 @@
41
41
  ],
42
42
  "dependencies": {
43
43
  "@clack/prompts": "^0.9.0",
44
+ "@daytonaio/sdk": "^0.179.0",
44
45
  "@xterm/headless": "^5.5.0",
45
46
  "commander": "^12.1.0",
46
47
  "execa": "^9.5.2",
@@ -56,10 +57,14 @@
56
57
  "typescript": "^5.7.2",
57
58
  "vitest": "^2.1.8",
58
59
  "@agentbox/config": "0.0.0",
59
- "@agentbox/core": "0.0.0",
60
+ "@agentbox/relay": "0.0.0",
60
61
  "@agentbox/ctl": "0.0.0",
62
+ "@agentbox/core": "0.0.0",
63
+ "@agentbox/sandbox-cloud": "0.0.0",
64
+ "@agentbox/sandbox-core": "0.0.0",
61
65
  "@agentbox/sandbox-docker": "0.0.0",
62
- "@agentbox/relay": "0.0.0"
66
+ "@agentbox/sandbox-daytona": "0.0.0",
67
+ "@agentbox/sandbox-hetzner": "0.0.0"
63
68
  },
64
69
  "scripts": {
65
70
  "build": "tsup",
@@ -0,0 +1,39 @@
1
+ # AgentBox sandbox (daytona provider)
2
+
3
+ You are running inside an AgentBox sandbox: a Daytona Cloud sandbox
4
+ provisioned just for this box, with docker-in-docker available (run `docker`
5
+ directly, no sudo). Your user is `vscode` and you can use passwordless
6
+ **sudo** to run commands as root. The whole sandbox is yours — the user's
7
+ host filesystem is not visible from here and nothing is bind-mounted.
8
+
9
+ You can save the current filesystem state to be reused by future boxes by
10
+ running `agentbox-ctl checkpoint --set-default`. This doesn't need to be confirmed by the user.
11
+
12
+ `/workspace` is a normal git checkout seeded from the host repo at create
13
+ time (via a `git bundle`). Because there is no host bind-mount, plain `git`
14
+ inside the box only affects this box-local repo — commits do **not** appear
15
+ in the user's host `git log` until you hand them off. For any operation that
16
+ must reach the host repo or its remotes (push, fetch, pull, picking up
17
+ host-side changes), use `agentbox-ctl git push|fetch|pull -- <args>` — it
18
+ RPCs to the host, which runs git with the real SSH agent and writes back into
19
+ the host's worktree state. The wrapper already builds `git push <remote>
20
+ <branch>` host-side from the registered worktree; the `-- <args>` slot is for
21
+ extra flags only (e.g. `--force-with-lease`, `--tags`). Re-passing the remote
22
+ or branch makes git treat them as refspecs and fails with
23
+ `refs/remotes/origin/HEAD cannot be resolved to branch`.
24
+
25
+ For GitHub PR work, use `agentbox-ctl git pr <op> [args...]` — same model,
26
+ relay shells to host `gh`. Ops: `create`, `view`, `list`, `comment`,
27
+ `review`, `merge`, `close`, `reopen`, `checkout`. `view` / `list` are
28
+ read-only and run silently; everything else asks the user to confirm in
29
+ the host wrapper (deny → exit 10).
30
+
31
+ For ad-hoc file transfers between this box and the host, use
32
+ `agentbox-ctl cp toHost <boxPath> <hostPath>` and
33
+ `agentbox-ctl cp fromHost <hostPath> <boxPath>` or `agentbox-ctl download claude` / `download env` /
34
+ `download config`. They RPC to the host and
35
+ ask the user for confirmation on the wrapper that runs `agentbox claude`;
36
+ deny returns exit 10 (`denied by user`).
37
+ Don't put any timeout on the command, it will run forever and the user will be notified through multiple channels.
38
+
39
+ Box identity: /etc/agentbox/box.env and the AGENTBOX_* env vars.
@@ -7,7 +7,7 @@
7
7
  # tar pipe for the no-git case). The old FUSE overlay over /host-src+/upper
8
8
  # is gone — but fuse3 + fuse-overlayfs stay as the in-box dockerd's fallback
9
9
  # storage driver (it prefers the kernel-native overlay2). Plus the "universal-ish" set of
10
- # language runtimes (Node.js 22 from NodeSource, Python 3 from apt). Heavier
10
+ # language runtimes (Node.js 24 from NodeSource, Python 3 from apt). Heavier
11
11
  # tooling (Go, Java, Ruby, .NET, more browser tooling, vscode-server) goes in
12
12
  # a later iteration.
13
13
  #
@@ -57,7 +57,7 @@ ENV COLORTERM=truecolor \
57
57
  RUN apt-get update \
58
58
  && apt-get install -y --no-install-recommends \
59
59
  curl ca-certificates gnupg \
60
- && curl -fsSL https://deb.nodesource.com/setup_22.x | bash - \
60
+ && curl -fsSL https://deb.nodesource.com/setup_24.x | bash - \
61
61
  && apt-get install -y --no-install-recommends \
62
62
  fuse3 \
63
63
  fuse-overlayfs \
@@ -87,7 +87,7 @@ RUN setcap cap_net_bind_service=+ep "$(readlink -f "$(command -v node)")"
87
87
  # Enable corepack (pnpm/yarn shims) at build time as root. Doing this here
88
88
  # rather than in the wizard's install task avoids two failures the runtime
89
89
  # `corepack enable` (run as non-root `vscode`) hits: it can't write shims into
90
- # the root-owned NodeSource bin dir (/usr/bin), and node 22's bundled corepack
90
+ # the root-owned NodeSource bin dir (/usr/bin), and node 24's bundled corepack
91
91
  # resolves its dist path relative to the symlink dirname, so a
92
92
  # ~/.local/bin/pnpm symlink looks for ~/.local/dist/pnpm.js and breaks.
93
93
  # `corepack@latest` fixes the symlink resolution; baking the shims into
@@ -97,6 +97,13 @@ RUN setcap cap_net_bind_service=+ep "$(readlink -f "$(command -v node)")"
97
97
  RUN npm install -g corepack@latest \
98
98
  && corepack enable pnpm yarn
99
99
 
100
+ # Pre-create the corepack download cache owned by `vscode`. Without this,
101
+ # the first corepack-driven install (e.g. the setup wizard's verification
102
+ # step) hits ENOENT on /home/vscode/.cache/node/corepack/v1 because nothing
103
+ # else creates ~/.cache for the runtime user.
104
+ RUN mkdir -p /home/vscode/.cache/node/corepack \
105
+ && chown -R vscode:vscode /home/vscode/.cache
106
+
100
107
  # Host repos are bind-mounted in at their identical absolute path (worktree
101
108
  # pointer files contain absolute paths to <main>/.git/worktrees/<name>, so both
102
109
  # sides have to resolve the same path), and the host owns those `.git/` dirs.
@@ -134,6 +141,19 @@ RUN apt-get update \
134
141
  COPY packages/ctl/dist/bin.cjs /usr/local/bin/agentbox-ctl
135
142
  RUN chmod +x /usr/local/bin/agentbox-ctl
136
143
 
144
+ # `gh` + `git` shims: route a strict subset of upstream subcommands through
145
+ # the host relay (via agentbox-ctl) so the host's authenticated `gh` / git
146
+ # creds stay on the host — the in-box agent never sees a token. The shims
147
+ # also light up Claude Code's branch-linked-to-PR badge (Claude Code calls
148
+ # `gh pr view --json …` on refresh). See packages/sandbox-docker/scripts/
149
+ # {gh,git}-shim and docs/plans/gh-and-git-shims-host-only.md. PATH ordering
150
+ # (line 50 above) puts /usr/local/bin ahead of /usr/bin, so the shim wins;
151
+ # the git shim execs /usr/bin/git directly for everything outside its tiny
152
+ # network-op whitelist (push/pull/fetch/clone).
153
+ COPY packages/sandbox-docker/scripts/gh-shim /usr/local/bin/gh
154
+ COPY packages/sandbox-docker/scripts/git-shim /usr/local/bin/git
155
+ RUN chmod +x /usr/local/bin/gh /usr/local/bin/git
156
+
137
157
  # Setup guide for the first-run wizard. This baked copy is the single source
138
158
  # of the /agentbox-setup skill: seedSetupSkillIntoVolume()
139
159
  # (packages/sandbox-docker/src/claude.ts) copies it into the box's
@@ -161,6 +181,38 @@ RUN mkdir -p /home/vscode/.claude \
161
181
  && ln -s /home/vscode/.claude/_claude.json /home/vscode/.claude.json \
162
182
  && chown -h vscode:vscode /home/vscode/.claude.json
163
183
 
184
+ # Cloud-provider credential pivot: ~/.agentbox-creds/<agent>/ is where the
185
+ # per-org `agentbox-credentials` Daytona volume gets mounted at runtime (three
186
+ # subpath mounts: claude/, codex/, opencode/). Three symlinks route the
187
+ # agent-expected credential paths through to it so the in-box agent reads
188
+ # tokens from the volume while the surrounding config sits on the snapshot-
189
+ # baked sandbox FS.
190
+ #
191
+ # These symlinks are dangling at build time — their targets only resolve once
192
+ # the volume is mounted. That's fine: ln succeeds, and the kernel resolves
193
+ # symlinks lazily on open().
194
+ #
195
+ # The Docker provider is unaffected: its named `agentbox-{claude,codex,
196
+ # opencode}-config` volumes mount *over* /home/vscode/.claude etc., obscuring
197
+ # the symlinks; the volume content includes the credential files directly.
198
+ RUN mkdir -p /home/vscode/.agentbox-creds/claude \
199
+ /home/vscode/.agentbox-creds/codex \
200
+ /home/vscode/.agentbox-creds/opencode \
201
+ /home/vscode/.codex \
202
+ /home/vscode/.local/share/opencode \
203
+ && ln -s /home/vscode/.agentbox-creds/claude/.credentials.json \
204
+ /home/vscode/.claude/.credentials.json \
205
+ && ln -s /home/vscode/.agentbox-creds/codex/auth.json \
206
+ /home/vscode/.codex/auth.json \
207
+ && ln -s /home/vscode/.agentbox-creds/opencode/auth.json \
208
+ /home/vscode/.local/share/opencode/auth.json \
209
+ && chown -R vscode:vscode /home/vscode/.agentbox-creds \
210
+ /home/vscode/.codex \
211
+ /home/vscode/.local \
212
+ && chown -h vscode:vscode /home/vscode/.claude/.credentials.json \
213
+ /home/vscode/.codex/auth.json \
214
+ /home/vscode/.local/share/opencode/auth.json
215
+
164
216
  # Prepare /home/vscode/.vscode-server and /home/vscode/.cursor-server (+ their
165
217
  # extensions subdirs) so the named volumes mounted at runtime — per-box
166
218
  # `agentbox-{vscode,cursor}-server-<id>` over the server dirs, then shared
@@ -184,6 +236,29 @@ USER vscode
184
236
  RUN curl -fsSL https://claude.ai/install.sh | bash -s stable
185
237
  USER root
186
238
 
239
+ # OpenAI Codex CLI. The @openai/codex npm package ships platform-native
240
+ # prebuilds for linux arm64/amd64, so a plain global install is enough.
241
+ # Parallel to the Claude Code install above: `agentbox codex` launches it in a
242
+ # tmux session and the box mounts a synced `agentbox-codex-config` volume at
243
+ # ~/.codex for auth/config (see packages/sandbox-docker/src/codex.ts).
244
+ #
245
+ # `bubblewrap` (bwrap) is Codex's command-sandbox backend; without it on PATH
246
+ # Codex falls back to a bundled copy and prints a warning on every run. It
247
+ # works nested because the agentbox container already runs with --cap-add
248
+ # SYS_ADMIN + apparmor:unconfined.
249
+ RUN apt-get update \
250
+ && apt-get install -y --no-install-recommends bubblewrap \
251
+ && rm -rf /var/lib/apt/lists/* \
252
+ && npm install -g @openai/codex
253
+
254
+ # OpenCode CLI (sst/opencode) — the multi-provider terminal coding agent.
255
+ # Parallel to the Claude/Codex installs: `agentbox opencode` launches it in a
256
+ # tmux session and the box mounts a synced `agentbox-opencode-config` volume
257
+ # (see packages/sandbox-docker/src/opencode.ts). OpenCode splits its state
258
+ # across ~/.config/opencode (config) and ~/.local/share/opencode (data + auth);
259
+ # the volume holds both, with the config dir relocated via OPENCODE_CONFIG_DIR.
260
+ RUN npm install -g opencode-ai
261
+
187
262
  # Browser support for in-box agents: Vercel's agent-browser drives Chrome via
188
263
  # CDP. Two things have to happen here:
189
264
  #
@@ -217,15 +292,26 @@ RUN apt-get update \
217
292
 
218
293
  RUN npm install -g agent-browser playwright
219
294
 
295
+ # Portless CLI (https://portless.sh). Only the client — the box never runs the
296
+ # proxy; that's a host process. With `portless.enabled`, createBox bind-mounts
297
+ # the host's Portless state dir into the box and sets PORTLESS_STATE_DIR, so
298
+ # the in-box `portless list`/`get` share the host's route registry (discovery).
299
+ # Requires Node 24+ — hence the setup_24.x bump above.
300
+ RUN npm install -g portless
301
+
220
302
  # Download Chromium as `vscode` so the ms-playwright cache lands in vscode's
221
303
  # home (the user agent-browser runs as). The downloaded binary lives at
222
- # `chromium-XXXX/chrome-linux/chrome`, where XXXX is a Playwright-internal
223
- # revision number that changes between releases — we resolve it once here and
224
- # write the result to a stable symlink so AGENT_BROWSER_EXECUTABLE_PATH can
225
- # point at something predictable.
304
+ # `chromium-XXXX/chrome-linux*/chrome`, where XXXX is a Playwright-internal
305
+ # revision number that changes between releases — and the inner dir is
306
+ # `chrome-linux` for old releases and `chrome-linux64` (or `chrome-linux/arm64`)
307
+ # for current Chrome-for-Testing builds. Glob both. We resolve once and write
308
+ # a stable symlink so AGENT_BROWSER_EXECUTABLE_PATH can point at something
309
+ # predictable.
226
310
  USER vscode
227
311
  RUN playwright install chromium \
228
- && ln -sf "$(ls /home/vscode/.cache/ms-playwright/chromium-*/chrome-linux/chrome | sort | tail -1)" /tmp/chromium-link \
312
+ && CHROME_BIN="$(ls /home/vscode/.cache/ms-playwright/chromium-*/chrome-linux*/chrome 2>/dev/null | sort | tail -1)" \
313
+ && test -n "$CHROME_BIN" \
314
+ && ln -sf "$CHROME_BIN" /tmp/chromium-link \
229
315
  && test -x "$(readlink /tmp/chromium-link)"
230
316
  USER root
231
317
  RUN mv /tmp/chromium-link /usr/local/bin/chromium
@@ -285,12 +371,12 @@ RUN chmod +x /usr/local/bin/agentbox-dockerd-start
285
371
  COPY packages/sandbox-docker/scripts/agentbox-checkpoint-cleanup /usr/local/bin/agentbox-checkpoint-cleanup
286
372
  RUN chmod +x /usr/local/bin/agentbox-checkpoint-cleanup
287
373
 
288
- # Host-routed link opener. The box has no real browser; this wrapper forwards
289
- # http(s) URLs to the host's default browser via the relay (`agentbox-ctl
290
- # open`). It shadows xdg-utils' /usr/bin/xdg-open (the symlink lands earlier
291
- # in PATH) and is set as $BROWSER so any tool that opens a link — Claude
292
- # Code's OAuth flow, `gh`, `git web--browse`, python's webbrowser — routes
293
- # to the host.
374
+ # In-box link opener. This wrapper routes http(s) URLs to `agentbox-ctl open`,
375
+ # which opens the link in the box's own Chromium (agent-browser) and notifies
376
+ # the relay so the host user can be offered to also open it on the host. It
377
+ # shadows xdg-utils' /usr/bin/xdg-open (the symlink lands earlier in PATH) and
378
+ # is set as $BROWSER so any tool that opens a link — Claude Code's OAuth flow,
379
+ # `gh`, `git web--browse`, python's webbrowser — routes through it.
294
380
  COPY packages/sandbox-docker/scripts/agentbox-open /usr/local/bin/agentbox-open
295
381
  RUN chmod +x /usr/local/bin/agentbox-open \
296
382
  && ln -sf /usr/local/bin/agentbox-open /usr/local/bin/xdg-open
@@ -309,6 +395,10 @@ RUN printf '%s\n' \
309
395
  'set -as terminal-overrides ",*:RGB"' \
310
396
  'set -as terminal-features ",*:hyperlinks"' \
311
397
  'set -as terminal-features ",*:RGB"' \
398
+ 'set -g allow-passthrough on' \
399
+ 'set -g set-clipboard on' \
400
+ 'set -g extended-keys on' \
401
+ 'set -as terminal-features ",*:extkeys"' \
312
402
  'set -g mouse on' \
313
403
  'bind -T copy-mode WheelUpPane send -N2 -X scroll-up' \
314
404
  'bind -T copy-mode WheelDownPane send -N2 -X scroll-down' \
@@ -337,6 +427,22 @@ RUN chmod 0644 /etc/claude-code/CLAUDE.md
337
427
  COPY packages/sandbox-docker/scripts/claude-managed-settings.json /etc/claude-code/managed-settings.json
338
428
  RUN chmod 0644 /etc/claude-code/managed-settings.json
339
429
 
430
+ # Codex activity-reporting hooks. Unlike Claude's managed-settings (an /etc
431
+ # enterprise path), Codex discovers hooks at ~/.codex/hooks.json — so this is
432
+ # staged in the image and seeded into the codex-config volume by
433
+ # seedCodexHooks() at create/start time. See packages/sandbox-docker/src/codex.ts.
434
+ COPY packages/sandbox-docker/scripts/agentbox-codex-hooks.json /usr/local/share/agentbox/codex-hooks.json
435
+ RUN chmod 0644 /usr/local/share/agentbox/codex-hooks.json
436
+
437
+ # OpenCode activity-reporting plugin. Unlike Claude's managed-settings hooks,
438
+ # OpenCode has no native hooks system — its only extension surface is a plugin
439
+ # loaded from $OPENCODE_CONFIG_DIR/plugins/*.js. The plugin subscribes to
440
+ # OpenCode's event bus and shells `agentbox-ctl opencode-state` on each
441
+ # lifecycle transition. Staged in the image; copied into the OpenCode config
442
+ # volume by seedOpencodePlugin() at create/start time. See packages/sandbox-docker/src/opencode.ts.
443
+ COPY packages/sandbox-docker/scripts/opencode-agentbox-plugin.js /usr/local/share/agentbox/opencode-agentbox-plugin.js
444
+ RUN chmod 0644 /usr/local/share/agentbox/opencode-agentbox-plugin.js
445
+
340
446
  # /etc/agentbox/ holds runtime-injected box.env (written by `agentbox create`
341
447
  # via docker exec). Pre-created here so the writable layer starts with the
342
448
  # right perms; the file itself appears at create time.
@@ -7,16 +7,22 @@ description: Generate an agentbox.yaml for the current AgentBox workspace. Invok
7
7
 
8
8
  ## Box layout (what you're configuring against)
9
9
 
10
- Your user i `vscode` and you can use passwordless sudo to run commands as root.
10
+ Your user i `vscode` and you can use `sudo` to run commands as root.
11
11
 
12
- `/workspace` is the box's plain writable filesystem — a per-box git worktree on a fresh `agentbox/<box-name>` branch (or a tar-piped copy of the host workspace for non-git projects). Anything you install or build into `/workspace` (incl. `node_modules`, `.next`, `target`, `.venv`) lives in the **container's writable layer** and is captured wholesale by `agentbox checkpoint` (`docker commit`) — so a setup task that runs the install once becomes a warm-start asset for every future box in the project. Everything is wiped on `agentbox destroy`.
12
+ `/workspace` is where the user code lives, a per-box git worktree on a fresh `agentbox/<box-name>` branch (or a tar-piped copy of the host workspace for non-git projects).
13
+ Run `agentbox checkpoint --set-default` (similar to `docker commit`) to save any changes make to the system and workspace so that new boxes will start from a warm state. Everything is wiped on `agentbox destroy`.
13
14
 
14
- Three bind mounts wire the box back to the host:
15
+ Some special folders:
15
16
 
16
- - **Host main repo's `.git/`** — bind-mounted RW at its identical absolute host path. In-box commits land on the host's branch refs (visible to `git log` on the host immediately); the box itself carries no SSH/git creds, so `git push` goes through the host relay (`agentbox-ctl git push`). The host's **working tree is never written to** — only refs/objects under `.git/`.
17
- - **`~/.claude`** — a Docker named volume (`agentbox-claude-config`, shared across boxes by default) seeded from the host's `~/.claude` on each create so auth, skills, and plugins persist without leaking the host's home dir.
17
+ - **Host main repo's `.git/`** — If the box bind-mounted RW at its identical absolute host path. In-box commits land on the host's branch refs (visible to `git log` on the host immediately); the box itself carries no SSH/git creds, so `git push` goes through the host relay (`agentbox-ctl git push`). The host's **working tree is never written to** — only refs/objects under `.git/`. GitHub PR ops (`agentbox-ctl git pr create|view|list|comment|review|merge|close|reopen|checkout`) flow the same way through host `gh`; write ops require host confirmation (deny → exit 10), `merge` and `checkout` have additional opt-in guards.
18
+ - **`~/.claude`** — and similar home folders for coding agents are seeded from the host's `~/.claude` on each create so auth, skills, and plugins persist without leaking the host's home dir.
18
19
  - **`agentbox.yaml`** — read by `agentbox-ctl` from `/workspace`. Tasks and services declared here are what the supervisor will run.
19
20
 
21
+ Exposed ports and services:
22
+ - **portless** - every port with `expose:` setting in agentbox.yaml, will be exposed not only as a local port but also as a special domain name `https://<name>.localhost` (so on https) using `portless` cli and proxy. This will be also mapped to the host where also `portless` proxy is running so users can access the same service on the same looking url.
23
+ - **vnc** - the webVNC server exposed on 6080 will be proxies to the host on a random port.
24
+ - **vscode** - the vscode server is proxied to the host on a random port.
25
+
20
26
  ## Goal
21
27
 
22
28
  Produce a `/workspace/agentbox.yaml` that captures this project's services, tasks, and box defaults so the in-box supervisor (`agentbox-ctl`) can boot the workspace deterministically.
@@ -64,7 +70,7 @@ The box's primary web app (the dev server / Next.js / API the user opens in a br
64
70
  as: 80 # must be 80 — the container port AgentBox publishes
65
71
  ```
66
72
 
67
- At most **one** service may set `expose:`. AgentBox forwards container `:80` to `127.0.0.1:<port>` and publishes it on the host, so `agentbox list`/`status` show it as the box's main URL on every engine (no OrbStack dependency). Set this on the same service whose `ready_when:` you just wrote (a DB or worker should **not** get `expose:`).
73
+ At most **one** service may set `expose:`. AgentBox forwards container `:80` to `127.0.0.1:<port>` and publishes it on the host with `portless` proxy to a <boxname>.localhost url, so `agentbox list`/`status` show it as the box's main URL on every engine (no OrbStack dependency). Set this on the same service whose `ready_when:` you just wrote (a DB or worker should **not** get `expose:`).
68
74
 
69
75
  ## 4. Restart + backoff
70
76
 
@@ -179,11 +185,12 @@ Tell the user (verbatim):
179
185
  ```
180
186
 
181
187
  your box is ready, you can start more sessions with `agentbox claude`
188
+ you can access the web app at https://<boxname>.localhost
182
189
 
183
190
  ## 10. Known issues
184
191
 
185
192
  - For Nextjs/Vite/Tasnstack projects, makes sure to forward also websocket for hot reload.
186
193
 
187
- - The `install` task is intentionally a no-op once `node_modules/.agentbox-installed` exists. Do **not** remove the marker guard to "force a fresh install" — that reinstalls on every box start. To force a one-off rebuild, delete `node_modules` (or just the marker) then run `agentbox-ctl reload`.
194
+ - Service like flask, nextjs, BETTER_AUTH_URL, NEXT_PUBLIC_APP_URL should use the <boxname>.localhost url for the local development so that on the host it will use the same url as the box.
188
195
 
189
- - Host-only CLI wrappers (portless, etc.) must be bypassed, eg some projects wrap the dev server with a host-side proxy (here: `portless projectname next dev --turbopack`). Override the service command: to call the underlying tool directly (`next dev --turbopack`)
196
+ - The `install` task is intentionally a no-op once `node_modules/.agentbox-installed` exists. Do **not** remove the marker guard to "force a fresh install" that reinstalls on every box start. To force a one-off rebuild, delete `node_modules` (or just the marker) then run `agentbox-ctl reload`.