@sproutboat/runtime 0.32.0 → 0.34.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +24 -0
- package/package.json +1 -1
- package/src/native-fetch-prelude.js +902 -2
- package/src/source.ts +12 -2
- package/src/transport-embedded.js +639 -0
- package/test/native-websockets-outbound.ts +244 -0
- package/test/native-websockets.ts +261 -0
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,29 @@
|
|
|
1
1
|
# @sproutboat/runtime
|
|
2
2
|
|
|
3
|
+
## 0.34.0
|
|
4
|
+
|
|
5
|
+
### Minor Changes
|
|
6
|
+
|
|
7
|
+
- 85ec3fe: WebSockets on every host, and outbound WebSockets, from compatibility date `2026-11-01`:
|
|
8
|
+
|
|
9
|
+
- **Client sockets on standalone and platform sprouts.** The native server (toolchain) carries the client end of a 101 response: it upgrades the connection, passes text and binary messages both ways, applies the 1 MiB read window, caps messages at 32 MiB (1009), and answers a close with the code and reason. A message the app sent before the 101 goes out right after it, and the app's `Sec-WebSocket-Protocol` is the one the client gets. Before 2026-11-01 these sprouts still answer a 101 with 501 (sproutd, which sets `sb_ws_hook` itself, carries them from 2026-10-30). The toolchain needs `@sproutboat/runtime` 0.33 or later.
|
|
10
|
+
- **Outbound WebSockets.** `new WebSocket(url, protocols)` (CONNECTING, then `open`, as in a browser) and `fetch(url, { headers: { Upgrade: "websocket" } })`, whose Response carries the connected socket as `response.webSocket` (call `accept()`); a server that answers the upgrade with another status is the Response. `ws`, `wss`, `http` and `https` URLs. Returning that Response from a handler relays the client's socket to the upstream. One I/O thread per socket (up to 64) connects through the egress policy, does TLS with BearSSL, and wakes the loop through the async pipe (sproutd) or the server's waker (standalone). On the embedded transport (standalone, sproutd); the broker transport (platform, `sproutboat dev`) answers `fetch` upgrades with a rejection for now.
|
|
11
|
+
- `validateHttpSyncSource(source, compatibilityDate)` accepts `WebSocket(` from 2026-11-01 and keeps refusing it before.
|
|
12
|
+
- **Hibernation, on a host that keeps client sockets open while the worker is gone (sproutd).** A Durable Object's hibernatable socket (`ctx.acceptWebSocket`) is recorded in storage scoped to the object (its id, tags, attachment, and the object's auto-response, kept current by `serializeAttachment` and `setWebSocketAutoResponse`), so the host may stop the worker while the socket is idle. When a message or close arrives, a new worker constructs the object again with `ctx.getWebSockets()` listing its sockets (tags and attachments intact) from the start of the constructor, and the event runs as `webSocketMessage` or `webSocketClose`. Socket ids are random. A host without this (standalone, platform) keeps every socket resident, as before.
|
|
13
|
+
|
|
14
|
+
## 0.33.0
|
|
15
|
+
|
|
16
|
+
### Minor Changes
|
|
17
|
+
|
|
18
|
+
- 90434e0: WebSockets, from compatibility date `2026-10-30`, as in workerd:
|
|
19
|
+
|
|
20
|
+
- **`WebSocketPair` and `WebSocket`.** `accept()`, `send()` (text, `ArrayBuffer` or a typed array), `close(code, reason)`, `readyState`, `binaryType` (binary messages are `Blob`s unless it is `"arraybuffer"`, workerd's standard binary type), `addEventListener` and `on<type>`. Messages sent before the other end accepts wait for it; each message is delivered in its own turn, so a reply reaches the other end before the next message, as in workerd. A close is answered automatically; invalid close codes throw `InvalidAccessError`, reasons over 123 bytes `SyntaxError`. Checked against workerd 1.20260730 (`test/native-websockets.ts`).
|
|
21
|
+
- **`new Response(null, { status: 101, webSocket })`** and `response.webSocket` (`null` when there is none). Any other status with a `webSocket` throws `RangeError`, as in workerd.
|
|
22
|
+
- **Durable Objects: the hibernation API.** `ctx.acceptWebSocket(ws, tags)`, `getWebSockets(tag)`, `getTags(ws)`, `setWebSocketAutoResponse` / `getWebSocketAutoResponse` with `WebSocketRequestResponsePair`, `serializeAttachment` / `deserializeAttachment`, and the `webSocketMessage` / `webSocketClose` handlers, run through the object's input gate.
|
|
23
|
+
- **Client sockets.** The client end of a 101 response becomes a real socket on a host that carries it (sproutd, which sets the runtime's `sb_ws_hook`). A standalone or platform sprout answers such a response with `501` for now; a pair whose ends both stay in the worker (a Worker and its Durable Object) works everywhere.
|
|
24
|
+
|
|
25
|
+
Before `2026-10-30` nothing is defined and `response.webSocket` stays `undefined`.
|
|
26
|
+
|
|
3
27
|
## 0.32.0
|
|
4
28
|
|
|
5
29
|
### Minor Changes
|