Back to Rivet

Flue now supports agentOS

website/src/content/posts/2026-07-23-flue-now-supports-agentos/page.mdx

2.3.98.2 KB
Original Source

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:

  • Startup got cheap: There's no dedicated container to provision on a cold start, so a Worker starts in milliseconds.
  • Idle got free: The shared runtime can pause your code while it waits on an external request and bill you nothing for the wait.

It turns out, agentic workloads look a lot like the backend workloads that Cloudflare optimized with V8 isolates.

Why agentOS: the isolate model for sandboxes

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 />

A full Linux-compatible environment on WebAssembly

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:

  • Library, not extra infrastructure: install from npm and run it in the backend process you already operate.
  • Direct function calls, not extra APIs: connect agents to your application with ordinary JavaScript instead of another network service.
  • Scoped access, not exposed credentials: bind trusted host functions without ever giving the agent your raw secrets.

You get Flue's developer experience on an OS built for agents.

Building a Flue agent with agentOS

Install Rivet's Flue preview builds and the three integration packages:

sh
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() });
ts
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 }),
}));
</CodeGroup>

Then run it using Flue's standard one-shot command:

sh
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.

Giving it a filesystem

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:

ts
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 } });

Heavier compute on demand

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:

sh
npm add @rivet-dev/agentos-sandbox modal
ts
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:

ts
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 } });

Just a library, deploy anywhere your backend runs

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.)

Working upstream with Flue

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.

Get started