Aude Code

aude-wire(7)

NAME

aude-wire — aude 的远程控制协议

DESCRIPTION

sdk/conformance/ 定义该协议。

TRANSPORT

链路是到机器监听器的 WebSocket,方式为:到 127.0.0.1 的 TCP、到隧道名称 443 端口的 TLS,或 ~/.aude/rc/listener.socket。 ‘Origin’ 标头得到 403。每条二进制消息都是一条最多 65535 字节的 Noise 消息。握手 ‘Noise_XX_25519_ChaChaPoly_SHA256’ 有 ‘aude-wire’ 序言和空载荷。客户端期望拨号所用的指纹,在 listener.socket 上则期望机器的指纹。

指纹是标准形式的 X25519 公钥的 SHA-256,截断为 28 个 base32 字符。

FRAMING

帧是一行中的一个严格 UTF-8 JSON 对象:

‘type’
 
‘id’
小写的 UUID v4 或提交项的 ID,由 1 到 64 个 ‘[A-Za-z0-9-]’ 字符组成
‘timestamp’
发送方的 RFC 3339 时间,形如 ‘2026-01-01T12:00:00.000Z’
‘reply_to’
在应答中,为所应答帧的 ‘id’
‘body’
该类型的字段(如果有)

有多个种类的对象只有一个字段,该字段以种类命名。保留未知的种类或词。忽略未知的字段或类型。

HANDSHAKE

链路的第一帧是 ‘hello’ 帧。它的字段为链路命名:

‘machine’
每个会话: ‘name’ 字段和可选的配对码 ‘code’
‘session’
一个会话: ‘name’、‘session’ ID,以及带有客户端最后一个 ‘sequence’ 或 0 的 ‘since’
‘host’
aude 自用,用于宿主: ‘session’ 字段,以及 ‘replaces’ 字段中它所替换的 ID
‘home’
aude 自用,为空,用于 aude pair、revoke 和 tunnel

‘welcome’ 帧以相同的字段应答:

‘machine’
‘backlog_count’ 字段,即随后的 ‘machine’ 帧的数量
‘session’
‘record’ 字段,即最后一个条目处的记录, ‘backlog_count’ 字段,即随后发送的 ‘since’ 之后的实录 ‘entry’ 帧的数量,以及客户端提交项所带的 ‘origin’
‘host’、‘home’
监听器的 ‘aude_version’

‘origin’ 含有 ‘connection’ ID 和 ‘name’ 名称。

FRAMES

类型 发送方 内容
hello 打开方 见 HANDSHAKE
welcome 监听器 见 HANDSHAKE
entry 监听器 一个条目,见 ENTRIES
presence 监听器 ‘attached’ 或 ‘detached’ 字段,其值为一个 ‘origin’
machine 监听器 ‘record’ 字段,即新出现或已改变的记录,或 ‘removed’ 字段,即一个 ID
submission 客户端、监听器 ‘text’ 字段,即一个轮次的文本行,可选的 ‘budget’ 字段(以秒为单位),以及发给宿主时的 ‘origin’
interrupt 客户端、监听器 无,发给宿主时为 ‘origin’
request 客户端 见 REQUESTS
response 监听器、宿主 见 REQUESTS
head 宿主 无,在日志增长之后
ping, pong 双方 无,但 ‘pong’ 有 ‘reply_to’
failure 监听器 见 PROTOCOL FAILURES

ENTRIES

条目有 ‘sequence’、‘timestamp’ 和 ‘kind’ 字段。实录条目就是 aude(1) 的 JSON 条目。其他每个种类都把它的字段放在它的名称之下:

‘settings’
‘conversation’、‘model’、‘alias’、‘effort’、‘agent’、‘context_tokens’、‘branch’ 和 ‘choices’
‘status’
宿主的 ‘queue’、‘last’ 和 ‘phase’ 字段,后者为 ‘starting’、‘held’、‘idle’、‘exiting’ 或 ‘busy’ 之一,而 ‘busy’ 带有 ‘submissions’ 和 ‘deadline’
‘gate’
见 GATE
‘settled’
‘submission’、‘origin’ 和 ‘fate’ 字段,后者为 ‘answered’、‘dropped’ 或 ‘ran’
‘ended’
‘stopped’、‘refused’、‘instructions_file’、‘died’ 或 ‘unknown_model’
‘began’
宿主的 ‘identity’、‘lifetime’ 和 ‘subagent’
‘merged’
无

