Security
Rivets is built so that your code and your model access stay on machines you control. This page describes how accounts and workers are authenticated, what data reaches Rivets, how GitHub credentials are handled, and what Rivets does not protect against.
Accounts
- Sign-in uses email and password. There is no external identity provider.
- Two-factor authentication uses a TOTP authenticator app. Turn it on under Settings › Security › Two-factor authentication. When you enable it, Rivets shows backup codes once. Save them somewhere safe.
- Native devices. Mac, iPhone, and iPad sessions are listed under Settings › Security › Native devices, with when each was last used. Choose Revoke to sign a device out.
- Organization isolation. Every request is scoped to one organization, and membership is checked on each one.
Worker authentication
A worker proves its identity with two factors, both kept in the operating system’s credential store (Keychain on macOS, Secret Service on Linux, DPAPI on Windows):
- A worker token starting with
rvw_. Rivets stores only its hash. A new token must be activated within 15 minutes or it expires. - A P-256 signing key the worker generates when it first connects. Enrollment permanently binds the key’s public half to the token.
After enrollment, every request and connection must carry a fresh ES256 signature over the method, the exact URL, the token’s hash, the time, and a one-use ID. Rivets records each ID and rejects any reuse, so a captured request cannot be replayed. A stolen token alone is not enough to impersonate a worker.
Neither secret is written to config.json, a service definition, command-line arguments, or environment variables. If no secure store is available, the worker refuses to start rather than fall back to a plaintext file.
Network
- Outbound only. Workers open an outbound TLS WebSocket to Rivets, which runs on Cloudflare. They never listen on a port, and no inbound connectivity is required or possible.
- Clients connect to Rivets over HTTPS and secure WebSockets.
- Optional direct paths. The same-machine path listens only on
127.0.0.1. The opt-in Tailscale path uses your existing tailnet, and every connection still needs a one-use Rivets ticket that expires after 60 seconds. See Terminals and scripts.
What Rivets stores
| Stored by Rivets | Stays on the worker |
|---|---|
| Account, organization, team, and repository records | Repository clones and task worktrees |
| Conversation event logs: prompts, agent messages, and tool activity | Your Claude Code and Codex logins |
| Snapshots of each task’s git status and diffs | Terminal scrollback, encrypted |
| Cached file contents viewed in the apps | Worker token and signing key |
| Prompt attachments | Service logs |
Snapshots are pruned over time. Rivets keeps the newest five per task and everything younger than 30 minutes.
Rivets runs no models. Commit messages, pull request descriptions, and task names are generated on the worker by your own agent, and the diff used to write them does not leave the machine for that purpose.
GitHub credentials
The Rivets GitHub App is the only GitHub credential Rivets uses. Workers never read your personal access tokens, SSH keys, or existing credential helpers.
When a job needs GitHub, Rivets issues a short-lived installation token. The worker passes it to each git command through a local credential helper over a Unix socket. It is never written to disk and never appears in a process listing. See GitHub.
Worker hardening
- Sandboxed file reads. When a client asks for a file, the worker resolves the path strictly inside the task’s worktree. Absolute paths,
..segments, and symlinks that point outside are rejected. Files over 1 MB and binary files are not sent. - No shell interpolation. The worker runs git and the agent CLIs with argument lists, never a shell command line built from your branch names, prompts, or paths.
- Validated input. Every message the worker receives is validated against the protocol schema. Anything invalid is dropped.
- Redaction. Rivets tokens, bearer headers, and credential URLs are stripped from logs and agent events before they leave the worker.
MCP tokens
Personal rvp_ tokens are shown once and stored hashed. Each is bound to one user and one organization, carries only the scopes you choose, can expire, and can be revoked at any time. MCP cannot manage tokens, members, settings, or workers. See MCP server.
What Rivets does not claim
- No filesystem isolation between repositories. Agents and terminals run as the worker’s OS user. A shell on a worker can reach other repositories’ checkouts and any credentials that user can read.
- Teams are not an isolation boundary for people who do not trust each other on a shared worker. They control what Rivets shows and allows, not what a process on the worker can touch. Use separate workers, in separate OS accounts or machines, for real separation.
- Checked-in scripts run automatically. A repository’s
setupscript runs when a worktree is created, before anyone reviews the branch. Turn scripts off with--no-scriptson workers that build untrusted code. See The .rivets directory. - Revoking access stops further access. It cannot take back content someone already copied.