blackbull.asgi¶
blackbull.asgi
¶
ASGI protocol types: event-type string constants, typed message shapes, and typed event wrappers.
Three responsibilities, all framework-side:
ASGIEvent: namespace of ASGI 3.0 event-type strings, used formatch/casedispatch and equality checks across both the framework and (importing from here) the server stack. Every constant isFinal, so a type checker infers aLiteraland comparisons against them narrow the event unions below.- The 19
TypedDictmessage shapes and the two direction unions (ASGIReceiveEvent/ASGISendEvent) plus the two channel callable aliases (ASGIReceiveCallable/ASGISendCallable). These are declarations only — erased at runtime, no wire or dispatch change. ResponseStart/ResponseBody: dict-subclass wrappers for the two outgoing response event shapes so middleware can dispatch on Python type rather than string comparison. Both subclassdictsoisinstance(e, dict)remains True — required for beartype and any ASGI send callable annotatedevent: dict.
Naming rule: an ASGI prefix marks boundary vocabulary and is
quarantined to this module; unprefixed names (Connection, Headers,
Request, Response) are BlackBull's native layer. The dicts on the
channel are ASGI 3.0 events verbatim — the spec is free documentation for
every key — so rg "from .asgi import" stays a literal map of the
remaining ASGI surface.
ASGIEvent
¶
Namespace for ASGI protocol event type strings (ASGI 3.0 spec).
HTTPDisconnectEvent
¶
Bases: TypedDict
Client went away before the response completed.
HTTPRequestEvent
¶
Bases: TypedDict
Incoming request body chunk.
HTTPResponseBodyEvent
¶
Bases: TypedDict
Response body chunk; more_body keeps the response open.
HTTPResponsePathsendEvent
¶
Bases: TypedDict
Hand a file path to the server to send (ASGI extension).
HTTPResponsePushEvent
¶
Bases: TypedDict
HTTP/2 server push (ASGI extension, not baseline ASGI 3.0).
HTTPResponseStartEvent
¶
Bases: TypedDict
Response status line + headers.
HTTPResponseTrailersEvent
¶
Bases: TypedDict
Trailing headers, sent after the final body chunk.
LifespanShutdownCompleteEvent
¶
Bases: TypedDict
Shutdown hooks finished successfully.
LifespanShutdownEvent
¶
Bases: TypedDict
Server is stopping; run shutdown hooks.
LifespanShutdownFailedEvent
¶
Bases: TypedDict
Shutdown hooks raised; message carries the reason.
LifespanStartupCompleteEvent
¶
Bases: TypedDict
Startup hooks finished successfully.
LifespanStartupEvent
¶
Bases: TypedDict
Server is starting; run startup hooks.
LifespanStartupFailedEvent
¶
Bases: TypedDict
Startup hooks raised; message carries the reason.
ResponseBody
¶
Bases: dict
http.response.body event with typed property access.
ResponseStart
¶
Bases: dict
http.response.start event with typed property access.
WebSocketAcceptEvent
¶
Bases: TypedDict
Complete the handshake.
WebSocketCloseEvent
¶
Bases: TypedDict
Close the connection (app-initiated).
WebSocketConnectEvent
¶
Bases: TypedDict
Handshake offered; the app answers with accept or close.
WebSocketDisconnectEvent
¶
Bases: TypedDict
Connection closed (peer- or transport-initiated).
WebSocketReceiveEvent
¶
Bases: TypedDict
One complete message from the client.
BlackBull's recipient always sets both keys, one of them None
(FragmentAssembler has already reassembled any fragments), so the
value types are optional rather than the keys being mutually exclusive.
WebSocketSendEvent
¶
Bases: TypedDict
One complete message to the client.
parse_response_event(event)
¶
Wrap event in the appropriate typed subclass for dispatch.
The returned object IS the event dict (shallow copy) — pass it directly to downstream send callables without re-serialisation. Trailers and unknown event types are returned unchanged.
ResponseStart/ResponseBody are dict subclasses, not statically
members of ASGISendEvent; a caller threading the result back into a
typed send callable casts at that seam (a runtime no-op) rather than
widening the public union.