Networking
Networking
import std::sockets;Covers TCP, HTTP and HTTPS, server-sent events, file downloads, WebSocket clients, and TCP, HTTP, and WebSocket servers.
Making a request
Request is a builder, and each method returns it so calls chain:
let response: sockets::HttpResponse? = new sockets::Request()
.method("POST")
.path("/api/thing")
.header("Content-Type", "application/json")
.body(payload)
.send_http(host, 443)
if !response.is_value() {
return None
}
let body: string = response.unwrap().body()send_http returns a parsed HttpResponse with status_code(), body(), and
header_value(name). send returns a plain Response. Both give None on a
transport failure. The default port is 443 with TLS and 80 without.
A Request with no method is sent as a raw TCP payload; with a method it is
serialized as HTTP/1.1 with Host, Content-Length, Connection: close, and a
user agent filled in.
Streaming
stream and stream_sse take callbacks for the headers and each chunk or
event, returning false from either to stop. open_stream gives a
RequestWriter for a request body written incrementally; a writer dropped
without finish() or abort() leaks its socket.
WebSocket client
let connected: sockets::WsClient? = sockets::ws_connect(url)
if connected.is_value() {
let client: sockets::WsClient = connected.unwrap()
client.send(`{"t":"hello"}`)
let incoming: string? = client.recv()
client.close()
}recv() blocks until a message arrives or the connection closes, returning
None for the latter.
Servers
Socket handles raw TCP, HttpSocket adds exact-URI routing, and WebSocket
serves WebSocket connections.
let server: sockets::WebSocket = new sockets::WebSocket()
server.set_callback(closure(connection: sockets::WsConnection,
request: sockets::Request) => void {
connection.send("ack")
})
server.listen()listen() runs on a new thread; listen_attached() blocks the caller. A port of
zero binds an ephemeral one, readable with get_port() afterwards. stop() sets
a flag, so the loop exits on its next pass rather than immediately.
Two things to be explicit about
The TLS layer encrypts but does not authenticate the server. There is no certificate verification. Treat it as protection against passive observation, not against an active attacker.
Three functions signal failure with a magic string. send_request,
send_request_tls, and send_raw return a string that begins with Error:
when the exchange failed. The Request methods wrap this and return optionals,
which is the better surface.