Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
38 commits
Select commit Hold shift + click to select a range
9c66cd7
runtime: add af_unix transport with url-scheme dispatch
cspinetta Apr 27, 2026
df9c57a
bridge: default to af_unix daemon discovery
cspinetta Apr 27, 2026
ab08589
tests: align fixtures with af_unix daemon default
cspinetta Apr 27, 2026
139cece
web: route vite proxy through the bridge
cspinetta Apr 27, 2026
82000fa
docs: replace tcp-by-default narrative with af_unix story
cspinetta Apr 27, 2026
148928a
deps: add axum + tokio + hyper-util stack, drop tiny_http
cspinetta Apr 28, 2026
50068b5
runtime: replace OpenOptions write probe with libc::access(W_OK)
cspinetta Apr 28, 2026
006f0a1
runtime: migrate void-box transport to hyper-util async client
cspinetta Apr 28, 2026
ada4547
orchestration: make ExecutionRuntime async, propagate through service
cspinetta Apr 28, 2026
be0c29a
bridge: replace tiny_http with axum, axum graceful shutdown
cspinetta Apr 28, 2026
d185cb8
voidctl: enter tokio runtime, dispatch via hyper-util
cspinetta Apr 28, 2026
7eeb043
runtime: switch ExecutionRuntime/MessageDeliveryAdapter to ?Send
cspinetta Apr 28, 2026
2b660f0
tests: migrate to tokio::test for async-touching paths
cspinetta Apr 28, 2026
6e7da14
runtime: drop ?Send from ExecutionRuntime + MessageDeliveryAdapter
cspinetta Apr 28, 2026
9920542
bridge: switch from LocalSet to tokio::spawn worker tick
cspinetta Apr 28, 2026
a45fb9d
tests: switch mock state from Rc<RefCell<…>> to Arc<Mutex<…>>
cspinetta Apr 28, 2026
4c5b684
tests: drop LocalSet in bridge pause/resume/cancel live test
cspinetta Apr 28, 2026
8a70339
docs: update AGENTS.md async-runtime trigger now type-bounds are Send…
cspinetta Apr 28, 2026
1f297d6
runtime: switch from current_thread to rt-multi-thread tokio flavor
cspinetta Apr 28, 2026
d0d034f
tests: promote runtime-sensitive tests to tokio::test multi_thread fl…
cspinetta Apr 28, 2026
07ac230
voidctl,tests: replace remaining std::thread::sleep with tokio::time:…
cspinetta Apr 28, 2026
99fbc41
bridge: build VoidBoxRuntimeClient once, share via Arc to worker tick
cspinetta Apr 28, 2026
766b2d3
runtime,bridge,voidctl: address review nits
cspinetta Apr 28, 2026
d76e5b9
runtime: harmonize hyper-util client wording in doc-comments
cspinetta Apr 28, 2026
038becd
tests: set VOIDBOX_DAEMON_TOKEN explicitly in tcp end-to-end test
cspinetta Apr 28, 2026
f2f023a
runtime: add try_new / try_with_daemon_url fallible constructors
cspinetta Apr 28, 2026
7925847
orchestration: tighten ExecutionRuntime trait to Send + Sync
cspinetta Apr 28, 2026
2d8b543
bridge: tighten CorsLayer, add JSON 404 fallback, drop redundant Sync…
cspinetta Apr 28, 2026
a6646ca
web: read VITE_VOID_CONTROL_BRIDGE_TARGET via loadEnv
cspinetta Apr 28, 2026
3ff12d7
voidctl: drop misleading pool-reuse claim from bridge_request doc
cspinetta Apr 28, 2026
9fe4a76
tests: loosen claim-refresh wait to 2s for CI runner tolerance
cspinetta Apr 28, 2026
d788a26
bridge: passthrough /v1/runs[/...] to the daemon
cspinetta Apr 28, 2026
db9e2be
docs: drop historical 'now' from daemon_address module header
cspinetta Apr 28, 2026
8e0225a
docs: rephrase ExecutionRuntime trait rationale in present tense
cspinetta Apr 28, 2026
019abdc
docs: replace historical narration in bridge route comments
cspinetta Apr 28, 2026
03d4e64
docs: rephrase voidctl tokio + import comments structurally
cspinetta Apr 28, 2026
e6803a4
docs: AGENTS.md async-runtime section in present tense
cspinetta Apr 28, 2026
aa4489a
docs: add source-code doc-comment style guidelines to AGENTS.md
cspinetta Apr 28, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
78 changes: 72 additions & 6 deletions AGENTS.md
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,24 @@ belongs to `void-box`.
When changing code here, preserve that boundary. Control-plane orchestration and
runtime transport concerns should stay separate.

## Async runtime

`voidctl serve` runs on a multi-threaded tokio runtime (plain
`#[tokio::main]` in `src/bin/voidctl.rs`) — the conventional default for
HTTP services in Rust. The bridge HTTP server (`axum`) and the worker tick
(`process_pending_executions_once`) both run as `tokio::spawn` tasks on
that runtime.

All async traits in the orchestration and runtime layers
(`ExecutionRuntime`, `MessageDeliveryAdapter`, `HttpTransport`,
`ProviderLaunchAdapter`) are bounded `Send + Sync`. Trait objects
(`Box<dyn ProviderLaunchAdapter>`, etc.) are `Send + Sync` by way of the
trait's supertrait. Test mocks use `Arc<Mutex<…>>` for shared recorders.

