Concepts
The handful of ideas that explain how VESPR behaves: one shared document per workspace, people and agents as equals in it, modes and approvals that keep the team in charge, and a record of who did what.
On this page
- Rooms and the shared document Built
- People and agents Built
- Modes Built
- Approvals Built
- Runners Partial
- Skills Built
- Claims and soft locks Built
- Provenance Built
- A request, start to finish
Rooms and the shared document Built
A workspace is a room. Each room has one shared document, and everything that happens in the workspace is written into it: the files, the chat, the approvals, the settings. The document is a CRDT (Yjs), a data structure that merges simultaneous edits without a central lock. That is why two people and an agent can type into the same file at once and nobody overwrites anybody.
| Part | What it holds |
|---|---|
files | Each file's path and its text. |
chat | Attributed messages with a role (user, agent, tool or approval). Agent text is streamed in live. A message may carry a thread name, a quote and attachments. |
provenance | One entry per agent edit: the file, who, the model, the chat message that caused it, and a summary. |
settings | The agent mode, where commands run, and other workspace settings such as the GitHub starting point and the first-run answer. |
claims | Which files someone is working on right now. See claims. |
usage | Token counts per agent and per person. |
runs | Run requests from the app and their output. |
ui | A short command bus from the app to your own SDE: open a file, follow an agent. |
handled, seen | Which agent took which message, and when each person was last here (for the catch-up digest). |
Presence (names, colors, who is looking at which file, cursors) is shared but not stored in the document.
The realtime server authenticates every connection with a token, keeps a snapshot of each room, exports its files to disk, and appends every document update and presence change to a log, which is what replay plays back.
Known limits: in the SDE only the files someone has open are live-synced, and the others are snapshotted when first opened; and if two people open a never-seen file at the same instant, the text of its first version can be duplicated.
People and agents Built
People and agents join a room the same way, as ordinary participants with a name, a color and a cursor. An agent has no special path into the files: it edits through the same shared document as everyone else, which is why it can have a visible cursor and why its edits merge with yours.
What makes an agent different is what it can do and what it must ask about:
- Its own identity and token. A person's token cannot start commands on a runner; only the agent can, and only after the permission rules say yes.
- Tools. It can list and read files, replace a snippet in a file, write a file, run a command, ask the Code Map, detect and start the project, read the output of a process it started, read a file someone attached, and look for a skill. It can also search the web, but that tool is off until the operator sets a web-search key.
- It never executes anything itself. It asks the workspace's current runner, after the mode has said yes.
- It answers messages that mention it. Several agents can join a room, and two of them do not answer the same message. There is no scheduler for background or parallel agents yet Planned.
- Models per role. Nemotron 3 Super serves everyday chat, edits and inline suggestions, and Nemotron 3 Ultra serves plan mode. The model that wrote something is recorded with it.
- A token meter. Counts per agent and per person are shown in the app; they are measured when the provider reports usage and estimated otherwise. The operator can cap the AI tokens used per 24 hours.
Modes Built
The mode is a setting on the workspace. It answers one question for every action an agent wants to take: may it go ahead alone, must it ask, or is it refused?
| Action | Manual | Accept edits | Auto | Plan | Bypass |
|---|---|---|---|---|---|
| Read a file | allow | allow | allow | allow | allow |
| Edit a file | ask | allow | allow | refuse | allow |
| Run a safe command | ask | ask | allow | refuse | allow |
| Run a risky command | ask | ask | ask | refuse | allow |
| Run a dangerous command | ask | ask | refuse | refuse | allow |
How a command is classified is rule-based:
- Safe: running a script in the workspace, a test runner (
pytest,python3 -m unittest,npm test,make test,cargo test,go test), a linter or formatter, read-only shell commands (ls,cat,grep,diff), andgit status,diff,log,showandbranch. Anything with a pipe, redirect, semicolon, backtick or$(is never safe. - Dangerous:
sudo,mkfs,dd if=,rm -rfon the root or home folder or on*, a fork bomb,chmod -R 777 /, andshutdown,rebootandhalt. - Risky: everything else, including network tools, installs, pipes and redirects.
On someone else's computer (a remote runner) the rules tighten: Bypass falls back to Auto, and in Auto only read-only commands count as safe, because running a script or a test suite executes whatever the workspace contains. A model-based classifier instead of these rules is Planned.
The default is Manual. Anyone in the room can change the mode, and the change is written into the chat so everyone sees who made it.
Approvals Built
When the answer is ask, the agent posts an Approve / Deny card in the shared chat and waits. The card says what it wants to do (an edit card shows the change) and on which runner. The rules:
- The first answer decides. Everyone in the room can answer. Once a card is decided, a later answer is ignored and changes nothing.
- Everyone sees who decided. The answer, the person and the time are stored with the card and appear in History.
- A card nobody answers expires after five minutes and counts as no. The agent is told not to retry the same action and to ask what the room prefers.
- Some things ask in every mode: editing a file someone else is working on, and installing a skill from outside the workspace.
From the keyboard in the SDE, Ctrl+Alt+M then A approves the newest pending card and then D denies it. From code, see decide in the Client API.
What is not here yet: roles. Anyone with a login to the server can approve any agent action in any room it can reach. Planned Owner, editor and viewer roles.
Runners Partial
A runner is any machine that can run a command for a workspace. The agent never runs anything itself; it hands the command to the workspace's current runner after the mode has allowed it. You pick the target per workspace with Runs on in the chat panel.
| Target | What it is | Status |
|---|---|---|
| Sandbox | A throwaway folder inside the agent's own container. Non-root, a 60-second limit and a 20 KB output cap. Files the command creates or changes are shared back into the workspace. | Built |
| Any server | The runner program on a small server, a cloud VM or a machine with a GPU. It dials out to the VESPR server. | Built |
| A teammate's computer | The same runner, started by that person (or by the desktop app, which asks before each workspace). Use it for builds and tests that need a real Mac or Windows PC. | Partial The runner library is built and tested on Linux. The desktop wrapper was built and launched on a Mac and is untested on Windows. No installers exist. |
One protocol covers all of them. A runner dials out to the server (so it works behind a home router with no open ports), announces itself, receives a job (workspace, command, time limit), recreates the workspace files in a temporary folder, runs the command, streams the output back and returns the exit code and the changed files. Changed files go back into the room as ordinary edits under the agent's name.
node runner/index.js --server ws://127.0.0.1:8241 --token YOUR-TOKEN --label "My computer" --allow-room demoSafety rules for every runner other than the sandbox:
- The connection is outbound only, with one token per runner that you can revoke at any time.
- The machine's owner must allow each workspace (once, always or deny).
- Every command still goes through the mode. Bypass never applies to a remote runner.
- The runner does not inherit your environment variables, runs only inside the workspace's temporary folder, has time and output limits, and never writes outside that folder.
- The approval card names the machine the command will run on, and History records every command, who approved it and its exit code, where everyone can see them.
Not built: scheduling by label, so that a job that needs macOS goes to a Mac runner. Planned And the sandbox has a caveat of its own; read the FAQ answer before you give it anything you care about.
Skills Built
A skill is a folder with a SKILL.md file (or a single .md file) that tells an agent how to do one kind of task. It starts with a small header holding a name and a description, then plain Markdown instructions:
---
name: changelog-entry
description: Write a short changelog entry for a finished piece of work.
---
# Changelog entry
1. Read the History for the change and list what was done.
2. Write one sentence a user would understand, in the past tense.
3. Name who did it, as the History does.Only the names and descriptions stay in the agent's prompt; the body is loaded when a skill is picked. Names are lowercase letters, digits and hyphens up to 64 characters, a description is up to 1,024 characters, and a body up to 64 KB. Skills come from the workspace (.vespr/skills/), an organization library or GitHub, and anything fetched from the internet is data until a person approves it. See the tour for the first-run question that sets them up.
Claims and soft locks Built
When several people and agents work at once they can collide. A claim is a small note in the shared document, "this file is being worked on by X since time T", which everyone's app can show. A claim lasts five minutes for an agent and 60 seconds for a person who is typing, and then it expires by itself.
Claims are soft: nothing stops a person from typing in a claimed file, and the edits still merge. What they do change is the agent's behavior. Before an agent edits a file that someone else holds a claim on, it asks the room, in every mode: "<person> is working on <file> right now. Edit anyway?"
Provenance Built
Provenance is the record of who wrote what and why. It is kept at three levels:
- Every character. Each insert carries an author. For an agent it also carries the model and the chat message that caused it. Because it travels with the text, it survives merges and shows up in replay and in the Code Map.
- Every agent edit. An entry in
provenancewith the file, the author, the model, the triggering chat message and a summary. History is built from it. - Every commit. The message is written from who did what and the request behind it. The git history can be blamed by author through the server.
Hover a line in the SDE to read it in one sentence: who wrote it, with which model, and because who asked what.
A request, start to finish
- A person types
@coder fix the discount bug in cart.py. The message lands in the shared chat, visible to everyone. - The agent reads the files and may ask the Code Map what depends on
cart.py. - It wants to edit. If someone else holds a claim on
cart.py, or the mode says ask, an Approve / Deny card appears. The first answer decides. - The agent takes a claim, edits through the shared document with its own cursor, and the change appears red and green in everyone's view as it is typed.
- It asks its runner to run the tests. In Auto mode a safe command goes through; in Manual a second card appears.
- Every character, the edit, the run and the approvals are recorded. History lists them, hover shows the author, and replay can play it back.