Skip to content
agentvfs ★ GitHub

Rust · MIT · crates.io/crates/agentvfs

A workspace runtime and execution boundary for AI agents.

agentvfs gives an agent an isolated vault, lets it fork the vault per task in milliseconds, checkpoints before risky work, mounts the workspace as a real directory, and runs one top-level command through a policy-gated proxy boundary — returning stdout, stderr, exit code, and a changed-files summary as one structured envelope.

The proxy boundary, in one line

agentproxy boundarymounted forked workspacecli tools

The proxy mediates between your agent and the workspace. It governs which commands run, creates checkpoints around risky ones, and reports the filesystem delta back as structured JSON.

What the boundary actually enforces

Six concrete capabilities

Workspaces

Isolated vaults, not your host fs

Each agent operates inside a vault — a single-file workspace (SQLite by default, Sled or LMDB optional) that lives at ~/.avfs/vaults/<name>.avfs. The agent never touches your real filesystem.

Forks

Cheap per-task workspaces

`avfs vault fork` clones a vault into a task workspace in milliseconds. Run experiments in parallel without copying files, and discard the fork when the task is done.

Checkpoints

Rollback before risky work

`avfs checkpoint save` creates a rollback point. If a proxy execution mutates state in a way you didn't want, `checkpoint restore` snaps the workspace back. Risky commands can auto-checkpoint via policy.

Proxy boundary

One top-level command surface

`avfs proxy exec -- <cmd>` is the agent-facing execution surface. The PolicyEngine classifies the command, MountSession mounts the workspace via FUSE, the command runs, and a ChangeSummary plus exit metadata come back as one structured envelope.

Tooling

Standard CLIs just work

Workspaces mount as real directories, so `git`, `cargo`, `npm`, `python`, `jq` run unchanged inside the boundary. No syscall shimming, no special agent SDK to learn.

Structured I/O

JSON output designed for agents

Every command supports `--json`. `proxy exec` returns a versioned ExecutionEnvelope with stdout, stderr, exit code, duration, policy decision, and the list of changed files. Errors return typed `{error, message, ...}` objects.

Install

Three ways to get the binary

The native Rust crate is the source of truth. The npm and pip packages are wrappers that resolve the matching native binary — useful if your agent infrastructure is JS- or Python-shaped.

Rust crate cargo install agentvfs

Native crate; library API also available.

npm wrapper npm install -g agentvfs-cli

CLI wrapper, fetches the matching native binary.

pip wrapper pip install agentvfs-cli

Auto-fetches binary to ~/.cache/agentvfs/<version>/. AGENTVFS_BIN overrides.

Quickstart

Five commands, end-to-end

Create a vault, fork it for a task, checkpoint, and run a real command through the proxy boundary.

~ avfs
# Create a workspace vault
avfs vault create myproject

# Fork it for a single task
avfs vault fork myproject task-001 --use

# Checkpoint before something risky
avfs checkpoint save before-refactor

# Run a command through the proxy boundary
avfs proxy exec -- cargo test

# → ExecutionEnvelope: stdout, stderr, exit_code, changed_files

Production runtime details

What survives concurrent access

These are the invariants the runtime currently holds. They come from the production-features section of the README and the architecture document in docs/architecture.md.

Atomic transactions

All SQLite mutations use BEGIN IMMEDIATE / COMMIT / ROLLBACK, eliminating race conditions during concurrent access.

Bounded execution

ExecutionTimeout is configurable as None or Millis(u64) (default 300s) with SIGTERM-then-SIGKILL escalation and dedicated pipe-drain threads.

Explicit mount lifecycle

MountSession owns mount/unmount through a state machine with double-unmount protection and automatic cleanup on drop.

Backend deduplication

A weak-reference cache ensures one backend handle per vault, preventing resource leaks under concurrent access.

Open-file state tracking

FUSE file handles transition Open → Dirty → Persisting → Flushed, eliminating double-persist races.

Quotas

Per-vault `max_size_mb`, `max_files`, and `max_file_size_mb` block runaway writes with typed QuotaExceeded errors.

How one proxy execution flows

Six explicit stages

01

Request

Agent calls `avfs proxy exec -- <cmd>`. The runtime parses the top-level command into an ExecutionRequest.

02

Classify

PolicyEngine returns allow, allow_with_checkpoint, deny, or require_approval. Pure function — no fs side effects.

03

Checkpoint

If policy says so, CheckpointService saves a rollback point before the workspace is mutated.

04

Mount

MountSession exposes the vault as a real directory via FUSE. State machine drives `Validating → Mounting → Executing → Completed`.

05

Execute

Command runs with the configured ExecutionTimeout (default 300s). SIGTERM then SIGKILL on timeout; pipe-drain threads collect stdout/stderr.

06

Report

ChangeSummary lists what changed. ExecutionResult ships back as a versioned ExecutionEnvelope JSON contract.

The runtime services live under src/runtime/: PolicyEngine, WorkspaceService, CheckpointService, MountSession, ChangeSummaryService, and ProxyRuntime — the extension seams of the system.

Honest comparisons

Where agentvfs fits

There are good tools next to agentvfs that solve overlapping problems. We compare two: one container baseline and one AI-agent sandbox SaaS.

FAQ

Questions before you embed it

+ Is agentvfs a sandbox like Docker or a microVM?

No. agentvfs is a workspace runtime: a vault (single-file database) plus a proxy boundary that classifies, checkpoints, mounts, and runs one top-level command at a time. It is explicitly a top-level command boundary, not a syscall monitor or kernel-level sandbox. The README and ROADMAP both list full syscall tracing and complete subprocess visibility as explicit non-goals.

+ How is the workspace exposed to commands?

Via a FUSE mount. The MountSession transitions through explicit states, exposes the vault as a real directory, and tears down on drop. Standard CLIs (git, cargo, npm) see a normal filesystem path. FUSE-backed runtime pieces are feature-gated behind `--features fuse`.

+ What languages can an agent call agentvfs from?

Anything that can spawn a subprocess and parse JSON. The README ships native install via cargo, an npm CLI wrapper, and a pip wrapper that auto-fetches the matching native binary. The integration guide demonstrates Python; any language that runs `avfs --json <cmd>` works.

+ What backend should I use in production?

SQLite. The docs note that SQLite is the recommended production backend and that LMDB and Sled backends do not yet have atomic transaction wrappers. Sled and LMDB are pluggable via feature flags (`sled-backend`, `lmdb-backend`).

+ Does the proxy guarantee that a script cannot escape the workspace?

No, and agentvfs is honest about this. It is a top-level command boundary: it does not try to observe every subprocess launched from inside scripts. Pair it with OS-level isolation (containers, microVMs, seccomp) if you need stronger guarantees against a hostile process.

+ What does the policy engine actually decide?

PolicyEngine classifies a top-level command and returns one of `allow`, `allow_with_checkpoint`, `deny`, or `require_approval`. It is side-effect-free and evaluated before any expensive workspace work, so denied commands never touch the mount.

+ Is it open source?

Yes — MIT-licensed, published to crates.io as `agentvfs`. Source lives at github.com/neul-labs/agentvfs.

Explore the docs

Everything else, one hop away

The full surface, the execution path, the workflows it's built for, step-by-step guides, and honest comparisons — each section is its own page.

Give your agent a workspace it can't escape by accident.

MIT-licensed, single-binary install, library API in Rust, JSON contract for everything else. The proxy boundary is the cheapest useful place to draw the line.