WheelmachineDocs
Open app

Organisations and teams

An organisation is an account of its own, held by the people in it: its machines, keys, secrets and spending are its own. Each person in it has a role, and each person's machines are their own.

wm

$ wm orgs
ID                              NAME  ROLE    PEOPLE  PRIMARY OWNER
acc_01jb2xk3n4p5q6r7s8t9v0w1x2  Acme  member  12      no
$ wm login --account acc_01jb2xk3n4p5q6r7s8t9v0w1x2
$ wm me
account:       acc_01jb2xk3n4p5q6r7s8t9v0w1x2
organisation:  Acme (acc_01jb2xk3n4p5q6r7s8t9v0w1x2)
person:        Mira Okafor (acc_01ja9wq7n4p5q6r7s8t9v0w1x2)
role:          member
teams:         prj_01jb2xk3n4p5q6r7s8t9v0w1x2
limits:        at most 5 machines, at most 16 CPUs at once, at most $200.00 a month; GPU machines: no
key:           key_8c41d07e2b9a6f13 "wm on laptop"
...

An organisation#

Anyone signed in to the dashboard can make an organisation. Whoever makes it is its primary owner, who can transfer or delete it. It begins with one team, Default, and with your own account's limits. A person is primary owner of at most 5 organisations at once. People, invitations and teams are managed in the dashboard; a program works in an organisation with a key made there.

Its primary owner deletes an organisation once it holds no machine: its secrets are deleted, its keys stop working, and its people are taken out of it. Deleting it, transferring it to another owner, and making someone an owner - by their role or by an invitation - each need a code we e-mail you (Confirm codes). In your own account nothing of this changes: everything in it is yours, and you are its owner.

Roles#

RoleSeesDoes
ownerEvery machine and every key, the people, the teams and the audit.Everything but use another person's machine: watches its screen, starts, stops, pauses and deletes it, sets its name, team, labels, secrets and internet, and forks it and backs it up. Invites and takes out people, and changes roles and limits. The primary owner transfers it to another owner, and deletes it.
adminAs an owner.Everything but change owners and the organisation's own limit for the month: makes nobody an owner, invites no owner, changes no owner's role or limits nor another admin's limits, takes no owner out, and does not delete the organisation.
billingWhat every machine costs, by its name and whose it is, the people and the teams - and no machine.Sets the organisation's own limit for the month, signed in to the dashboard, and a member's limit for the month - nothing else. Opens no machine: no command, file, terminal, screen or private address.
memberIn their teams, the machines they hold - the ones they made, forked or were handed - and in a team they manage the machines its members hold.Makes and uses the machines they hold in their teams: commands, files, terminals, screens, ports and apps. Forks them with the OK of a full manager of the team, an owner or an admin (see Forks wait for an OK). Makes GPU machines when their limits let them, and keys for their own work.

Only the person who holds a machine uses it. Owners and admins see every machine and can watch its screen, view only: no keyboard, mouse or clipboard (access: watch). Each watch is in the audit. A screen being watched ends soon after its machine stops running. If a holder has left, an owner or admin can use the machine. An organisation keeps at least one owner, and its primary owner transfers it before their own role changes.

A team is a project with people in it: wm and the API say project. Owners and admins put people in teams, and may make a member one of a team's managers, at a level. Owners, admins and billing are not limited to a team; members see the projects of their teams alone.

WhoSees which machines
An owner or an adminEvery machine of the organisation.
A team's manager, at any levelTheir own, and the machines the members of their team hold there - never an owner's or an admin's.
A memberTheir own, in their teams.
BillingNone: what each costs, under Usage.

Taking a person out of a team stops their keys for it and closes what they have open; they can open again what they still may.

Managers' levels#

Each of a team's managers has a level, and each level does what the one before it does, and more:

LevelIn the team
ApproverSees the machines its members hold and watches their screens, and approves or declines the team's hand-offs that wait for a manager.
Team managerAlso starts, stops, pauses and deletes its members' machines, sets their name, labels and internet, and takes their secrets away. Puts the organisation's people in the team, and takes out those with no level. Sets the limits of members with no level whose every team they manage, up to the team's budget and never above what an owner, admin or billing set.
Full managerAlso approves or declines the forks of the team's machines, which wait for a full manager, an owner or an admin - their own fork is made at once; sets the team's rules; and makes a person an approver, or no longer one.