The trait surface also supports `current_thread` via
`#[tokio::main(flavor = "current_thread")]` for any future workload that
prefers it.

## Repository layout

- `spec/`: canonical specifications and design contracts
Expand Down Expand Up @@ -111,9 +129,17 @@ TMPDIR=$PWD/target/tmp scripts/build_claude_rootfs.sh
export VOID_BOX_KERNEL=/boot/vmlinuz-$(uname -r)
export VOID_BOX_INITRAMFS=$PWD/target/void-box-rootfs.cpio.gz
export ANTHROPIC_API_KEY=sk-ant-...
cargo run --bin voidbox -- serve --listen 127.0.0.1:43100
cargo run --bin voidbox -- serve
```

The daemon defaults to AF_UNIX at mode `0o600` (path-discovery chain:
`$XDG_RUNTIME_DIR/voidbox.sock` → `$TMPDIR/voidbox-$UID.sock` →
`/tmp/voidbox-$UID.sock`). Same-uid `void-control` finds it with no
configuration. To listen on TCP instead, pass
`--listen tcp://127.0.0.1:43100`; TCP requires a bearer token resolved
from `VOIDBOX_DAEMON_TOKEN_FILE`, `VOIDBOX_DAEMON_TOKEN`, or
`$XDG_CONFIG_HOME/voidbox/daemon-token`.

In a second terminal:

```bash
Expand Down Expand Up @@ -149,10 +175,17 @@ Swarm/service template requirements:
- `agent.mode: service` requires `agent.output_file`
- `agent.mode: service` must not set `agent.timeout_secs`

Health check:
Health check (AF_UNIX default; pass `--unix-socket` to curl):

```bash
curl -sS --unix-socket "$XDG_RUNTIME_DIR/voidbox.sock" http://localhost/v1/health
```

When the daemon listens on TCP:

```bash
curl -sS http://127.0.0.1:43100/v1/health
curl -sS http://127.0.0.1:43100/v1/health \
-H "Authorization: Bearer $(cat "$XDG_CONFIG_HOME/voidbox/daemon-token")"
```

Execution examples:
Expand Down Expand Up @@ -238,9 +271,15 @@ Important:

## Runtime compatibility commands

Live daemon contract gate:
Live daemon contract gate. The contract test dials the daemon directly,
so `VOID_BOX_BASE_URL` must be set; both shapes are accepted.

```bash
# AF_UNIX (default daemon listener)
VOID_BOX_BASE_URL=unix://$XDG_RUNTIME_DIR/voidbox.sock \
cargo test --features serde --test void_box_contract -- --ignored --nocapture

# TCP
VOID_BOX_BASE_URL=http://127.0.0.1:43100 \
cargo test --features serde --test void_box_contract -- --ignored --nocapture
```
Expand All @@ -249,8 +288,19 @@ cargo test --features serde --test void_box_contract -- --ignored --nocapture

Control-plane / bridge:

- `VOID_BOX_BASE_URL` — void-box daemon endpoint (default:
`http://127.0.0.1:43100`).
- `VOID_BOX_BASE_URL` — void-box daemon endpoint. Default: auto-discover
the AF_UNIX socket the daemon advertises (`$XDG_RUNTIME_DIR/voidbox.sock`
→ `$TMPDIR/voidbox-$UID.sock` → `/tmp/voidbox-$UID.sock`). Override
with `unix:///abs/path` for an explicit AF_UNIX path or
`http://host:port` to talk to a TCP-listening daemon. TCP requires a
bearer token via `VOIDBOX_DAEMON_TOKEN_FILE`, `VOIDBOX_DAEMON_TOKEN`,
or `$XDG_CONFIG_HOME/voidbox/daemon-token`; construction fails closed
if none resolves.
- `VOIDBOX_DAEMON_TOKEN_FILE` / `VOIDBOX_DAEMON_TOKEN` — bearer-token
sources for the TCP transport (mirrors void-box's resolution chain).
Token files must be owner-only (`mode & 0o077 == 0`).
- `VOID_CONTROL_BRIDGE_LISTEN` — bridge listen address (default:
`127.0.0.1:43210`). The Vite dev server proxies `/api` here.
- `VOID_CONTROL_LLM_PROVIDER` — optional global override that patches
`llm.provider` on every runtime template at launch. Set to
`claude-personal` to use OAuth from the macOS Keychain or
Expand Down Expand Up @@ -292,6 +342,22 @@ Preferred order:
- update `README.md`, `AGENTS.md`, or `docs/architecture.md` when behavior or
workflows change materially

### Source-code doc and inline comments

- explain *why* the code is structured the way it is, not how it got
there — avoid "previously did X, now does Y" and "this replaces…";
state the rationale in present tense
- keep concrete attack examples or worked use-cases when pedagogically
useful — those are illustrations, not history
- no ticket IDs (e.g. `R-*`) or PR/commit references inside doc
comments or inline comments — they belong in commit messages and PR
descriptions where they live as audit trail
- never reference a private repository by name in source — if a
reasoning trail lives in a private repo, inline the structural
reasoning here instead, or refer to a public PR/issue if one exists
- no AI-attribution trailers (`Co-Authored-By: Claude`, robot emojis,
"Generated by …") in commit messages or code

## Testing expectations

- keep unit/contract tests close to the relevant Rust logic where practical
Expand Down
Loading
Loading