Remote commands and the authority's snapshot
How a remote command reaches a host whose service directory route is held, and what the registry authority's status and snapshot answer from.
A remote command rides the host channel to the host it names. The channel is
a new SSH connection, not the resolver's session: a resolver session to a
host can stand while the host answers a new session at once, and refusing
every command to such a host left its one diagnostic unsent. Every command
that rides the channel (host exec, host uptime, host ping, service logs, a delivery, a reclaim) therefore reads the published list first, and
when this host's resolver holds connections to that host unanswered longer
than the refresh interval it asks every declared path to the host, even a
single one. A path that answers carries the command, saying stado: <host> answers over <path> (<destination>) although this host's resolver holds it: <held>; the command goes over that channel on stderr, where <held> is
this host's resolver holds <N> connection(s) to <host> unanswered longer than the <interval>s refresh interval it declares (services <names>): <the held wait's sentence>; stado resolver status lists every one. When no path
answers the refusal is <held>; target <host> has no reachable SSH connection path (<each path's failure>), and when the channel key cannot be read from
the vault it is <held>; and the key <host>'s command channel authenticates with cannot be read: <cause>, so the vault's error never stands in for the
host's state. A published list that cannot be read refuses with whether <host> answers cannot be told before sending to it: <cause>. A command to
this machine itself rides no channel and is not read against the list. The
real test tests/service_directory/held/held.rs sends host uptime to the
held fixture's target from a machine that is not it and reads the held
reading beside the key failure.
A declared repair is the exception: stado repair <service> --target <host> --apply sends its steps to a host whose services stand, saying stado: sending the declared repair of <service> to <host> although it stands: <the held sentence> on stderr, because that repair (stado repair skarbiec --step crypto, Skarbiec's own recover-daemons) is what clears the wedge holding
them, and refusing it would leave the host with no product path out.
The registry read every host command starts with asks the same of the
registry authority before it runs stado resolver snapshot there over SSH:
an authority whose services this resolver holds unanswered past the refresh
interval is not asked, with the same held reading (this host's resolver holds <N> connection(s) to <host> unanswered longer than the …; whether the registry authority <host> answers cannot be told before asking it: <cause>
when the list cannot be read), and the read goes
on to the store and then the last-known-good copy, announcing which. A
snapshot command sent to such a host reads the same vault and stood with it,
and every host command stood behind it before sending anything of its own.
Every command run on the authority over SSH — stado resolver snapshot, a
registry write, a key or route step — passes each line it writes to stderr
on to the caller's stderr as it arrives, as <destination>: <line>, and
keeps the whole of it for the refusal when the command fails. The
authority's Stado announces its own waits there (czekam: …, koniec czekania: …), so a caller standing minutes on the authority reads what the
authority itself stands on instead of only how long it took.
A request already sent when the route it rides stops answering is not
waited on without end either. Every request that rides a resolver route —
an object API request (the registry read behind every command, stado resolver status among them), a Skarbiec request, and the authority's
stado resolver snapshot over SSH — reads the published list again at every
refresh interval the target declares while it is unanswered; once a
connection on the adapter it rides, or to the host it is sent to, has waited
longer than that interval, its own included, the request is dropped, which
closes its connection and gives its place back, and the read is refused:
<url> request abandoned unanswered: this host's resolver holds <N> connection(s) on that adapter unanswered longer than the <N>s refresh interval it declares, … for an adapter, <host> request abandoned unanswered: <the held reading> for a host, with the exit
code of a store that does not answer. The authority's snapshot over SSH
stands in no list of this host's — the SSH connection opens in a second and
the remote command answers nothing — so a snapshot read that outlasts the
interval with nothing published held is abandoned too: <host> request abandoned unanswered: it stood longer than the <N>s refresh interval this host's resolver declares; the host's own stado resolver snapshotis what answered nothing:stado host exec lists what every Stado process there waits on, andstado service logs com.wisent.stado
--host says what its unit is doing, and the reader goes on to its store or its
last-known-good copy, announcing which. When the host runs a Stado older than
the release that declared stado waits (or any approved Stado verb), stado host exec says so instead of ending on the usage error: the Stado installed on <host> does not take : it exited with the usage status, so the release it runs is older than this Stado <version>, which declares the command; stado release statusshows the release each host was asked to run and the one it runs; exited <code>; its last line was: <line>.
The journey
tests/host_silence/silent_authority/main.rs runs it against a real OpenSSH
server on a loopback port that runs the real stado as the authority: it
answers one read, is stopped with SIGSTOP and then accepts every connection
and sends nothing, as a hung host does. stado resolver status therefore ends with the address it stood on instead of standing for
hours on the registry read of the resolver it diagnoses. A client reaching a
route without a resolver adapter, or on a host that declares no resolver,
has no such reading and waits as before. No other bound exists: the one
measure is the resolver's own refresh interval.
The authority line of stado resolver status says how long the authority
took to answer: authority <target> source=ssh reachable generation=<N> answered_after=<seconds>s (--json: authority.answered_after_seconds,
null for the local authority, whose document is in hand). An authority
that answers only after longer than the refresh interval the target
declares is a blocker, the registry authority <target> answered over SSH only after <seconds>s, longer than the <interval>s refresh interval this target declares: that wait is the cause
of the stale snapshot and of every relay held to that host, so the verdict
is degraded and the line names it instead of reporting the authority as
reachable alone.
What the authority's snapshot answers from
stado resolver snapshot on the registry authority does not read the
registry store. The authority's store is its object API, which authorizes
each read through Skarbiec, so a Skarbiec that stopped answering left the
snapshot, and every registry read of every host behind it, standing. The
command asks the authority's running resolver for the generation it holds in
memory, at the API address that resolver publishes in its state file
(api_bind in ~/.stado/resolver-state.json), in one registered wait on
that loopback address (stado waits lists it while it lasts). The resolver
reads the store itself on its declared refresh interval and keeps answering
the generation it last read while a refresh fails. The command prints the same
{"store_version", "document"} every reader already reads, and is refused at
once, so the caller goes on to its own last-known-good copy, when:
- no resolver has published its state on this host, or the process that published it is not running;
- the running resolver publishes no API address (a resolver older than this behaviour);
- this host is not the registry authority (
<host> is not the registry authority; its resolver holds a copy read from <authority>); - the held generation is older than the declared max-stale (
the registry generation <N> this resolver holds was loaded at <time> (<seconds> s ago), past the declared max-stale of <seconds> s; every refresh since failed), andstado resolver statuson that host names the failed refresh.
Source: this website