Owners and admins do all of it, in every team, and give or take away any level. A level is a member's alone, and a team's managers invite nobody into the organisation. No level uses, forks or hands off a member's machine: only its holder uses it, and its holder and the organisation's owners and admins fork it and back it up. In the API a person's place in a team says their level - approver, manager or full; GET /v1/me says yours in levels, by team.

Forks wait for an OK#

Every member's fork waits for the OK of a full manager of the machine's team, an owner or an admin. Until then it is a request under Requests, and nothing is made. Asked with a key, it first waits for your own OK in the dashboard. Full managers, owners and admins fork at once. Where the team's Forks rule is Off, members and managers cannot fork.

wm

# in an organisation, a member's fork prints its request: it waits for an OK
$ wm machines fork build-box --name build-box-try

wm machines fork prints the request while the fork waits, and wm requests lists it. In the libraries, machines.fork answers the request while it waits: in Python a MachineRequest, in TypeScript a Machine or a MachineRequest, told apart by object. The API answers 202 with the request (object is request, its holder and receiver both you, and for a fork from a backup its backup and cpus); asked again while it waits, the fork is answered with the same request (200). Once it is approved, the request is done, with the fork in result.

Handing off and forking for a teammate#

A machine can be handed off to a teammate exactly as it is, or forked for one with its sign-ins cleared. The person who made a machine hands it off; a machine handed to you can only be given back. Its holder, owners and admins fork it for someone. A teammate may also ask. What waits for you is under Requests.

wm

$ wm machines hand-off build-box --to ravi@example.com
ID                             WHAT      MACHINE    ASKED BY     FOR   STATE                    AGE
rq_01jb2xk3n4p5q6r7s8t9v0w1x2  hand-off  build-box  Mira Okafor  Ravi  Waiting for Mira Okafor  0s
made with a key, it waits for your own OK: approve it signed in to the dashboard, https://app.wheelmachine.ai/requests
$ wm machines fork build-box --for ravi --why "for the demo"
ID                             WHAT  MACHINE    ASKED BY     FOR   STATE                    AGE
rq_01jb2xk3n4p5q6r7s8t9v0w1x3  fork  build-box  Mira Okafor  Ravi  Waiting for Mira Okafor  0s
made with a key, it waits for your own OK: approve it signed in to the dashboard, https://app.wheelmachine.ai/requests

The teammate is named by their @handle, id, e-mail address or GitHub login. Signed in, it happens at once when nobody else must approve it; otherwise it waits as a request. With a key, it first waits for your own OK in the dashboard. A team rule set to Off refuses it, unless an owner or admin does it. Rules, limits and budgets are checked again as it is carried out. Then:

A fork of another person's machine for yourself, from it as it is or from a backup, is cleared the same way.

Taking back and giving back#

The person who handed a machine off can take it back at any time, with nobody's OK (Take back). It comes back exactly as it is then, the holder's sign-ins included, paused with its memory kept. So put nothing in it you would not give the person who handed it to you. The holder can give it back the same way (Give back). Made with a key, either waits for the OK of the person who made the key in the dashboard.

wm

$ wm machines take-back build-box
$ wm machines give-back build-box

What a fork for a teammate clears, and what stays#

A fork for a teammate is made live from the machine - its memory, the programs running in it and its screen - cleared before it is theirs, its internet closed until then; a hand-off is not cleared at all. Gone:

What holds a sign-in open is ended first: the dashboard's terminal tabs, root's too, with what runs in them; the browser; an agent signed in with its own account; and the SSH and GPG agents. Your own machine keeps its terminal tabs. An agent running on the machine's AI keys keeps running, OpenClaw and Ollama start again, and the windows that were open open again in their order - the browser on its tabs, signed out. A machine that holds no memory - stopped, or archived - is forked by its files; an older machine may be cleared whole, its browser opening on no page.

Stays, named before you send and never by value:

The dashboard says how many in one chip beside Fork for a teammate, and each of them when it is tapped; POST /v1/machines/{machine_id}/check says it all and clears nothing - though, woken to be asked, a machine may restart first, its files kept and its programs ended (restarted). A machine that cannot be cleared yet refuses the check, a hand-off and a fork for another person, and a fork of another person's machine for yourself (Fork, For Me). One that could not clear something says what, and stays its giver's.

