website/src/content/posts/2026-07-23-flue-now-supports-agentos/page.mdx
Today, Rivet's Flue fork supports agentOS.
Cloudflare Workers popularized running backend code in V8 isolates instead of dedicated containers. Most backends sit idle waiting on a database, an API, or the network, so lightweight execution environments can start quickly and return shared capacity to the pool while they wait.
Running backends this way unlocked two things:
It turns out, agentic workloads look a lot like the backend workloads that Cloudflare optimized with V8 isolates.
An agent spends almost all of its time sitting idle waiting on inference, tool calls, and the user to respond. But the sandbox an agent works in is a full VM, booted and billed for the whole session even while it sits idle.
agentOS applies the same model to sandboxes. It exposes a Linux-compatible VM abstraction implemented with WebAssembly and V8 isolation, rather than provisioning a separate hypervisor VM for every agent session. Against a best-in-class sandbox provider, the linked shell benchmark measures agentOS as:
<video src="https://assets.rivet.dev/website/blog/2026-07-23-flue-now-supports-agentos/performance.mp4?v=1" autoPlay loop muted playsInline />
But a WebAssembly and V8 isolate is just a place to run code, and an agent needs a shell, a filesystem, and languages like Python.
agentOS runs a full Linux-compatible guest environment inside that WebAssembly isolate. The agent gets a real shell, a filesystem, and languages like Bash, Node.js, and Python. That's a real scripting layer, not a chain of tool calls.
The agent becomes part of your application, not another service:
You get Flue's developer experience on an OS built for agents.
Install Rivet's Flue preview builds and the three integration packages:
npm add "@flue/runtime@npm:@rivet-dev/labs-flue-runtime"
npm add --save-dev "@flue/cli@npm:@rivet-dev/labs-flue-cli"
npm add @rivet-dev/flue @rivet-dev/agentos @rivet-dev/agentos-flue rivetkit
@rivet-dev/labs-flue-* provides preview builds of Flue's proposed extension APIs.@rivet-dev/flue runs Flue agents and workflows as durable Rivet Actors.@rivet-dev/agentos and @rivet-dev/agentos-flue provide the isolated VM actor and connect Flue's sandbox API to it.Register the VM, point Flue's Rivet target at it, and attach it as the agent's sandbox:
<CodeGroup workspace> ```ts actors.ts import { agentOS, setup } from "@rivet-dev/agentos";const vm = agentOS();
export const registry = setup({ use: { vm } });
```ts flue.config.ts
import { defineConfig } from "@flue/cli/config";
import { rivet } from "@rivet-dev/flue";
export default defineConfig({ target: rivet() });
import { createAgent } from "@flue/runtime";
import { agentOSSandbox } from "@rivet-dev/agentos-flue";
import { registry } from "../actors";
export default createAgent(() => ({
model: "anthropic/claude-sonnet-5",
sandbox: agentOSSandbox({ actor: "vm", registry }),
}));
Then run it using Flue's standard one-shot command:
npx flue run assistant --id local \
--input '{"message":"Write hello from Flue to /workspace/hello.txt, run wc -c /workspace/hello.txt, then read the file back."}'
Each agent instance and each workflow run gets its own durable Rivet Actor and SQLite database, so accepted work recovers after an interruption.
Most of what an agent does is read and write files, so the filesystem is where a sandbox earns its keep.
Every Flue context gets a persistent filesystem by default that survives sleep and wake with no setup, backed by Rivet Actors' storage. The adapter derives a stable VM key from the Flue context ID, so reusing a context reconnects to the same files. Anything else you want the agent to see gets mounted at a path, the same way you'd mount a disk:
import { agentOS, setup } from "@rivet-dev/agentos";
export const vm = agentOS({
mounts: [
{
path: "/mnt/data",
plugin: {
id: "s3",
config: { bucket: "my-bucket", prefix: "agent-data/", region: "us-east-1" },
},
},
],
});
export const registry = setup({ use: { vm } });
The vast majority of agent work never needs more than the VM. Desktop automation, heavy compilation, and full browsers do.
Instead of provisioning a heavy sandbox for every agent on the chance that one task needs it, agentOS starts one on demand and tears it down when the task finishes. The common path stays in the lightweight WebAssembly isolate, and you pay sandbox cost and sandbox cold starts only for the small slice of work that actually requires one.
It's the same execution ladder Workers developers already reach for. Escalate to a container only when you're limited by the WebAssembly isolate itself, or call out to an external service such as image resizing or a browser for work that doesn't fit in a WebAssembly isolate.
Mounting a full sandbox takes two extra packages:
npm add @rivet-dev/agentos-sandbox modal
import { agentOS, setup } from "@rivet-dev/agentos";
import { modal } from "@rivet-dev/agentos-sandbox/modal";
export const vm = agentOS({
sandbox: {
// Also supports Daytona, E2B, Vercel, Cloudflare, and other sandbox providers.
provider: modal(),
},
});
export const registry = setup({ use: { vm } });
Browsers arrive the same way, as a software package such as Browserbase:
import browserbase from "@agentos-software/browserbase";
import { agentOS, setup } from "@rivet-dev/agentos";
export const vm = agentOS({
software: [browserbase],
});
export const registry = setup({ use: { vm } });
Most sandboxes are extra infrastructure: a service the provider hosts for you, reached over an API, with its own latency and its own bill.
agentOS is just a library. The same code that manages your agent runs inside the backend you already operate, and that backend runs both your agent and its sandbox. There's no hypervisor, no nested virtualization, and no provider sandbox API to code against.
It works with Node.js, Bun, or Deno on platforms such as Rivet, Railway, Kubernetes, or Vercel. (agentOS doesn't run on Cloudflare Workers yet, since it relies on OS-level APIs, but the same WebAssembly target we use to run agentOS in the browser experimentally makes future support possible.)
This integration currently runs on Rivet's Flue fork. We're opening upstream pull requests soon to merge our generic, provider-agnostic extension API that lets Rivet plug into Flue.