Problem
Pekko HTTP supports HTTP/2 and WebSockets, but WebSocket support currently appears to be limited to the classic HTTP/1.1 upgrade handshake.
RFC 8441 defines how to bootstrap WebSockets over HTTP/2 using Extended CONNECT:
- server advertises
SETTINGS_ENABLE_CONNECT_PROTOCOL = 1
- client sends
:method = CONNECT
- client sends
:protocol = websocket
- request also includes
:scheme, :path, and :authority
- server accepts with
:status = 200
- WebSocket frames are then carried over the HTTP/2 stream
This would allow applications to serve HTTP/2 requests and WebSockets on the same HTTP/2 connection instead of falling back to a separate HTTP/1.1 WebSocket upgrade connection.
RFC: https://www.rfc-editor.org/rfc/rfc8441.html
Current Behavior
Pekko HTTP WebSocket handling is based on the HTTP/1.1 upgrade model:
- request validation expects
Upgrade: websocket, Connection: Upgrade, Sec-WebSocket-Key, and Sec-WebSocket-Version
- accepted WebSockets return
101 Switching Protocols
- the existing
WebSocketUpgrade API represents upgrading the connection to WebSocket
That matches RFC 6455 over HTTP/1.1, but not RFC 8441 over HTTP/2.
Expected Behavior
When HTTP/2 is enabled, Pekko HTTP should optionally support RFC 8441 WebSockets over HTTP/2.
At a high level this likely means:
- advertise
SETTINGS_ENABLE_CONNECT_PROTOCOL = 1 when server-side support is enabled
- accept HTTP/2 Extended CONNECT requests with
:protocol = websocket
- expose those requests to routing / low-level APIs similarly to existing WebSocket upgrade requests
- allow existing
handleWebSocketMessages / WebSocketUpgrade style APIs to work where practical
- respond with HTTP/2
:status = 200 when the WebSocket is accepted
- connect the existing WebSocket frame/message stack to the HTTP/2 stream DATA flow
- map HTTP/2 stream end/reset/failure semantics sensibly to WebSocket close behavior
Motivation
Modern browsers support WebSockets over HTTP/2 via RFC 8441. Supporting this in Pekko HTTP would allow one server port and one HTTP/2 connection to handle both normal HTTP traffic and WebSockets.
This is useful for frameworks built on Pekko HTTP as well. For example, Play Framework can enable HTTP/2 on its Pekko HTTP backend, but WebSocket support still depends on the HTTP/1.1 upgrade path because Pekko HTTP does not currently expose RFC 8441 WebSocket support.
Notes
Netty has already added several low-level RFC 8441 building blocks, but still tracks high-level WebSocket-over-HTTP/2 support as an open feature request:
A third-party Netty implementation also exists:
Questions
- Would the Pekko HTTP project be open to RFC 8441 server-side support?
- Should this be implemented behind an explicit config flag, for example under
pekko.http.server.websocket or pekko.http.server.http2?
- Should the existing
WebSocketUpgrade API be reused for HTTP/2 Extended CONNECT, or should there be a separate API to distinguish HTTP/1.1 upgrade from HTTP/2 stream-based WebSocket bootstrap?
Problem
Pekko HTTP supports HTTP/2 and WebSockets, but WebSocket support currently appears to be limited to the classic HTTP/1.1 upgrade handshake.
RFC 8441 defines how to bootstrap WebSockets over HTTP/2 using Extended CONNECT:
SETTINGS_ENABLE_CONNECT_PROTOCOL = 1:method = CONNECT:protocol = websocket:scheme,:path, and:authority:status = 200This would allow applications to serve HTTP/2 requests and WebSockets on the same HTTP/2 connection instead of falling back to a separate HTTP/1.1 WebSocket upgrade connection.
RFC: https://www.rfc-editor.org/rfc/rfc8441.html
Current Behavior
Pekko HTTP WebSocket handling is based on the HTTP/1.1 upgrade model:
Upgrade: websocket,Connection: Upgrade,Sec-WebSocket-Key, andSec-WebSocket-Version101 Switching ProtocolsWebSocketUpgradeAPI represents upgrading the connection to WebSocketThat matches RFC 6455 over HTTP/1.1, but not RFC 8441 over HTTP/2.
Expected Behavior
When HTTP/2 is enabled, Pekko HTTP should optionally support RFC 8441 WebSockets over HTTP/2.
At a high level this likely means:
SETTINGS_ENABLE_CONNECT_PROTOCOL = 1when server-side support is enabled:protocol = websockethandleWebSocketMessages/WebSocketUpgradestyle APIs to work where practical:status = 200when the WebSocket is acceptedMotivation
Modern browsers support WebSockets over HTTP/2 via RFC 8441. Supporting this in Pekko HTTP would allow one server port and one HTTP/2 connection to handle both normal HTTP traffic and WebSockets.
This is useful for frameworks built on Pekko HTTP as well. For example, Play Framework can enable HTTP/2 on its Pekko HTTP backend, but WebSocket support still depends on the HTTP/1.1 upgrade path because Pekko HTTP does not currently expose RFC 8441 WebSocket support.
Notes
Netty has already added several low-level RFC 8441 building blocks, but still tracks high-level WebSocket-over-HTTP/2 support as an open feature request:
:protocolnetty/netty#11192A third-party Netty implementation also exists:
Questions
pekko.http.server.websocketorpekko.http.server.http2?WebSocketUpgradeAPI be reused for HTTP/2 Extended CONNECT, or should there be a separate API to distinguish HTTP/1.1 upgrade from HTTP/2 stream-based WebSocket bootstrap?