statewire
The Statewire protocol for Python, on top of pinned.
Statewire is a PinnedAPI (one live instance per id cluster-wide) that replicates
one JSON object — any State — over packet streams:
POST /stream(SSE) — the body is the first client frame ({"headers", "ctx"?, "cmd"?}), the response the packet stream. Every packet is an envelope{"ops"?, "cmd"?, "syn"?, "idle"?, "fin"?}. The first packet is a full snapshot (ops: [{"op": "replace", "path": [], "value": <state>}]) with the hellosyn{"seq", "ctxSeq", "idle"?}: the client's admitted watermark per lane. Each attach's lease rides theStatewire-Leaseresponse header.GET /streamis the degenerate empty-frame attach and/wsthe WebSocket twin (frames ride the socket). A client id may hold any number of concurrent attaches: each gets its own hello and lease, and cmd answers anddurreceipts fan out to every live attach of the id.POST /frames— submits follow-up frames{"headers"?, "ctx"?, "cmd"?}underStatewire-Client-Idand a live attach'sStatewire-Lease. Each cmd statement is a method call{"method": <name>, "params": [...], "seq": <int>}routed to the@commandhandler registered under that name; the ctx lane replaces the client's context object. The HTTP response is receipt only:200 {}admitted whole,409seq gap and429backpressure answer the{"syn": ...}refusal body (the 429 also carriesRetry-After),423dead lease (its attach is gone — re-attach and resend),400malformed (the stream also finserror). Verdicts ride the stream. Over WS the same frames ride the socket — no lease header, holding the connection is the lease.
ops are Immer-style deltas with array paths (object keys as strings, list
indices as ints): replace sets a value, add splices — its final int segment
indexes into the parent, so a list parent gains an element and a string parent
gains text at that offset — remove deletes. cmd carries the issuing
client's verdicts as an array of {"seq", "type": "result" | "applied" | "rejected" | "failed" | "crashed" | "expired", "code"?, "message"?, "payload"?} entries plus {"seq", "dur": true} durability markers; effect
ops precede the verdict, and applied states the broadcast state now
contains the command's effects while the result is still in flight. fin
({"reason": "evicted" | "error" | "gone" | "idle", "message"?}) is always the last packet.
Handler outcomes: the return value becomes the terminal result payload;
raise StatewireReject becomes rejected; any other raise becomes failed;
an involuntary death (cancellation at shutdown or eviction) becomes crashed.
ctx.applied() flushes the applied entry riding the ops packet that carries
the handler's effects so far; the terminal entry follows on a later flush.
Duplicate seqs never re-run: a replayed statement re-emits its stored verdict
on the stream (expired once the outcome outlived retention).
The protocol is generic: it says nothing about messages, queues, or agents — it
only replicates whatever self.state dict you assign and dispatches whatever
commands you declare. Domain-specific layers (see the harness-sdk package) sit
on top.
from statewire import Statewire, command
class Thread(Statewire):
async def lifespan(self):
self.state = {"messages": []} # yielding without setting self.state throws
yield
@command
async def addMessage(self, message_id: str, content: str):
self.state["messages"].append({"id": message_id, "content": content})
self.create_task(self.run()) # long work outside the inbox; returning here => applied
@command registers the handler under the method's own name; @command("name")
registers it under an explicit wire name. Params are positional. An unknown
method or a params/signature mismatch is a rejected verdict on the stream,
not an HTTP error; the seq is consumed.
self.state is a change-tracking proxy: mutate it plainly and the ops replicate
to every attached stream. += on a string becomes an end-offset text-insert
add op of the suffix; other mutations become narrow replace / add /
remove ops. Mutations within
one synchronous segment coalesce into a single envelope.
Extra routes
Need an endpoint beyond the protocol trio (a health check, a file upload)?
Decorate a method with pinned's route escape hatch:
from pinned import route
from statewire import Statewire
class Thread(Statewire):
@route.get("/health")
async def health(self, request):
return {"ok": True}
The reserved protocol paths /stream, /frames, and /ws are Statewire's
own; a subclass that decorates a @route onto any of them raises at
class-definition time rather than silently shadowing the protocol.
Layering
pinned one live instance per id, with an HTTP surface
└─ statewire the Statewire protocol: /stream + /ws (packets) + /frames
└─ harness-sdk HarnessState types, queueing, deepagents
Develop
uv sync
uv run pytest
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file statewire-0.12.4.tar.gz.
File metadata
- Download URL: statewire-0.12.4.tar.gz
- Upload date:
- Size: 82.4 kB
- Tags: Source
- Uploaded using Trusted Publishing? Yes
- Uploaded via:
twine/7.0.0 CPython/3.13.14
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
b872e4e680ec7e94af95e7aa4fceccf41c1168d9053006339d1618e9db5d27a5
|
|
| MD5 |
ddb09daee174b0d5252eb1782ad526d9
|
|
| BLAKE2b-256 |
aab6ffb287f1f254694b4559f0a77654b4bbcaa71f70d8fb71942ecaeddfd81c
|
Provenance
The following attestation bundles were made for statewire-0.12.4.tar.gz:
Publisher:
pypi-publish.yaml on assistant-ui/harness-sdk
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
statewire-0.12.4.tar.gz -
Subject digest:
b872e4e680ec7e94af95e7aa4fceccf41c1168d9053006339d1618e9db5d27a5 - Sigstore transparency entry: 2596653673
- Sigstore integration time:
-
Permalink:
assistant-ui/harness-sdk@60ad65576aff39e2838747c6a5050dd87675413c -
Branch / Tag:
refs/heads/main - Owner: https://github.com/assistant-ui
-
Access:
private
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
pypi-publish.yaml@60ad65576aff39e2838747c6a5050dd87675413c -
Trigger Event:
workflow_dispatch
-
Statement type:
File details
Details for the file statewire-0.12.4-py3-none-any.whl.
File metadata
- Download URL: statewire-0.12.4-py3-none-any.whl
- Upload date:
- Size: 44.7 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? Yes
- Uploaded via:
twine/7.0.0 CPython/3.13.14
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
e60badabcb651fcbf6aedc0744c4c16df797e295572a334707a5c20f6ed758ba
|
|
| MD5 |
a2320f031753fefd264db91b643bba7e
|
|
| BLAKE2b-256 |
e3449ab4e3fc1d7dd36e663626876671c57cfc6cbb56e4a33e1d7023992868e9
|
Provenance
The following attestation bundles were made for statewire-0.12.4-py3-none-any.whl:
Publisher:
pypi-publish.yaml on assistant-ui/harness-sdk
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
statewire-0.12.4-py3-none-any.whl -
Subject digest:
e60badabcb651fcbf6aedc0744c4c16df797e295572a334707a5c20f6ed758ba - Sigstore transparency entry: 2596653697
- Sigstore integration time:
-
Permalink:
assistant-ui/harness-sdk@60ad65576aff39e2838747c6a5050dd87675413c -
Branch / Tag:
refs/heads/main - Owner: https://github.com/assistant-ui
-
Access:
private
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
pypi-publish.yaml@60ad65576aff39e2838747c6a5050dd87675413c -
Trigger Event:
workflow_dispatch
-
Statement type: