1
0

websocket.go 1.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566
  1. package net
  2. import (
  3. "errors"
  4. "net"
  5. "net/http"
  6. "golang.org/x/net/websocket"
  7. )
  8. var ErrWebsocketListenerClosed = errors.New("websocket listener closed")
  9. const (
  10. FrpWebsocketPath = "/~!frp"
  11. )
  12. type WebsocketListener struct {
  13. ln net.Listener
  14. acceptCh chan net.Conn
  15. server *http.Server
  16. }
  17. // NewWebsocketListener to handle websocket connections
  18. // ln: tcp listener for websocket connections
  19. func NewWebsocketListener(ln net.Listener) (wl *WebsocketListener) {
  20. wl = &WebsocketListener{
  21. acceptCh: make(chan net.Conn),
  22. }
  23. muxer := http.NewServeMux()
  24. muxer.Handle(FrpWebsocketPath, websocket.Handler(func(c *websocket.Conn) {
  25. notifyCh := make(chan struct{})
  26. conn := WrapCloseNotifyConn(c, func() {
  27. close(notifyCh)
  28. })
  29. wl.acceptCh <- conn
  30. <-notifyCh
  31. }))
  32. wl.server = &http.Server{
  33. Addr: ln.Addr().String(),
  34. Handler: muxer,
  35. }
  36. go func() {
  37. _ = wl.server.Serve(ln)
  38. }()
  39. return
  40. }
  41. func (p *WebsocketListener) Accept() (net.Conn, error) {
  42. c, ok := <-p.acceptCh
  43. if !ok {
  44. return nil, ErrWebsocketListenerClosed
  45. }
  46. return c, nil
  47. }
  48. func (p *WebsocketListener) Close() error {
  49. return p.server.Close()
  50. }
  51. func (p *WebsocketListener) Addr() net.Addr {
  52. return p.ln.Addr()
  53. }