Requests#

A hand-off or fork that needs someone else's OK, and every ask from a teammate, is a request. It waits on each step below in turn.

StepDecided byWhen
The OK of the person who made the keyWhoever gave or asked it, signed inIt was given or asked with a key - wm's, a library's or an agent's. Their right counts from then, as if they had given or asked it signed in.
The holder's OKThe machine's holderSomeone asks for one of theirs, and they pick which as they approve.
A manager's OKFor a fork, a full manager of the machine's team; for a hand-off, a manager of it at any level; or an owner or adminEvery fork, of a machine of one's own or for another person; a hand-off when the team's rules say Ask.
An admin's OKAn owner or adminIt goes into another team.

wm

$ wm requests
ID                             WHAT             MACHINE    ASKED BY     FOR   STATE                       AGE
rq_01jb2xk3n4p5q6r7s8t9v0w1x4  asks for a fork  -          Ravi         Ravi  Waiting for Mira Okafor     2m
rq_01jb2xk3n4p5q6r7s8t9v0w1x3  fork             build-box  Mira Okafor  Ravi  Waiting for a full manager  5m
$ wm requests ask hand-off --of mira --why "taking over the build"
$ wm requests take-back rq_01jb2xk3n4p5q6r7s8t9v0w1x4

Team rules#

Each team has rules, set on its Rules page under Teams by its full managers, owners and admins - each choice saved as it is tapped - and read by everyone in it. Beside them, what its machines came to this month and how many are open to the internet are shown to its managers, its owners and admins and billing; to its members they are null.

RuleChoicesWhat it holds
Hand-offsFree, Ask, OffWhether its machines are handed off to teammates freely, with a manager's OK, or not at all.
ForksAsk, OffAsk: every member's fork of its machines - of their own, or for another person - waits for the OK of a full manager of the team, an owner or an admin. Off: no member forks them, a full manager neither.
GPUsOn, OffOff: no GPU machine is made, forked, started or moved into it.
Open internetOn, OffOff: no machine with open internet is made, forked, started or moved into it, and none is opened to it - nor given a list as wide as the whole internet (an IPv4 range wider than /8, or an IPv6 range wider than /16). One running open already stays so until it is changed.
Monthly budgetAn amount in the organisation's currency, or noneWhat its machines may come to in a month. Used up, its running machines are paused, and making, starting, forking or running anything in one answers 402 payment_required. Told at 50%, 75%, 90% and 100% to the owners, admins, billing and the team's full managers (Alerts).
Largest machineCPUs, or no limitNo machine bigger is made, forked, moved or handed into it. One bigger already keeps running and waking, but does not start again in the team: move it to another, or fork it from a backup at the size allowed.
Longest idleA length of time, or no limitThe longest its machines stay up idle before they sleep. A new machine may not ask for longer, or never to sleep; one saying nothing waits no longer than the rule. Set, the team's machines set longer are lowered to it at once - a machine running now takes it as it next wakes or starts - and a machine forked, moved or handed in is too. The shortest wins.
Public portsOn, Links only, OffLinks only: no port of its machines is opened to the whole internet, and those that are become private as the rule is set; a five-minute share link still works. Off: no link is made either, and every link made before stops working.
Types onlyOn, OffOn: its members and managers make machines from its machine types alone, and neither change a machine's internet in it nor move one into it. Owners and admins set it, and are not limited by it.

The rules' answer also says models: allowed where a list of allowed models holds the team or the whole organisation (Allowed models), else any. It is read here, and set there.

A team with no rules has the defaults: hand-offs and forks Ask; GPUs, open internet and public ports On; no budget, largest machine or longest idle. A refused call answers 403 forbidden in the rule's own words (Forks: Off in Lab), with a rule member. Owners' and admins' own hand-offs go past a rule, and the audit says which (past_rule). GET /v1/projects/{project_id}/rules reads the rules (wm projects rules); PUT needs the first five named; PATCH changes only those it names. Setting them answers, in applied, what they did to the team's machines.

Machine types#

