Platform
One platform. No bolt-ons.
Everything a team needs around the agent, in the same product, on every device.
Everything around the agent, at a glance
- Builder defaulttests, video, previews, merge requests
- Reviewerreads diffs, files findings under security-audit
- Opsdeploys, backups, AWS preflight
Named personalities with their own prompt, skills and tools. Any model you configure.
Agents
Named personalities with their own prompt, skills and tools. Hire one from the library or write your own.
Each one above is a section of this page. Two more have a page of their own.
Agents
Named personalities with their own prompt, skills and tools.
An agent is a name and a handle, a system prompt, a set of specialties, and the skills and tools it is given. Mention one in a workspace's chat to put it to work, or give it recurring work on the Schedule.
- Builder defaulttests, video, previews, merge requests
- Reviewerreads diffs, files findings under security-audit
- Opsdeploys, backups, AWS preflight
Named personalities with their own prompt, skills and tools. Any model you configure.
Hire from library
A catalogue of ready-made personalities:
- project manager
- team lead
- full-stack engineer
- sales
- growth
- SEO
- GEO
- content
- design
- QA
- security
- DevOps
- data
Hiring one copies it into your organization, so tuning its prompt afterwards is yours to do. An improved version of a persona reaches new organizations rather than overwriting an agent you have already adjusted.
Tools are picked per piece of work
MCP tools are registered separately and chosen per task rather than attached to the agent. The same SEO specialist can have web search on the weekly crawl and nothing on the monthly summary, without two copies of the agent. Only the tools a schedule lists exist for that execution. The restriction is real, not advisory.
A fresh box, booted as the persona
When a scheduled task runs as an agent, its prompt is written as the box's standing instructions and its skills into the box's skills directory. The work never goes to the agent's own long-lived container.
That container accumulates state from everything the agent has ever done, and a recurring task's continuity is supposed to come from its briefing, where it can be read and switched off, not from a leftover working directory.
Recurring work, each run in a fresh box, with a memory of what earlier runs found.
A scheduled task is recurring work. Each execution gets its own box, is handed the task's description, and reports back as it goes. Once, every day, selected weekdays, or every N days.
- Backup to S3 nightly0 3 * * *ok
- Security audit, weekly0 9 * * 1ok
- Dependency bump0 7 * * 3silent run flagged
Send a task to the agent
A prompt, in a fresh box. It may name an info-only workspace, in which case the prompt goes into that workspace's box, repos checked out and context to hand. That is what “audit this every Monday” is.
Send a task to a named agent
The same dispatch, with the box booted as that persona and restricted to the tools you tick for this task. An unticked tool does not exist for that execution.
Post a chat message
No box at all. A message into a workspace's chat on a schedule.
A watchdog
A task that has not reported itself started within 15 minutes, or finished within 60, is marked failed and an admin is told. A run that silently never happened is the failure this exists to catch.
Continuity: why run 40 differs from run 1
Scheduled work used to go nowhere, and the reason was structural. Every execution got a brand-new box, the box was destroyed afterwards, the brief told the agent to treat the request as standalone, and nothing a run learned was written anywhere a later run could find. Run 1 and run 40 were the same run with a different date.
Now a task publishes under subjects and reads them back. On every dispatch DevBench assembles a “what previous runs of this task already established” section, the last few executions with their outcomes and the documents they published, and folds it into the prompt. The closing line says the opposite of what it used to: this is one execution of a recurring task, continue from what is above, and leave something the next one can continue from.
The Continuity tab answers, in plain language, why a task is not accumulating anything: seventeen runs and zero documents; continuity switched off; runs lost to a signed-out session; runs closed by the watchdog rather than reported. Consolidate folds a task's whole history into one digest document that supersedes the previous digest.
What previous runs of this task already established
- Run 40this execution
- Run 39published under security-audit
- Run 38published under security-audit
- Run 37closed by the watchdog
Continue from what is above, and leave something the next one can continue from.
Scripts kept alive in a box, restarted when they exit.
A poller, a sync, a queue reader: something that should keep running in a workspace's box whether or not anyone has the workspace open.
DevBench restarts a watcher that exits and posts to the workspace's chat when it does, so a watcher that quietly died is not something you find out about a week later. It can run continuously, on an interval, or at fixed times of day, with everything that box has.
Its script, its output and its run history are all on the page. The logs are the box's own stdout; the run history is start-to-exit per run, which is what tells you whether “it is running” means running or crash-looping. Edit the script and a running watcher restarts with the new one. Stop takes it out of service until you start it again.
- alive stripe-webhook-relay.pyrestarted 2 times this week
- alive queue-depth-monitor.shup 6 days
$ devbench watcher add <name> --script-file <path> --interval <n>
Create one from inside the box.
$ devbench watcher list
This workspace's watchers and their status.
$ devbench watcher logs <name> --tail 100
The watcher's own output.
$ devbench watcher runs <name>
Its start-to-exit run history.
$ devbench watcher edit <name> --script-file <path>
Change its code or schedule.
Shared skills with named credential profiles.
A tool is a script the whole organization shares: a scraper, a query runner, a headless browser, a research helper. Any workspace's agent can run one, so a capability written once is available everywhere instead of being re-implemented per box.
- Base environmentAWS_REGION
- staging encrypted, never returned
- prod encrypted, never returned
$ devbench tools run aws --env prod -- s3 ls
One tool, a profile per environment
Each tool carries a base environment and any number of named credential profiles. A profile is a set of variables under a name, staging, prod, so the same tool runs against different environments without a second copy and without pasting keys into a prompt.
Secret values are stored encrypted and never returned by the API; a run picks a profile with --env, and one-off values can be added at the call site.
- aws profile: prod-readonly key never in a prompt
- stripe profile: test key never in a prompt
- devbench videorecords a real browser on the preview
Written once, run by any workspace's agent
The one-line description you give a tool is what an agent reads when deciding whether to use it. Pick the interpreter, python3, bash, and so on, paste the script, and any workspace's agent can run it.
$ devbench tools list
The team's shared tools and skills.
$ devbench tools show <name>
A tool's info, env vars and profiles.
$ devbench tools run <name> --env prod -- <args>
Run one under a named credential profile.
Releases
One version across every repo.
A release ships a chosen set of repositories together, under one version. Which repos are in it is a setting; a repo nobody added is not released.
It runs entirely through your own provider token. No container is involved.
- 1
Gate
For every tracked repo, the source branch must be fully merged into the gate branch. If one is not, the release is blocked and named; you run that promotion first.
- 2
Cut
release/<version>is branched from the source in each repo. - 3
Record
The commits that are actually shipping are written into the changelog. A commit lands even where a repo has no changes, so the protocol is uniform.
- 4
Ship
The release branch is merged into production.
- 5
Tag
The release branch is tagged
v<version>.
- sourcefirst stage
- gatebefore production
- productionlast stage
Three branches carry a release, and all three are read from your git flow rather than named here: source is the flow's first stage, production its last, and the gate the stage immediately before production. A flow with fewer than three stages has no distinct gate, so the check passes trivially. A single-stage flow cannot release at all, and says so.
Show commits in this release on a past release lists exactly what shipped. Resume any pending/failed repos picks up one that did not finish.
One record of everything that happened to you.
A workspace finishing provisioning, an agent finishing a change, a mention, a merge that landed, a deploy that failed, a backup that ran partial. Newest first, grouped by day, and pushed to your phone.
- Jonas mentioned you in upload-rate-limit09:50
- Agent finished Onboarding emails, step 2 of 609:12
- Nightly backup run was silent03:00
Markdown renders
A notification written as a proper post renders as one, with its first line as the row title. Open workspace takes you to what it is about.
Two channels on the phone
Chat and Inbox arrive on their own Android channels with their own collapse keys, so an assignment is not replaced on your lock screen by the next chat message from the same workspace.
Quiet means quiet
A workspace you have not subscribed to on the phone does not buzz: not for its messages, and not for its assignments. The in-app Inbox and the unread badges are unaffected.
Owners hear what only owners can fix
A cloud account whose credentials stopped working, an integration that failed its check, a backup that could not reach a box. These go to owners, throttled per thing, so a broken account does not become wallpaper.
Team
Owner, maintainer, member. Grown by invite code, not sign-ups.
Access is a person's role plus a workspace's assignees. The rule is applied to the query itself, so no screen can leak a workspace by forgetting a check.
- Maya ownerevery workspace
- Jonas maintainerevery workspace
- Priya memberupload-rate-limit, Onboarding emails
Members reach only the workspaces they are on. The rule is in the query, not the screen.
Owner
- Workspaces they reach
- Every workspace in the organization
- Also
- Roles, invite codes, API keys, organization settings
Maintainer
- Workspaces they reach
- Every workspace in the organization
- Also
- Chooses which show on their own board
Member
- Workspaces they reach
- Only the workspaces they are assigned to, plus any they created
- Also
- Nothing more
Can manage deployments is a separate flag
No role implies it, not even owner. “Owners and maintainers” would make “who can deploy to production?” a question with two answers that drift apart, and it would bind trusting somebody with infrastructure to a decision about workspace visibility. A maintainer who reaches every workspace is not automatically the person you want spending money in the AWS account. An owner may grant it to themselves; that is how an organization gets its first person who can deploy to production.
It gates Apps and run recipes, databases and their seeds, the organization's deploy settings, cloud accounts, where an environment points and its update script, and deploying or stopping anywhere but DevBench compute. Reads are gated too. Two things stay open to everybody: previews on DevBench compute, and an environment's URL, login and notes.
Invite codes
There is no self-serve organization. A code is how somebody joins: it carries the role they join as, and can have an expiry and a use limit. No emails are involved; you hand over the code. You cannot change your own role, which is what stops an organization losing its last owner by accident.
The defaults every workspace inherits.
Eight tabs, grouped by what each decides. Each workspace has its own settings on top: General, Automation, Git & merging, Security, Notifications, and a Danger zone kept apart from the routine toggles on purpose.
AI
The agent login every workspace shares, and the organization's standing instructions: the stack, the review etiquette, the library that must never be used again. They are written into every workspace's instructions under a managed heading and rewritten wholesale on each push, so editing the text converges every box and clearing it removes the rule. Saving and Apply to all workspaces are separate, deliberate acts.
Standing instructionsevery workspace## Organization (managed)
- the stack
- the review etiquette
- the library that must never be used again
SaveApply to all workspacesWorkspace defaults
What every new workspace's container is built with, on top of the built-in language toolchains. Switching an extension off uninstalls it from workspaces created afterwards.
Board stages
The columns: rename, reorder, add, delete. The default column is also the one whose workspaces may keep a box running. A stage still holding workspaces cannot be deleted, and the refusal names it and its count.
Integrations
Your personal GitHub and GitLab tokens, used to import repos and let workspaces push.
Notifications
Where events from outside DevBench arrive, an inbound webhook, and how they reach the team.
Git flow
An ordered list of stages, each with a key, a label and a branch. The first is what work is cut from; the last is production. Every branch in the flow is protected from direct agent pushes.
Backup
App
Versions: the desktop app, and the devbench CLI inside your workspace boxes.
A few hundred kilobytes that hold everything you configured.
Every workspace's repos already live at GitHub or GitLab. Everything else, the workspaces, the git flow, the environments, the deploy recipes, the tools, the agents, the watchers, the schedules, exists in one database, and re-entering it by hand is days of work nobody has a record of.
- 1
Push
Every eligible workspace's repos are committed and pushed to their own branches, the same call the Push button uses. A stopped box can be started for it. An info-only workspace is skipped: “nothing is ever pushed from here” is a promise, and a backup is not a reason to break it.
- 2
Record
The configuration is serialized to gzipped JSON, each repo appearing as the branch and commit its work was pushed to. The repository contents are never in the file.
That ordering is what makes the size claim true: a hundred workspaces come out as a few hundred kilobytes rather than tens of gigabytes, small enough that every backup is kept. What is deliberately not in it, git objects, container images and volumes, and every kind of history, is recorded as a count, so a file opened a year from now says plainly what it is not.
Secrets are off by default. Turned on, each travels as the ciphertext already in the database; the plaintext is never written. A backup with secrets is only usable on an install holding the same encryption key, which is what makes it safe to leave one in a bucket.
Restoring
The dry run is the default, and it is performed with the same walk as the real restore, inside a transaction that is thrown away. It is also the diff: comparing two DevBench installs is exactly “restore this file into that org and tell me what moves”, answered in both directions.
Nothing is ever deleted.
Something the target has and the backup does not is reported and left alone.
Merge is the default.
Existing rows are untouched unless you ask for overwrite; restoring twice changes nothing the second time.
Code is not restored, because it was never taken.
A restored workspace points at the same repository and branch, and its box is provisioned as normal.
What cannot come back is reported rather than skipped in silence: user accounts, other people's git tokens, the inbound webhook secret, media file bytes, and, under a different encryption key, every credential. A wrong key is detected up front by test-decrypting one value, so it is reported once, and the rest still restores.
$ devbench backup
Run a backup. Download configuration in the app answers immediately, skipping the push.
$ devbench backup list
Past backups, newest first.
$ devbench backup diff <file>
What restoring this file would change, in both directions.
$ devbench backup restore <file> --apply
Actually restore it. Without --apply it is the dry run.
What AI costs, per workspace, and where the money actually goes.
Spend is collected from each box every six hours, so the figure survives the box being deleted. Look at 30 days, 90 days or 12 months.
The most useful thing on the page is where the money goes. Cache reads, the context an agent re-reads on every turn, are usually most of the bill. Long sessions and large contexts are what move that number, not how much the agent writes. Spend is also broken down by model, by workspace, by day, and by what the agents were doing, which tells you whether the money went into work or into orientation.
The page is honest about its own accuracy. Rows written before a counting bug was fixed are labelled estimated, not counted, scaled by a measured factor and shown alongside what they read as stored, because they cannot be recounted: the boxes that held the records are gone. Everything collected since is counted.
- upload-rate-limit
- Onboarding emails
- Media share-link audit
- up production, mainHetzner, over SSH
- up stagingAWS, S3 + CloudFront
- preview project/upload-rate-limitstops when idle
Monitor is the live health of the DevBench server itself: host resources, Docker, and app activity. For when the question is “is the platform healthy” rather than “what did it cost”.
The API from your own scripts.
A key acts with your account's access, so it can use every endpoint you can. Treat it as your password, not as a scoped token.
curl -H "Authorization: Bearer devbench_sk_…" \
https://<your-host>/api/auth/me/Send it as a Bearer token, or in an X-API-Key header, to any endpoint under /api. The full value is shown once, when it is created. The page has a ready-made curl to copy, and a last used column that finds keys nobody needs any more. Revoke switches one off; Delete removes the row.
Each workspace's box holds its own agent-scoped key, which is what devbench in that box authenticates with. That is why the keys list has a row named after each workspace. Revoking one stops that box's CLI, which is occasionally exactly what you want.
The same account, everywhere.
The web app, the desktop app, the mobile app and the command line all talk to the same server with the same account. There is no mobile-only backend and no desktop-only API; each is a client of the DevBench you already run.
Web
The full app. Everything on these pages, and the editor.
Rate-limit the upload endpoint and record the change working. One task, one merge request, waiting on a person.
- Agent opened
!18409:48 - Recording attached to #1209:47
- 42 tests passed09:45
The board with its three views; each workspace's Overview, Chat, Tasks, Changes, Git, Deploy, Media, Collaboration and Settings tabs; the shared editor and the session beside it; Docs, Merge requests, Releases, Agents, Schedule, Watchers, Tools, Cloud, Apps, Inbox, Tasks for you, Team, Usage, Monitor, Settings and API keys. And a Guide, one article per topic, each with a recorded walkthrough made by devbench video.
Opening a workspace gives you a browser-based VS Code with every repo cloned and checked out on the workspace's branch. It is the same container for everyone in the organization: two people opening the workspace are in one editor and one terminal session, not two copies.
Desktop
The app in a native window, plus Open on my PC in your local VS Code.
Windows, macOS and Linux.
- Clones to~/DevBench/upload-rate-limit
- On the branchproject/upload-rate-limit
- Opens withcode <folder>
Your own git credentials. No tokens are handled by the app.
$ code ~/DevBench/upload-rate-limit
The desktop app is the same UI and the same server; you sign in with your normal account and create workspaces exactly as on the web. It runs a small local server that serves the bundled app and reverse-proxies /api to your DevBench host, so there is no CORS setup and no backend change. The desktop app is a pure client of the server you already run.
Open on my PC clones the workspace's repositories to ~/DevBench/<workspace> on the workspace's branch, using your own git credentials, and runs code <folder> to open them in your local VS Code. No tokens are handled by the app. Re-opening fetches and relaunches; the browser editor stays available as a second option.
- What it needs
- git, and VS Code with the
codecommand on PATH. - Where workspaces go
- Workspaces → Choose workspaces folder… sets where they are cloned.
- A debug log
- Help → Open debug log. It records startup, the local port and API target, each proxied call with its upstream status, and clone or VS Code errors, for when a build on another machine cannot sign in.
- Where to get it
- Get DevBench, at the foot of the sidebar, has the installer for each platform. The current version is listed on Settings → App, next to the CLI version.
Mobile
Chat with push, the Inbox, the board, and the agent session, from your pocket.
iOS and Android. The token is kept in the device keychain, not in app storage.
/api/upload, 20 a minute per user.!184; it needs a person to merge.The agent is asking
Answer 429 with Retry-After?
| Screen | What it shows |
|---|---|
| Workspaces | The board as cards or a calendar: stage, box status, whether an agent is working, progress across tasks, deadline, unread count. Filter by stage, by search, or by unread, overdue and running. |
| Chats | Every workspace chat, most recently active first, with the last message and an unread badge. One screen answers where there is something new for you. |
| Inbox | Assignments, stage changes, provisioning news. Tapping a row marks it read and opens what it is about. |
| Workspace | Stage, deadline, progress, requirements, repos, branch, and the three ways into its live state. |
| Tasks | Top-level tasks with their subtasks, filterable by status, and status editable from the phone. |
| Session | The workspace's agent session in the same two views the web offers, Conversation and Terminal. The composer types into it either way, and a message starts a stopped box exactly as it does on the web. |
| Merges | The approval queue across the organization, with the human-only Merge button. |
| Chat | The workspace conversation, live. @agent puts a request to that workspace's agent, /restart starts a stopped box, and a pending question appears as a card with tappable options. |
A phone cannot host an interactive terminal, so the Terminal panel reads the pane as text, cached on the server so several phones cost one capture. A stopped box renders as off rather than as an error. Photos, videos and documents attach to a chat message from the phone's own pickers, and the share sheet can send a file straight into a workspace.
Push goes straight from your server to Firebase Cloud Messaging, with a service account you provide and no third-party relay in the path. Tapping a notification opens the thing it is about, from a cold start too. Push is opt-in per workspace, the bell in a chat's header, and that governs the Inbox as well: a workspace you have not subscribed to does not buzz.
A phone changes network constantly, so the chat socket reconnects with backoff, reconnects on foreground, and falls back to polling when it will not connect at all. The screen says Live or Offline rather than letting a stalled thread pass for a quiet one. Sends carry a client id, so a retry after a dropped connection never posts a message twice or acts on an @agent request twice.
CLI
devbench on your machine, and inside every box.
Two things with one name.
$ devbench list
Your workspaces.
$ devbench setup <id>
Clone a workspace locally on its branch.
$ devbench create -n "Name" -r <repo-id>
Create a workspace.
$ devbench commit
Push all repos, and archive the session's chats and memory.
$ devbench task done 12 --note "Rate limit in place; 42 tests pass" $ devbench video record upload-rate-limit --task 12 $ devbench mr create --target develop
- On your own machine
- Creates workspaces, clones the same setup locally on the workspace's branch, and pushes your work back. The installer embeds your API token, so
devbench listworks straight away. It needsgitandpython3, and works on macOS, Linux and Windows. - Inside a workspace's box
- How an agent reports. Tasks, notes, chat, docs, media, deploys, merge requests, watchers, tools and video all have subcommands, and it authenticates with that box's own agent-scoped key. A box holds no provider token, so gh and glab cannot work there; devbench ci is how CI runs and releases are read.
- Work on this locally
- On a workspace's Collaboration tab: one command, run in an empty folder, that clones every repo and checks out the workspace's branch, so you can work in your own editor and push as usual.
Invite only
We set your organization up with you.
Tell us about your team and the repositories you would bring; we reply within a working day.