On this page
Host connections
Every Stado host operation reaches its target over one of the routes that
host's registry declaration names. The declaration is ordered, the product
tries the routes in that order, and the receipt says which one carried the
command. No connection provider is built into the product: tailscale,
lan, nebula and primary are names an operator declares, and a host that
loses one of them keeps working over the next.
Declaration
The routes live on the registry target in canonical registry.json:
targets[].sshis the preferred destination and is always the path namedprimary.- The target's alternate-route array holds the rest, read top to bottom. Each
entry carries
name(a lowercase identifier other thanprimary) anddestination([user@]host[:port]). At most sixteen are accepted, and a duplicate name or destination is refused by registry validation. stado registry host path list <host> --jsonis the read contract: oneconnectionsarray withname,destination,orderandpreferred.
A host that declares one destination behaves exactly as before: one route,
tried once. A host that declares two — say primary on its Tailscale address
and lan on build-mac.lan.example — keeps working when the Tailscale path
goes down.
The networks the product can describe are themselves declared, in
stado-rs/data/fleet/connections.json, compiled into the binary and read
through targets::declared_connection_providers. That document is the one
place the names live: the listing publishes it, Stado Desktop shows what the
listing publishes, and the connection tests draw from it instead of writing a
network name of their own. It is not a closed set — a fleet-specific name is
accepted as a route like any other — so what the declaration buys is that
every surface offering a choice offers the same one.
Choosing and changing the provider
stado registry host path list <host> [--json]
stado registry host path set <host> <path> --ssh <[user@]host[:port]> [--priority <n>] [--json]
stado registry host path remove <host> <path> [--json]
list prints the preferred path and the ordered alternates with their
positions, marks each one declared or fleet-specific against the declared
vocabulary, and ends with the networks this product describes. Under --json
that vocabulary is known_providers, an array of name and summary beside
the connections array. set adds or replaces one path: --priority places
an alternate (counting from 1); omitting it keeps an existing position or
appends. Passing --priority for primary is refused with the primary path is always preferred and does not take --priority, and removing it is refused
with the primary path cannot be removed; replace it with registry host path set. Every write goes through the canonical registry's compare-and-swap and
validates the whole document first, so a refused declaration changes nothing.
Moving a host from one network onto another follows the identity rule: two routes may not name one host, so a destination is held by exactly one path at a time. Declare the new network beside the one in use, prove the host answers on it, then release that name and hand the identity to the preferred entry, and finally declare the address the host came off under its own network name so it stays as an alternate:
stado registry host path set <host> wireguard --ssh operator@host-wg --priority 1
stado host link <host>
stado registry host path remove <host> wireguard
stado registry host path set <host> primary --ssh operator@host-wg
stado registry host path set <host> tailscale --ssh operator@host-ts --priority 1
Asking for a second route at the address the preferred entry already holds is
refused with host identity '<host>' is already declared by registry.targets[N].ssh, and the document is left byte-identical.
How a connection is chosen
stado-rs/src/deploy/host_channel/ owns the selection. A target that is
this machine is answered locally without any ssh at all. A target with one
declared route uses it. A target with several probes them in declared order
and takes the first that answers, so a dead preferred route costs one probe
rather than the operation. A target with no declared route is refused with
target "<name>" has no registry-managed SSH connection path.
The route that carried the work is reported, not inferred: host command
receipts carry used_connection with the path's own name, or local for the
machine itself. A receipt that published only the declared routes could not
distinguish a healthy preferred path from a dead one whose alternate rescued
the read.
Accounts made through the channel
stado host user create <username> (--target <host>… | --all) creates one
local account on each selected kind=local registry host that has an SSH
destination, asking for the initial password twice on the terminal and
carrying it on the channel's stdin, never in an argv. --full-name sets the
display name and --shell the login shell; either one omitted is left to the
host's account tool (sysadminctl on macOS, useradd on Linux). --admin
adds the account to the administrators, --require-password-change makes the
first login change the password, and --dry-run lists the hosts without
connecting. stado host user delete <username> --target <host> --confirm <username> [--keep-home] removes one.
Each host is reported as created, exists, plan or failed, and with
--json as one document listing every host's status, os, ssh_target
and detail; any failed host makes the run exit non-zero. A failure's detail
is the account tool's own words, whole: its stderr, else its stdout, else the
exit status. A display name or shell is refused only when it carries NUL or a
newline, which the remote command line cannot carry; how long either may be is
the account tool's limit, refused in its own words.
Where it is visible
stado registry host path list <host> --json— the declaration, andknown_providersfor the networks the product describes.stado host link <host>— the probe of every declared route, and the silences recorded against them.stado host execand the other host commands —used_connectionin the receipt.- Stado Desktop, Hosts inspector: the routes sheet lists the preferred route
and its alternates with their probe results, and its editor writes exactly
the
registry host path setandremovecalls above, showing the command line before it runs.
Source: this website