@@ -19,6 +19,15 @@ import (
1919 "testing"
2020)
2121
22+ // These test cases use a websocket client (Dialer)/proxy/websocket server (Upgrader)
23+ // to validate the cases where a proxy is an intermediary between a websocket client
24+ // and server. The test cases usually 1) create a websocket server which echoes any
25+ // data received back to the client, 2) a basic duplex streaming proxy, and 3) a
26+ // websocket client which sends random data to the server through the proxy,
27+ // validating any subsequent data received is the same as the data sent. The various
28+ // permutations include the proxy and backend schemes (HTTP or HTTPS), as well as
29+ // the custom dial functions (e.g NetDialContext, NetDial) set on the Dialer.
30+
2231const (
2332 subprotocolv1 = "subprotocol-version-1"
2433 subprotocolv2 = "subprotocol-version-2"
@@ -288,13 +297,13 @@ func TestHTTPProxyWithNetDialContext(t *testing.T) {
288297// TLS Config: set (used for both proxy and backend TLS)
289298func TestHTTPSProxyAndBackend (t * testing.T ) {
290299 // Start the websocket server running TLS.
291- cert , err := tls .X509KeyPair (localhostCert , localhostKey )
300+ websocketCert , err := tls .X509KeyPair (websocketServerCert , websocketServerKey )
292301 if err != nil {
293302 t .Fatalf ("error creating TLS key pair: %v" , err )
294303 }
295304 websocketServer := httptest .NewUnstartedServer (websocketEchoHandler )
296305 websocketServer .TLS = & tls.Config {
297- Certificates : []tls.Certificate {cert },
306+ Certificates : []tls.Certificate {websocketCert },
298307 }
299308 websocketServer .StartTLS ()
300309 defer websocketServer .Close ()
@@ -303,13 +312,17 @@ func TestHTTPSProxyAndBackend(t *testing.T) {
303312 t .Fatalf ("error parsing websocket server URL: %v" , err )
304313 }
305314 // Start the proxy server running TLS.
315+ proxyCert , err := tls .X509KeyPair (proxyServerCert , proxyServerKey )
316+ if err != nil {
317+ t .Fatalf ("error creating TLS key pair: %v" , err )
318+ }
306319 var proxyCalled atomic.Int64
307320 proxyServer := httptest .NewUnstartedServer (http .HandlerFunc (func (w http.ResponseWriter , req * http.Request ) {
308321 proxyCalled .Add (1 )
309322 proxyHandler .ServeHTTP (w , req )
310323 }))
311324 proxyServer .TLS = & tls.Config {
312- Certificates : []tls.Certificate {cert },
325+ Certificates : []tls.Certificate {proxyCert },
313326 }
314327 proxyServer .StartTLS ()
315328 defer proxyServer .Close ()
@@ -320,7 +333,8 @@ func TestHTTPSProxyAndBackend(t *testing.T) {
320333 // Dial the websocket server to create the websocket connection,
321334 // setting the proxy URL, the TLS CA data, and the requested subprotocol.
322335 certPool := x509 .NewCertPool ()
323- certPool .AppendCertsFromPEM (localhostCert )
336+ certPool .AppendCertsFromPEM (websocketServerCert )
337+ certPool .AppendCertsFromPEM (proxyServerCert )
324338 dialer := Dialer {
325339 Proxy : http .ProxyURL (proxyServerURL ),
326340 TLSClientConfig : & tls.Config {
@@ -362,7 +376,7 @@ func TestHTTPSProxyAndBackend(t *testing.T) {
362376// TLS Config: set (used for both proxy and backend TLS)
363377func TestHTTPSProxyUsingNetDial (t * testing.T ) {
364378 // Start the websocket server running TLS.
365- cert , err := tls .X509KeyPair (localhostCert , localhostKey )
379+ cert , err := tls .X509KeyPair (websocketServerCert , websocketServerKey )
366380 if err != nil {
367381 t .Fatalf ("error creating TLS key pair: %v" , err )
368382 }
@@ -377,13 +391,17 @@ func TestHTTPSProxyUsingNetDial(t *testing.T) {
377391 t .Fatalf ("error parsing websocket server URL: %v" , err )
378392 }
379393 // Start the proxy server running TLS.
394+ proxyCert , err := tls .X509KeyPair (proxyServerCert , proxyServerKey )
395+ if err != nil {
396+ t .Fatalf ("error creating TLS key pair: %v" , err )
397+ }
380398 var proxyCalled atomic.Int64
381399 proxyServer := httptest .NewUnstartedServer (http .HandlerFunc (func (w http.ResponseWriter , req * http.Request ) {
382400 proxyCalled .Add (1 )
383401 proxyHandler .ServeHTTP (w , req )
384402 }))
385403 proxyServer .TLS = & tls.Config {
386- Certificates : []tls.Certificate {cert },
404+ Certificates : []tls.Certificate {proxyCert },
387405 }
388406 proxyServer .StartTLS ()
389407 defer proxyServer .Close ()
@@ -396,7 +414,8 @@ func TestHTTPSProxyUsingNetDial(t *testing.T) {
396414 // Also, set the "NetDial" function to dial the proxy (with the
397415 // TLSClientConfig for the TLS handshake).
398416 certPool := x509 .NewCertPool ()
399- certPool .AppendCertsFromPEM (localhostCert )
417+ certPool .AppendCertsFromPEM (websocketServerCert )
418+ certPool .AppendCertsFromPEM (proxyServerCert )
400419 var netDialCalled atomic.Int64
401420 dialer := Dialer {
402421 NetDial : func (network , addr string ) (net.Conn , error ) {
@@ -446,13 +465,13 @@ func TestHTTPSProxyUsingNetDial(t *testing.T) {
446465// TLS Config: set (used for both proxy and backend TLS)
447466func TestHTTPSProxyUsingNetDialContext (t * testing.T ) {
448467 // Start the websocket server running TLS.
449- cert , err := tls .X509KeyPair (localhostCert , localhostKey )
468+ websocketCert , err := tls .X509KeyPair (websocketServerCert , websocketServerKey )
450469 if err != nil {
451470 t .Fatalf ("error creating TLS key pair: %v" , err )
452471 }
453472 websocketServer := httptest .NewUnstartedServer (websocketEchoHandler )
454473 websocketServer .TLS = & tls.Config {
455- Certificates : []tls.Certificate {cert },
474+ Certificates : []tls.Certificate {websocketCert },
456475 }
457476 websocketServer .StartTLS ()
458477 defer websocketServer .Close ()
@@ -461,13 +480,17 @@ func TestHTTPSProxyUsingNetDialContext(t *testing.T) {
461480 t .Fatalf ("error parsing websocket server URL: %v" , err )
462481 }
463482 // Start the proxy server running TLS.
483+ proxyCert , err := tls .X509KeyPair (proxyServerCert , proxyServerKey )
484+ if err != nil {
485+ t .Fatalf ("error creating TLS key pair: %v" , err )
486+ }
464487 var proxyCalled atomic.Int64
465488 proxyServer := httptest .NewUnstartedServer (http .HandlerFunc (func (w http.ResponseWriter , req * http.Request ) {
466489 proxyCalled .Add (1 )
467490 proxyHandler .ServeHTTP (w , req )
468491 }))
469492 proxyServer .TLS = & tls.Config {
470- Certificates : []tls.Certificate {cert },
493+ Certificates : []tls.Certificate {proxyCert },
471494 }
472495 proxyServer .StartTLS ()
473496 defer proxyServer .Close ()
@@ -480,7 +503,8 @@ func TestHTTPSProxyUsingNetDialContext(t *testing.T) {
480503 // Also, set the "NetDialContext" function to dial the proxy (with the
481504 // TLSClientConfig for the TLS handshake).
482505 certPool := x509 .NewCertPool ()
483- certPool .AppendCertsFromPEM (localhostCert )
506+ certPool .AppendCertsFromPEM (websocketServerCert )
507+ certPool .AppendCertsFromPEM (proxyServerCert )
484508 var netDialCalled atomic.Int64
485509 dialer := Dialer {
486510 NetDialContext : func (ctx context.Context , network , addr string ) (net.Conn , error ) {
@@ -530,13 +554,13 @@ func TestHTTPSProxyUsingNetDialContext(t *testing.T) {
530554// TLS Config: set (used for backend TLS)
531555func TestHTTPSProxyUsingNetDialTLSContext (t * testing.T ) {
532556 // Start the websocket server running TLS.
533- cert , err := tls .X509KeyPair (localhostCert , localhostKey )
557+ websocketCert , err := tls .X509KeyPair (websocketServerCert , websocketServerKey )
534558 if err != nil {
535559 t .Fatalf ("error creating TLS key pair: %v" , err )
536560 }
537561 websocketServer := httptest .NewUnstartedServer (websocketEchoHandler )
538562 websocketServer .TLS = & tls.Config {
539- Certificates : []tls.Certificate {cert },
563+ Certificates : []tls.Certificate {websocketCert },
540564 }
541565 websocketServer .StartTLS ()
542566 defer websocketServer .Close ()
@@ -545,13 +569,17 @@ func TestHTTPSProxyUsingNetDialTLSContext(t *testing.T) {
545569 t .Fatalf ("error parsing websocket server URL: %v" , err )
546570 }
547571 // Start the proxy server running TLS.
572+ proxyCert , err := tls .X509KeyPair (proxyServerCert , proxyServerKey )
573+ if err != nil {
574+ t .Fatalf ("error creating TLS key pair: %v" , err )
575+ }
548576 var proxyCalled atomic.Int64
549577 proxyServer := httptest .NewUnstartedServer (http .HandlerFunc (func (w http.ResponseWriter , req * http.Request ) {
550578 proxyCalled .Add (1 )
551579 proxyHandler .ServeHTTP (w , req )
552580 }))
553581 proxyServer .TLS = & tls.Config {
554- Certificates : []tls.Certificate {cert },
582+ Certificates : []tls.Certificate {proxyCert },
555583 }
556584 proxyServer .StartTLS ()
557585 defer proxyServer .Close ()
@@ -564,7 +592,8 @@ func TestHTTPSProxyUsingNetDialTLSContext(t *testing.T) {
564592 // performs the TLS handshake. NOTE: Subsequent TLS handshake to backend
565593 // (over proxied connection) uses TLSClientConfig for handshake.
566594 certPool := x509 .NewCertPool ()
567- certPool .AppendCertsFromPEM (localhostCert )
595+ certPool .AppendCertsFromPEM (websocketServerCert )
596+ certPool .AppendCertsFromPEM (proxyServerCert )
568597 tlsConfig := & tls.Config {RootCAs : certPool }
569598 var netDialCalled atomic.Int64
570599 dialer := Dialer {
@@ -623,7 +652,7 @@ func TestHTTPSProxyUsingNetDialTLSContextWithHTTPBackend(t *testing.T) {
623652 t .Fatalf ("error parsing websocket server URL: %v" , err )
624653 }
625654 // Start the proxy server running TLS.
626- cert , err := tls .X509KeyPair (localhostCert , localhostKey )
655+ proxyCert , err := tls .X509KeyPair (proxyServerCert , proxyServerKey )
627656 if err != nil {
628657 t .Fatalf ("error creating TLS key pair: %v" , err )
629658 }
@@ -633,7 +662,7 @@ func TestHTTPSProxyUsingNetDialTLSContextWithHTTPBackend(t *testing.T) {
633662 proxyHandler .ServeHTTP (w , req )
634663 }))
635664 proxyServer .TLS = & tls.Config {
636- Certificates : []tls.Certificate {cert },
665+ Certificates : []tls.Certificate {proxyCert },
637666 }
638667 proxyServer .StartTLS ()
639668 defer proxyServer .Close ()
@@ -643,7 +672,7 @@ func TestHTTPSProxyUsingNetDialTLSContextWithHTTPBackend(t *testing.T) {
643672 }
644673 // Dials websocket backend through HTTPS proxy, using NetDialTLSContext.
645674 certPool := x509 .NewCertPool ()
646- certPool .AppendCertsFromPEM (localhostCert )
675+ certPool .AppendCertsFromPEM (proxyServerCert )
647676 tlsConfig := & tls.Config {RootCAs : certPool }
648677 var netDialCalled atomic.Int64
649678 dialer := Dialer {
@@ -684,10 +713,12 @@ func TestHTTPSProxyUsingNetDialTLSContextWithHTTPBackend(t *testing.T) {
684713 }
685714}
686715
687- // localhostCert was generated from crypto/tls/generate_cert.go with the following command:
716+ // proxyServerCert was generated from crypto/tls/generate_cert.go with the following command:
688717//
689718// go run generate_cert.go --rsa-bits 2048 --host 127.0.0.1,::1,example.com --ca --start-date "Jan 1 00:00:00 1970" --duration=1000000h
690- var localhostCert = []byte (`-----BEGIN CERTIFICATE-----
719+ //
720+ // proxyServerCert is a self-signed.
721+ var proxyServerCert = []byte (`-----BEGIN CERTIFICATE-----
691722MIIDGTCCAgGgAwIBAgIRALL5AZcefF4kkYV1SEG6YrMwDQYJKoZIhvcNAQELBQAw
692723EjEQMA4GA1UEChMHQWNtZSBDbzAgFw03MDAxMDEwMDAwMDBaGA8yMDg0MDEyOTE2
693724MDAwMFowEjEQMA4GA1UEChMHQWNtZSBDbzCCASIwDQYJKoZIhvcNAQEBBQADggEP
@@ -707,8 +738,8 @@ MGYMzP0u4nw47aRz9shB8w+taPKHx2BVwE1m/yp3nHVioOjXqA1fwRQVGclCJSH1
707738D2iq3hWVHRENgjTjANBPICLo9AZ4JfN6PH19mnU=
708739-----END CERTIFICATE-----` )
709740
710- // localhostKey is the private key for localhostCert .
711- var localhostKey = []byte (`-----BEGIN RSA PRIVATE KEY-----
741+ // proxyServerKey is the private key for proxyServerCert .
742+ var proxyServerKey = []byte (`-----BEGIN RSA PRIVATE KEY-----
712743MIIEogIBAAKCAQEAtD8UdzJXB0UfEBFtsPYoG0NRPsSeL7yKg12O0Zya1eoG/jkQ
713744LUIk6qoYlOugUYnpD2RAhn0WofkglHZ844kP2Q5O54bhW3UljWuPUpumN5+7xeV5
714745nktIHAhZWc3+USwRu4qaPs3aAu3kAffMxmIEjWaDW71nllkdhsKJOkGvCyrpxOW9
@@ -736,3 +767,56 @@ LiAGaec8xjl6QK/DdXmFuQBKqyKJ14rljFODP4QuE9WJid94bGqjpf3j99ltznZP
736767KR8NJEkK99Vh/tew6jAMll70xFrE7aF8VLXJVE7w4sQzuvHxl9Q=
737768-----END RSA PRIVATE KEY-----
738769` )
770+
771+ // websocketServerCert is self-signed.
772+ var websocketServerCert = []byte (`-----BEGIN CERTIFICATE-----
773+ MIIDOTCCAiGgAwIBAgIQYSN1VY/favsLUo+B7gJ5tTANBgkqhkiG9w0BAQsFADAS
774+ MRAwDgYDVQQKEwdBY21lIENvMCAXDTcwMDEwMTAwMDAwMFoYDzIwODQwMTI5MTYw
775+ MDAwWjASMRAwDgYDVQQKEwdBY21lIENvMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8A
776+ MIIBCgKCAQEApBlintjkL1fO1Sk2pzNvl862CtTwU7/Jy6EZqWzI17wEbPn4sbSD
777+ bHhfDlPl2nmw3hVkc6LNK+eqzm2GX/ai4tgMiaH7kyyNit1K3g7y7GISMf9poWIa
778+ POJhid2wmhKHbEtHECSdQ5c/jEN1UVzB4go5LO7MEEVo9kyQ+yBqS6gISyFmfaT4
779+ qOsPJBir33bBpptSend1JSXaRTXqRa1p+oudw2ILa4U7KfuKK3emp21m5/HYAuSf
780+ CV4WqqDoDiBPMpsQ0kPEPugWZKFeF3qanmqFFvptYx+zJbOznWYY2D3idWsvcg6q
781+ VLPEB19oXaVBV0HXPFtObm5m1jCpl8FI1wIDAQABo4GIMIGFMA4GA1UdDwEB/wQE
782+ AwICpDATBgNVHSUEDDAKBggrBgEFBQcDATAPBgNVHRMBAf8EBTADAQH/MB0GA1Ud
783+ DgQWBBQcSkjqA9rgos1daegNj49BpRCA0jAuBgNVHREEJzAlggtleGFtcGxlLmNv
784+ bYcEfwAAAYcQAAAAAAAAAAAAAAAAAAAAATANBgkqhkiG9w0BAQsFAAOCAQEAnk9i
785+ 9rogNTi9B1pn+Fbk3WALKdEjv/uyePsTnwdyvswVbeYbQweU9TrhYT2+eXbMA5kY
786+ 7TaQm46idRqxCKMgc3Ip3DADJdm8cJX9p2ExU4fKdkPc1KD/J+4QHHx1W2Ml5S2o
787+ foOo6j1F0UdZP/rBj0UumEZp32qW+4DhVV/QQjUB8J0gaDC7yZBMdyMIeClR0RqE
788+ YfZdCJbQHqtTwBXN+imQUHPGmksYkRDpFRvw/4crpcMIE04mVVd99nOpFCQnK61t
789+ 9US1y17VW1lYpkqlCS+rkcAtor4Z5naSf9/oLGCxEAwyW0pwHGO6MXtMxvB/JD20
790+ hJdlz1I7wlSfF4MiRQ==
791+ -----END CERTIFICATE-----` )
792+
793+ // websocketServerKey is the private key for websocketServerCert.
794+ var websocketServerKey = []byte (`-----BEGIN PRIVATE KEY-----
795+ MIIEvAIBADANBgkqhkiG9w0BAQEFAASCBKYwggSiAgEAAoIBAQCkGWKe2OQvV87V
796+ KTanM2+XzrYK1PBTv8nLoRmpbMjXvARs+fixtINseF8OU+XaebDeFWRzos0r56rO
797+ bYZf9qLi2AyJofuTLI2K3UreDvLsYhIx/2mhYho84mGJ3bCaEodsS0cQJJ1Dlz+M
798+ Q3VRXMHiCjks7swQRWj2TJD7IGpLqAhLIWZ9pPio6w8kGKvfdsGmm1J6d3UlJdpF
799+ NepFrWn6i53DYgtrhTsp+4ord6anbWbn8dgC5J8JXhaqoOgOIE8ymxDSQ8Q+6BZk
800+ oV4XepqeaoUW+m1jH7Mls7OdZhjYPeJ1ay9yDqpUs8QHX2hdpUFXQdc8W05ubmbW
801+ MKmXwUjXAgMBAAECggEAE6BkTDgH//rnkP/Ej/Y17Zkv6qxnMLe/4evwZB7PsrBu
802+ cxOUAWUOpvA1UO215bh87+2XvcDbUISnyC1kpKDyAGGeC5llER2DXE11VokWgtvZ
803+ Q0OXavw5w83A+WVGFFdiUmXP0l10CxEm7OwQjFz6D21GQ1qC65tG9NZZghTxbFTe
804+ iZKqgWqyHsaAWLOuDQbj1FTEBMFrY8f9RbclSh0luPZnzGc4BVI/t34jKPZBpH2N
805+ NCkr8aB7MMHGhrNZFHAu/KAvq8UBrDTX+O8ERMwcwQWB4nne2+GOTN0MdcAUc72i
806+ GryzIa8TgO+TpQOYoZ4NPnzFrsa+m3G2Tug3vbt62QKBgQDOPfM4/5/x/h/ggxQn
807+ aRvEOC+8ldeqEOS1VTGiuDKJMWXrNkG+d+AsxfNP4k0QVNrpEAZSYcf0gnS9Odcl
808+ luEsi/yPZDDnPg/cS+Z3336VKsggly7BWFs1Ct/9I+ZfSCl88TkVpIfeCBC34XEb
809+ 0mFUq/RdLqXj/mVLbBfr+H8cEwKBgQDLsJUm8lkWFAPJ8UMto8xeUMGk44VukYwx
810+ +oI6KhplFntiI0C1Dd9wrxyCjySlJcc0NFt6IPN84d7pI9LQSbiKXQ1jMvsBzd4G
811+ EMtG8SHpIY/mMU+KzWLHYVFS0FA4PvXXvPRNLOXas7hbALZdLshVKd7aDlkQAb5C
812+ KWFHeIFwrQKBgA8r5Xl67HQrwoKMge4IQF+l1nUj/LJo/boNI1KaBDWtaZbs7dcq
813+ EFaa1TQ6LHsYEuZ0JFLpGIF3G0lUOOxt9fCF97VApIxON3J4LuMAkNo+RGyJUoos
814+ isETJLkFbAv0TgD/6bga21fM9hXgwqZOSpSk9ZvpM5DbBO6QbA4SwJ77AoGAX7h1
815+ /z14XAW/2hDE7xfAnLn6plA9jj5b0cjVlhvfF44/IVlLuUnxrPS9wyUdpXZhbMkG
816+ DBicFB3ZMVqiYTuju3ILLojwqGJkahlOTeJXe0VIaHbX2HS4bNXw76fxat07jsy/
817+ Sd1Fj0dR5YIqMRQhFNR+Y57Gf90x2cm0a2/X9GkCgYANawYx9bNfcX0HMVG7vktK
818+ 6/80omnoBM0JUxA+V7DxS8kr9Cj2Y/kcS+VHb4yyoSkDgnsSdnCr1ZTctcj828MJ
819+ 8AUwskAtEjPkHRXEgRRnEl2oJGD1TT5iwBNnuPAQDXwzkGCRYBnlfZNbILbOoSUz
820+ m+VDcqT5XzcRADa/TLlEXA==
821+ -----END PRIVATE KEY-----
822+ ` )
0 commit comments