The server end of one runner daemon's socket.
A WebSock handler: it registers itself with the Managoat.Runner.Host
under the runner's id, turns call/3 requests from anywhere the host can
route from into JSON frames, matches the daemon's replies back to the
callers, and forwards the daemon's unsolicited stream frames to the owner
of the command they belong to as the standard Managoat.Sandbox owner
messages.
The init map the host application hands WebSockAdapter.upgrade/4:
%{runner_id: "…", name: "mini", meta: %{...}, host: MyApp.RunnerHost}runner_id is required. name is the runner's display name, used in log
lines and in the 4409 close reason. meta (default %{}) is opaque and is
handed to the host on register/2 and presence/3. host overrides the
configured Managoat.Runner.Host for this connection; see
Managoat.Runner.Config.
Wire protocol
Text frames, JSON objects. Platform → daemon, one request per id:
{"id": 7, "op": "spawn", "name": "runner-…", "cmd": "…", "args": [...], ...}Daemon → platform, one reply per request plus unsolicited stream frames:
{"id": 7, "ok": true, "result": {...}}
{"id": 7, "ok": false, "error": "not_found", "detail": "…"}
{"stream": "stdout" | "stderr", "session_id": "s-…", "data": "<base64>"}
{"stream": "exit", "session_id": "s-…", "code": 0}
{"stream": "stdout", "session_id": "s-…", "data": "…", "replay_for": 7}A spawn/attach request names the owner and ref its session's frames
should reach; the subscription is installed before the reply is delivered
so no frame can slip past it. The daemon sends the reply first, then replays
the session's journal from byte zero tagged replay_for with that request's
id — those frames reach only the subscriber that request installed, so a
second attacher's replay never duplicates output at the first owner — and
then streams live frames, which reach every subscriber of the session.
Failure
When the socket closes, every caller still waiting gets
{:error, {:unavailable, :runner_disconnected}} and every subscribed owner
gets {:error, %{ref: ref}, :runner_disconnected} — a transport failure in
the contract's terms, after which no :exit follows. Detached sessions on
the daemon keep running; that is what reattach is for.
Summary
Functions
Send a request to the runner and wait for its reply. The connection
process is found through the configured host's whereis/1.
Stop forwarding a session's frames to ref's owner (this end only).
Functions
Send a request to the runner and wait for its reply. The connection
process is found through the configured host's whereis/1.
Options: :timeout (ms or :infinity, default 30000);
:subscribe — {owner_pid, ref} for spawn/attach, installed on the
session id the reply names before the reply is returned.
Returns {:ok, result} / {:error, reason} with the daemon's error string
already normalized into the sandbox error taxonomy, or
{:error, {:unavailable, :runner_offline | :runner_disconnected | :runner_timeout}}.
Stop forwarding a session's frames to ref's owner (this end only).