...

Text file src/nhooyr.io/websocket/README.md

Documentation: nhooyr.io/websocket

     1# websocket
     2
     3[![Go Reference](https://pkg.go.dev/badge/nhooyr.io/websocket.svg)](https://pkg.go.dev/nhooyr.io/websocket)
     4[![Go Coverage](https://img.shields.io/badge/coverage-91%25-success)](https://nhooyr.io/websocket/coverage.html)
     5
     6websocket is a minimal and idiomatic WebSocket library for Go.
     7
     8## Install
     9
    10```sh
    11go get nhooyr.io/websocket
    12```
    13
    14## Highlights
    15
    16- Minimal and idiomatic API
    17- First class [context.Context](https://blog.golang.org/context) support
    18- Fully passes the WebSocket [autobahn-testsuite](https://github.com/crossbario/autobahn-testsuite)
    19- [Zero dependencies](https://pkg.go.dev/nhooyr.io/websocket?tab=imports)
    20- JSON helpers in the [wsjson](https://pkg.go.dev/nhooyr.io/websocket/wsjson) subpackage
    21- Zero alloc reads and writes
    22- Concurrent writes
    23- [Close handshake](https://pkg.go.dev/nhooyr.io/websocket#Conn.Close)
    24- [net.Conn](https://pkg.go.dev/nhooyr.io/websocket#NetConn) wrapper
    25- [Ping pong](https://pkg.go.dev/nhooyr.io/websocket#Conn.Ping) API
    26- [RFC 7692](https://tools.ietf.org/html/rfc7692) permessage-deflate compression
    27- [CloseRead](https://pkg.go.dev/nhooyr.io/websocket#Conn.CloseRead) helper for write only connections
    28- Compile to [Wasm](https://pkg.go.dev/nhooyr.io/websocket#hdr-Wasm)
    29
    30## Roadmap
    31
    32See GitHub issues for minor issues but the major future enhancements are:
    33
    34- [ ] Perfect examples [#217](https://github.com/nhooyr/websocket/issues/217)
    35- [ ] wstest.Pipe for in memory testing [#340](https://github.com/nhooyr/websocket/issues/340)
    36- [ ] Ping pong heartbeat helper [#267](https://github.com/nhooyr/websocket/issues/267)
    37- [ ] Ping pong instrumentation callbacks [#246](https://github.com/nhooyr/websocket/issues/246)
    38- [ ] Graceful shutdown helpers [#209](https://github.com/nhooyr/websocket/issues/209)
    39- [ ] Assembly for WebSocket masking [#16](https://github.com/nhooyr/websocket/issues/16)
    40  - WIP at [#326](https://github.com/nhooyr/websocket/pull/326), about 3x faster
    41- [ ] HTTP/2 [#4](https://github.com/nhooyr/websocket/issues/4)
    42- [ ] The holy grail [#402](https://github.com/nhooyr/websocket/issues/402)
    43
    44## Examples
    45
    46For a production quality example that demonstrates the complete API, see the
    47[echo example](./internal/examples/echo).
    48
    49For a full stack example, see the [chat example](./internal/examples/chat).
    50
    51### Server
    52
    53```go
    54http.HandlerFunc(func (w http.ResponseWriter, r *http.Request) {
    55	c, err := websocket.Accept(w, r, nil)
    56	if err != nil {
    57		// ...
    58	}
    59	defer c.CloseNow()
    60
    61	ctx, cancel := context.WithTimeout(r.Context(), time.Second*10)
    62	defer cancel()
    63
    64	var v interface{}
    65	err = wsjson.Read(ctx, c, &v)
    66	if err != nil {
    67		// ...
    68	}
    69
    70	log.Printf("received: %v", v)
    71
    72	c.Close(websocket.StatusNormalClosure, "")
    73})
    74```
    75
    76### Client
    77
    78```go
    79ctx, cancel := context.WithTimeout(context.Background(), time.Minute)
    80defer cancel()
    81
    82c, _, err := websocket.Dial(ctx, "ws://localhost:8080", nil)
    83if err != nil {
    84	// ...
    85}
    86defer c.CloseNow()
    87
    88err = wsjson.Write(ctx, c, "hi")
    89if err != nil {
    90	// ...
    91}
    92
    93c.Close(websocket.StatusNormalClosure, "")
    94```
    95
    96## Comparison
    97
    98### gorilla/websocket
    99
   100Advantages of [gorilla/websocket](https://github.com/gorilla/websocket):
   101
   102- Mature and widely used
   103- [Prepared writes](https://pkg.go.dev/github.com/gorilla/websocket#PreparedMessage)
   104- Configurable [buffer sizes](https://pkg.go.dev/github.com/gorilla/websocket#hdr-Buffers)
   105
   106Advantages of nhooyr.io/websocket:
   107
   108- Minimal and idiomatic API
   109  - Compare godoc of [nhooyr.io/websocket](https://pkg.go.dev/nhooyr.io/websocket) with [gorilla/websocket](https://pkg.go.dev/github.com/gorilla/websocket) side by side.
   110- [net.Conn](https://pkg.go.dev/nhooyr.io/websocket#NetConn) wrapper
   111- Zero alloc reads and writes ([gorilla/websocket#535](https://github.com/gorilla/websocket/issues/535))
   112- Full [context.Context](https://blog.golang.org/context) support
   113- Dial uses [net/http.Client](https://golang.org/pkg/net/http/#Client)
   114  - Will enable easy HTTP/2 support in the future
   115  - Gorilla writes directly to a net.Conn and so duplicates features of net/http.Client.
   116- Concurrent writes
   117- Close handshake ([gorilla/websocket#448](https://github.com/gorilla/websocket/issues/448))
   118- Idiomatic [ping pong](https://pkg.go.dev/nhooyr.io/websocket#Conn.Ping) API
   119  - Gorilla requires registering a pong callback before sending a Ping
   120- Can target Wasm ([gorilla/websocket#432](https://github.com/gorilla/websocket/issues/432))
   121- Transparent message buffer reuse with [wsjson](https://pkg.go.dev/nhooyr.io/websocket/wsjson) subpackage
   122- [1.75x](https://github.com/nhooyr/websocket/releases/tag/v1.7.4) faster WebSocket masking implementation in pure Go
   123  - Gorilla's implementation is slower and uses [unsafe](https://golang.org/pkg/unsafe/).
   124    Soon we'll have assembly and be 3x faster [#326](https://github.com/nhooyr/websocket/pull/326)
   125- Full [permessage-deflate](https://tools.ietf.org/html/rfc7692) compression extension support
   126  - Gorilla only supports no context takeover mode
   127- [CloseRead](https://pkg.go.dev/nhooyr.io/websocket#Conn.CloseRead) helper for write only connections ([gorilla/websocket#492](https://github.com/gorilla/websocket/issues/492))
   128
   129#### golang.org/x/net/websocket
   130
   131[golang.org/x/net/websocket](https://pkg.go.dev/golang.org/x/net/websocket) is deprecated.
   132See [golang/go/issues/18152](https://github.com/golang/go/issues/18152).
   133
   134The [net.Conn](https://pkg.go.dev/nhooyr.io/websocket#NetConn) can help in transitioning
   135to nhooyr.io/websocket.
   136
   137#### gobwas/ws
   138
   139[gobwas/ws](https://github.com/gobwas/ws) has an extremely flexible API that allows it to be used
   140in an event driven style for performance. See the author's [blog post](https://medium.freecodecamp.org/million-websockets-and-go-cc58418460bb).
   141
   142However it is quite bloated. See https://pkg.go.dev/github.com/gobwas/ws
   143
   144When writing idiomatic Go, nhooyr.io/websocket will be faster and easier to use.
   145
   146#### lesismal/nbio
   147
   148[lesismal/nbio](https://github.com/lesismal/nbio) is similar to gobwas/ws in that the API is
   149event driven for performance reasons.
   150
   151However it is quite bloated. See https://pkg.go.dev/github.com/lesismal/nbio
   152
   153When writing idiomatic Go, nhooyr.io/websocket will be faster and easier to use.

View as plain text