A team's owners and admins save the kinds of machine its people make, on the Types page: a name, a size, its apps, its internet, when it sleeps and is archived, and which repositories and folders it reaches. A machine keeps what its type said when it was made ("type" in POST /v1/machines, wm machines create --type); only its repositories and folders follow later changes.

GET /v1/projects/{project_id}/types lists them, with the apps a type may turn on; POST saves one, PUT .../types/{type_id} changes it, said whole - its repositories and folders, left out, stay as they are - and DELETE deletes it once no machine of the team is of it, signed in, as an owner or an admin. wm machines types lists them.

Under Types only, members and managers fork only machines of the team's types, at their size, and turn on only the apps of their machine's type.

Machines for others#

Owners and admins make machines for anyone in its team; a team's managers for members with no level; a member for themselves. They are made from one of the team's types - or, where the team has none, as the call says: size, sleep and internet, like one machine. One call answers for each machine: made, on its way, or refused with why. What the organisation and team may spend is checked for the whole batch first. Each is its person's own from the start; the person who made it never takes it back, and its person may give it back. POST /v1/machines/batch; wm machines new --type builder --for @ada,@lin or --everyone.

Switching between accounts#

In the dashboard you act in one account at a time: your own, or an organisation you are in, chosen by pressing your picture at the top of the page, where you can also make a new organisation. Each tab keeps its own choice, and a new tab begins in the one you chose last, so two tabs can be in two accounts, and neither acts in the other's.

A key belongs to the account it was made in, and acts there alone: a key's call naming another account in X-Account is refused with 400 invalid_request. To work in an organisation from a program, give it a key made there. wm login --account <id> asks for one: the page you approve on shows that organisation first, and you choose there. wm orgs (GET /v1/orgs) lists the organisations you are in, with a key of your own account.

@handles#

Everyone has an @handle, shown with their name: "Ada Lovelace · @ada". It is lower-case letters, digits and -, 2 to 30 characters. A few words are reserved. Change it on your Account page or with PUT /v1/me/handle. The API and wm take @ada wherever they take a person's id or e-mail address.

Invitations#

Owners and admins invite people on the People page, up to 30 at once, by e-mail address, @handle or GitHub login (without an @), with a role, teams and limits. Each link is shown once to whoever invites. E-mail and @handle invitations are also e-mailed (emailed); send a GitHub login's link yourself (E-mails). The link:

Opened before signing in, the link says the organisation, who invites you and the role. Signed in, you read what the organisation can see of your machines (below), pick your @handle, and join with the invitation's role, teams and limits. An organisation has at most 100 invitations waiting.

What your organisation can see#

Before you join, the invitation tells you what its people can see of your machines there:

Billing sees what each machine costs, and opens none.

Keys in an organisation#

See Keys in an organisation. wm keys ls says who made each key, in MADE BY. A member in no team yet makes no key. A key made in an organisation lists no organisations.

Limits for each person#

Each person may have limits of their own: machines held, CPUs at once, GPU machines and a month's spend, in the organisation's currency. See Your limits in an organisation.

The audit#

The audit says what was done in the account: when, by whom - the person, and the key or the sign-in they did it with - what, to which thing, and from where. What the API does by itself says system, and what we did says wheelmachine, and no more. It is read with a key that holds every scope (cloud:*), and in an organisation by its owners and admins alone.

wm

$ wm audit --action machine. --since 7d
TIME (UTC)           PERSON       ACTION                 TARGET                        FROM
2026-10-23 11:02:41  Mira Okafor  machine.terminal.open  m_01jb2xk3n4p5q6r7s8t9v0w1x2  203.0.113.7
2026-10-23 09:30:12  Mira Okafor  machine.create         m_01jb2xk3n4p5q6r7s8t9v0w1x2  203.0.113.7
$ wm audit --out audit.csv
wm: wrote 48213 bytes of CSV to audit.csv

GET /v1/audit gives a page at a time, the newest first, narrowed by one person, by what the actions begin with (machine., member.) and by time. GET /v1/audit/export gives it whole, as CSV or JSON: a year at most, the last one when since is left out, and 100,000 events at most. See the reference.

When someone leaves#

Anyone but the primary owner may leave; owners and admins can remove people. Their machines stay the organisation's. Their keys stop working and what they have open ends. A link already made still works: unopened for five minutes, opened for up to an hour.