blackbull.client.websocket¶
blackbull.client.websocket
¶
WebSocket client (RFC 6455).
Two pieces:
WebSocketClientopens a TCP/TLS connection and drives the HTTP/1.1Upgrade: websockethandshake.WebSocketSession, returned byWebSocketClient.connect, owns the post-handshake frame loop:send_text/send_bytes/receive/ping/close.
Reuses HTTP1RequestSender / HTTP1ResponseRecipient for the handshake
and encode_frame(mask=True) / WebSocketRecipient(require_masked=False)
for post-handshake frames — the same codec serves both directions,
parameterised by the mask flag.
WebSocketClient
¶
Async WebSocket client.
Use as an async context manager::
async with WebSocketClient('localhost', 8000) as c:
ws = await c.connect('/path', subprotocols=[b'chat'])
await ws.send_text('hello')
msg = await ws.receive()
await ws.close()
The transport is held open between connect() and __aexit__;
only one concurrent session per WebSocketClient is supported.
connect(path, *, subprotocols=())
async
¶
Run the HTTP/1.1 Upgrade: websocket handshake on this connection.
Returns a WebSocketSession once the server has confirmed the
upgrade with HTTP 101 and a valid Sec-WebSocket-Accept header.
Raises HandshakeError on any handshake-time failure.
WebSocketSession
¶
Frame-level WebSocket session over an established connection.
Always masks outgoing frames (RFC 6455 §5.1). Reads use
WebSocketRecipient(require_masked=False) because servers MUST NOT
mask their outgoing frames.
receive()
async
¶
Read one ASGI websocket.* event from the connection.
Returns one of
{'type': 'websocket.receive', 'text': str, 'bytes': None}{'type': 'websocket.receive', 'text': None, 'bytes': bytes}{'type': 'websocket.disconnect', 'code': int}
Server-initiated PING frames are auto-PONGed by the underlying
WebSocketRecipient (with masking, since this session is the
client). Server PONG frames are silently dropped.