记录的 ‘work.state’ 说明的是工作。每个 ‘settings’ 或 ‘status’ 条目都替换上一个。只有 ‘settled’ 条目的 ‘origin’ 所属的客户端会显示它。 ‘ended’ 是 ‘session’ 链路的最后一帧。

GATE

‘gate’ 不含任何凭据。它有 ‘harness’ 和 ‘finding’ 字段,后者为 ‘ok’、‘not_logged_in’、‘other_provider’、‘timed_out’、‘not_found’、‘silent’、‘unreadable’、‘spawn’ 或 ‘unreported’ 之一。 ‘silent’ 带有 ‘exit’,‘spawn’ 带有 ‘detail’。

REQUESTS

请求 链路 内容
start machine ‘name’、‘harness’、‘text’、‘budget’、‘working_directory’ 和 ‘prerequisites’ 字段,以及可选的 ‘model’、‘effort’ 和 ‘agent’
remove machine 一个会话 ID
pair home 无
revoke home ‘device’ 字段,其值为一个指纹,或者 ‘all’
tunnel home 可选的 ‘tunnel’ 字段,其值为 aude-tunnel(7) 中的一个词

‘response’ 帧应答其 ‘reply_to’ 所指的帧,内容为下列之一:

‘taken’
 
‘started’、‘continued’
记录
‘window’
‘expires’ 和 ‘url’ 字段,后者有 ‘endpoint’ 和 ‘code’
‘paired’
‘name’ 和 ‘fingerprint’
‘reach’
用于 ‘tunnel’ 请求
‘refused’、‘failed’
wire.schema.json 中的一种情形

‘pair’ 请求先得到 ‘window’ 响应,然后得到 ‘paired’ 响应,或者得到 ‘refused’ 或 ‘failed’ 响应。每个提交项和中断都得到 ‘taken’、‘refused’ 或 ‘failed’ 响应。

PROTOCOL FAILURES

‘failure’ 帧有 ‘code’、‘detail’ 和 ‘is_fatal’ 字段。致命的失败会关闭链路。

代码 致命 条件
bad_json 否 错误的行、重复的字段、未知的类型或请求、不属于该链路的帧、第二个 ‘hello’ 帧,或错误的 ID
line_too_long 是 超过 8 MiB 的行
unauthorised 是 被拒绝或被撤销的设备、未知的链路,或没有 ‘hello’ 帧
busy 是 会话的第二个宿主
not_found 是 机器未持有的会话
internal 是 无法写入 peers.json,或它已改变
retired 是 已退役的名称

ADMISSION

收到 ‘hello’ 帧时,监听器使用第一条匹配的规则:

  1. 在 listener.socket 上,它只接受机器的密钥。
  2. 在端口上,它拒绝机器的密钥。
  3. 对于指纹在 peers.json 中的密钥,它只在 ‘machine’ 或 ‘session’ 链路上接受。
  4. 其他密钥在 ‘machine’ 链路上带有打开的配对窗口的配对码时,它配对并接受该密钥。
  5. 对于错误或过期的配对码,它以 ‘pairing code rejected’ 拒绝。
  6. 它拒绝没有配对码的密钥。

拒绝是致命的 ‘unauthorised’ 失败。它的 ‘detail’ 是规则给出的值,或者是 ‘this machine does not list this device’ 这一值。

LIMITS

‘hello’ 帧必须在 30 秒和 16 KiB 之内到达。没有 ‘hello’ 帧的端口链路超过 8 条时,最早的一条会关闭。静默 15 秒的链路会收到 ‘ping’ 帧,30 秒内没有收到 ‘pong’ 帧时,链路会关闭。名称会被清理,并截断为 48 个标量值。 wire.schema.json 给出每个文本和数组的最大长度。队列中已有 8 个提交项时,新的提交项会得到带有 ‘queue_full’ 的 ‘dropped’ 结果。积压内容按链路读取的速度发送。

EXAMPLES

第一个 ‘hello’ 帧:

{"body":{"machine":{"code":"<code>","name":"my phone"}},
"id":"<uuid>","timestamp":"<time>","type":"hello"}

一个 ‘submission’ 帧及其 ‘entry’ 帧:

{"body":{"budget":300,"text":"hi"},"id":"<id>","timestamp":"<time>",
"type":"submission"}
{"body":{"kind":"user","origin":{"connection":"<id>","name":"my phone"},
"sequence":7,"text":"hi","timestamp":"<time>"},"id":"<uuid>",
"timestamp":"<time>","type":"entry"}

SEE ALSO

aude(1), aude-rc(7)