Skip to content

Commit 25e72f7

Browse files
committed
TUN-3549: Use a separate handler for each websocket proxy
1 parent 7613410 commit 25e72f7

File tree

1 file changed

+51
-37
lines changed

1 file changed

+51
-37
lines changed

websocket/websocket.go

Lines changed: 51 additions & 37 deletions
Original file line numberDiff line numberDiff line change
@@ -147,54 +147,68 @@ func StartProxyServer(logger logger.Service, listener net.Listener, staticHost s
147147
ReadBufferSize: 1024,
148148
WriteBufferSize: 1024,
149149
}
150+
h := handler{
151+
upgrader: upgrader,
152+
logger: logger,
153+
staticHost: staticHost,
154+
streamHandler: streamHandler,
155+
}
150156

151-
httpServer := &http.Server{Addr: listener.Addr().String(), Handler: nil}
157+
httpServer := &http.Server{Addr: listener.Addr().String(), Handler: &h}
152158
go func() {
153159
<-shutdownC
154160
httpServer.Close()
155161
}()
156162

157-
http.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
158-
// If remote is an empty string, get the destination from the client.
159-
finalDestination := staticHost
160-
if finalDestination == "" {
161-
if jumpDestination := r.Header.Get(h2mux.CFJumpDestinationHeader); jumpDestination == "" {
162-
logger.Error("Did not receive final destination from client. The --destination flag is likely not set")
163-
return
164-
} else {
165-
finalDestination = jumpDestination
166-
}
167-
}
163+
return httpServer.Serve(listener)
164+
}
168165

169-
stream, err := net.Dial("tcp", finalDestination)
170-
if err != nil {
171-
logger.Errorf("Cannot connect to remote: %s", err)
172-
return
173-
}
174-
defer stream.Close()
166+
// HTTP handler for the websocket proxy.
167+
type handler struct {
168+
logger logger.Service
169+
staticHost string
170+
upgrader websocket.Upgrader
171+
streamHandler func(wsConn *Conn, remoteConn net.Conn, requestHeaders http.Header)
172+
}
175173

176-
if !websocket.IsWebSocketUpgrade(r) {
177-
w.Write(nonWebSocketRequestPage())
178-
return
179-
}
180-
conn, err := upgrader.Upgrade(w, r, nil)
181-
if err != nil {
182-
logger.Errorf("failed to upgrade: %s", err)
174+
func (h *handler) ServeHTTP(w http.ResponseWriter, r *http.Request) {
175+
// If remote is an empty string, get the destination from the client.
176+
finalDestination := h.staticHost
177+
if finalDestination == "" {
178+
if jumpDestination := r.Header.Get(h2mux.CFJumpDestinationHeader); jumpDestination == "" {
179+
h.logger.Error("Did not receive final destination from client. The --destination flag is likely not set")
183180
return
181+
} else {
182+
finalDestination = jumpDestination
184183
}
185-
conn.SetReadDeadline(time.Now().Add(pongWait))
186-
conn.SetPongHandler(func(string) error { conn.SetReadDeadline(time.Now().Add(pongWait)); return nil })
187-
done := make(chan struct{})
188-
go pinger(logger, conn, done)
189-
defer func() {
190-
done <- struct{}{}
191-
conn.Close()
192-
}()
193-
194-
streamHandler(&Conn{conn}, stream, r.Header)
195-
})
184+
}
196185

197-
return httpServer.Serve(listener)
186+
stream, err := net.Dial("tcp", finalDestination)
187+
if err != nil {
188+
h.logger.Errorf("Cannot connect to remote: %s", err)
189+
return
190+
}
191+
defer stream.Close()
192+
193+
if !websocket.IsWebSocketUpgrade(r) {
194+
w.Write(nonWebSocketRequestPage())
195+
return
196+
}
197+
conn, err := h.upgrader.Upgrade(w, r, nil)
198+
if err != nil {
199+
h.logger.Errorf("failed to upgrade: %s", err)
200+
return
201+
}
202+
conn.SetReadDeadline(time.Now().Add(pongWait))
203+
conn.SetPongHandler(func(string) error { conn.SetReadDeadline(time.Now().Add(pongWait)); return nil })
204+
done := make(chan struct{})
205+
go pinger(h.logger, conn, done)
206+
defer func() {
207+
done <- struct{}{}
208+
conn.Close()
209+
}()
210+
211+
h.streamHandler(&Conn{conn}, stream, r.Header)
198212
}
199213

200214
// SendSSHPreamble sends the final SSH destination address to the cloudflared SSH proxy

0 commit comments

Comments
 (0)