mirror of
https://github.com/oauth2-proxy/oauth2-proxy.git
synced 2026-10-18 04:41:19 +02:00
Implement configurable timeout for upstream connections
Signed-off-by: Jack Henschel <jack.henschel@cern.ch>
This commit is contained in:
committed by
Joel Speed
parent
27f4bb6a0e
commit
7a27cb04df
+22
-7
@@ -1,7 +1,6 @@
|
||||
package upstream
|
||||
|
||||
import (
|
||||
"crypto/tls"
|
||||
"net/http"
|
||||
"net/http/httputil"
|
||||
"net/url"
|
||||
@@ -100,6 +99,14 @@ func (h *httpUpstreamProxy) ServeHTTP(rw http.ResponseWriter, req *http.Request)
|
||||
func newReverseProxy(target *url.URL, upstream options.Upstream, errorHandler ProxyErrorHandler) http.Handler {
|
||||
proxy := httputil.NewSingleHostReverseProxy(target)
|
||||
|
||||
// Inherit default transport options from Go's stdlib
|
||||
transport := http.DefaultTransport.(*http.Transport).Clone()
|
||||
|
||||
// Change default duration for waiting for an upstream response
|
||||
if upstream.Timeout != nil {
|
||||
transport.ResponseHeaderTimeout = upstream.Timeout.Duration()
|
||||
}
|
||||
|
||||
// Configure options on the SingleHostReverseProxy
|
||||
if upstream.FlushInterval != nil {
|
||||
proxy.FlushInterval = upstream.FlushInterval.Duration()
|
||||
@@ -110,9 +117,7 @@ func newReverseProxy(target *url.URL, upstream options.Upstream, errorHandler Pr
|
||||
// InsecureSkipVerify is a configurable option we allow
|
||||
/* #nosec G402 */
|
||||
if upstream.InsecureSkipTLSVerify {
|
||||
proxy.Transport = &http.Transport{
|
||||
TLSClientConfig: &tls.Config{InsecureSkipVerify: true},
|
||||
}
|
||||
transport.TLSClientConfig.InsecureSkipVerify = true
|
||||
}
|
||||
|
||||
// Ensure we always pass the original request path
|
||||
@@ -127,6 +132,10 @@ func newReverseProxy(target *url.URL, upstream options.Upstream, errorHandler Pr
|
||||
if errorHandler != nil {
|
||||
proxy.ErrorHandler = errorHandler
|
||||
}
|
||||
|
||||
// Apply the customized transport to our proxy before returning it
|
||||
proxy.Transport = transport
|
||||
|
||||
return proxy
|
||||
}
|
||||
|
||||
@@ -156,11 +165,17 @@ func setProxyDirector(proxy *httputil.ReverseProxy) {
|
||||
// newWebSocketReverseProxy creates a new reverse proxy for proxying websocket connections.
|
||||
func newWebSocketReverseProxy(u *url.URL, skipTLSVerify bool) http.Handler {
|
||||
wsProxy := httputil.NewSingleHostReverseProxy(u)
|
||||
|
||||
// Inherit default transport options from Go's stdlib
|
||||
transport := http.DefaultTransport.(*http.Transport).Clone()
|
||||
|
||||
/* #nosec G402 */
|
||||
if skipTLSVerify {
|
||||
wsProxy.Transport = &http.Transport{
|
||||
TLSClientConfig: &tls.Config{InsecureSkipVerify: true},
|
||||
}
|
||||
transport.TLSClientConfig.InsecureSkipVerify = true
|
||||
}
|
||||
|
||||
// Apply the customized transport to our proxy before returning it
|
||||
wsProxy.Transport = transport
|
||||
|
||||
return wsProxy
|
||||
}
|
||||
|
||||
+33
-14
@@ -3,7 +3,6 @@ package upstream
|
||||
import (
|
||||
"bytes"
|
||||
"crypto"
|
||||
"crypto/tls"
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"net/http"
|
||||
@@ -23,9 +22,8 @@ import (
|
||||
)
|
||||
|
||||
var _ = Describe("HTTP Upstream Suite", func() {
|
||||
|
||||
const flushInterval5s = options.Duration(5 * time.Second)
|
||||
const flushInterval1s = options.Duration(1 * time.Second)
|
||||
defaultFlushInterval := options.Duration(options.DefaultUpstreamFlushInterval)
|
||||
defaultTimeout := options.Duration(options.DefaultUpstreamTimeout)
|
||||
truth := true
|
||||
falsum := false
|
||||
|
||||
@@ -62,12 +60,15 @@ var _ = Describe("HTTP Upstream Suite", func() {
|
||||
|
||||
flush := options.Duration(1 * time.Second)
|
||||
|
||||
timeout := options.Duration(options.DefaultUpstreamTimeout)
|
||||
|
||||
upstream := options.Upstream{
|
||||
ID: in.id,
|
||||
PassHostHeader: &in.passUpstreamHostHeader,
|
||||
ProxyWebSockets: &falsum,
|
||||
InsecureSkipTLSVerify: false,
|
||||
FlushInterval: &flush,
|
||||
Timeout: &timeout,
|
||||
}
|
||||
|
||||
Expect(in.serverAddr).ToNot(BeNil())
|
||||
@@ -318,13 +319,13 @@ var _ = Describe("HTTP Upstream Suite", func() {
|
||||
req = middlewareapi.AddRequestScope(req, &middlewareapi.RequestScope{})
|
||||
rw := httptest.NewRecorder()
|
||||
|
||||
flush := options.Duration(1 * time.Second)
|
||||
upstream := options.Upstream{
|
||||
ID: "noPassHost",
|
||||
PassHostHeader: &falsum,
|
||||
ProxyWebSockets: &falsum,
|
||||
InsecureSkipTLSVerify: false,
|
||||
FlushInterval: &flush,
|
||||
FlushInterval: &defaultFlushInterval,
|
||||
Timeout: &defaultTimeout,
|
||||
}
|
||||
|
||||
u, err := url.Parse(serverAddr)
|
||||
@@ -354,6 +355,7 @@ var _ = Describe("HTTP Upstream Suite", func() {
|
||||
skipVerify bool
|
||||
sigData *options.SignatureData
|
||||
errorHandler func(http.ResponseWriter, *http.Request, error)
|
||||
timeout options.Duration
|
||||
}
|
||||
|
||||
DescribeTable("newHTTPUpstreamProxy",
|
||||
@@ -366,6 +368,7 @@ var _ = Describe("HTTP Upstream Suite", func() {
|
||||
FlushInterval: &in.flushInterval,
|
||||
InsecureSkipTLSVerify: in.skipVerify,
|
||||
ProxyWebSockets: &in.proxyWebSockets,
|
||||
Timeout: &in.timeout,
|
||||
}
|
||||
|
||||
handler := newHTTPUpstreamProxy(upstream, u, in.sigData, in.errorHandler)
|
||||
@@ -380,49 +383,63 @@ var _ = Describe("HTTP Upstream Suite", func() {
|
||||
proxy, ok := upstreamProxy.handler.(*httputil.ReverseProxy)
|
||||
Expect(ok).To(BeTrue())
|
||||
Expect(proxy.FlushInterval).To(Equal(in.flushInterval.Duration()))
|
||||
transport, ok := proxy.Transport.(*http.Transport)
|
||||
Expect(ok).To(BeTrue())
|
||||
Expect(transport.ResponseHeaderTimeout).To(Equal(in.timeout.Duration()))
|
||||
Expect(proxy.ErrorHandler != nil).To(Equal(in.errorHandler != nil))
|
||||
if in.skipVerify {
|
||||
Expect(proxy.Transport).To(Equal(&http.Transport{
|
||||
TLSClientConfig: &tls.Config{InsecureSkipVerify: true},
|
||||
}))
|
||||
Expect(transport.TLSClientConfig.InsecureSkipVerify).To(Equal(true))
|
||||
}
|
||||
},
|
||||
Entry("with proxy websockets", &newUpstreamTableInput{
|
||||
proxyWebSockets: true,
|
||||
flushInterval: flushInterval1s,
|
||||
flushInterval: defaultFlushInterval,
|
||||
skipVerify: false,
|
||||
sigData: nil,
|
||||
errorHandler: nil,
|
||||
timeout: defaultTimeout,
|
||||
}),
|
||||
Entry("with a non standard flush interval", &newUpstreamTableInput{
|
||||
proxyWebSockets: false,
|
||||
flushInterval: flushInterval5s,
|
||||
flushInterval: options.Duration(5 * time.Second),
|
||||
skipVerify: false,
|
||||
sigData: nil,
|
||||
errorHandler: nil,
|
||||
timeout: defaultTimeout,
|
||||
}),
|
||||
Entry("with a InsecureSkipTLSVerify", &newUpstreamTableInput{
|
||||
proxyWebSockets: false,
|
||||
flushInterval: flushInterval1s,
|
||||
flushInterval: defaultFlushInterval,
|
||||
skipVerify: true,
|
||||
sigData: nil,
|
||||
errorHandler: nil,
|
||||
timeout: defaultTimeout,
|
||||
}),
|
||||
Entry("with a SignatureData", &newUpstreamTableInput{
|
||||
proxyWebSockets: false,
|
||||
flushInterval: flushInterval1s,
|
||||
flushInterval: defaultFlushInterval,
|
||||
skipVerify: false,
|
||||
sigData: &options.SignatureData{Hash: crypto.SHA256, Key: "secret"},
|
||||
errorHandler: nil,
|
||||
timeout: defaultTimeout,
|
||||
}),
|
||||
Entry("with an error handler", &newUpstreamTableInput{
|
||||
proxyWebSockets: false,
|
||||
flushInterval: flushInterval1s,
|
||||
flushInterval: defaultFlushInterval,
|
||||
skipVerify: false,
|
||||
sigData: nil,
|
||||
errorHandler: func(rw http.ResponseWriter, req *http.Request, arg3 error) {
|
||||
rw.WriteHeader(502)
|
||||
},
|
||||
timeout: defaultTimeout,
|
||||
}),
|
||||
Entry("with a non-default timeout", &newUpstreamTableInput{
|
||||
proxyWebSockets: false,
|
||||
flushInterval: defaultFlushInterval,
|
||||
skipVerify: false,
|
||||
sigData: nil,
|
||||
errorHandler: nil,
|
||||
timeout: options.Duration(5 * time.Second),
|
||||
}),
|
||||
)
|
||||
|
||||
@@ -431,12 +448,14 @@ var _ = Describe("HTTP Upstream Suite", func() {
|
||||
|
||||
BeforeEach(func() {
|
||||
flush := options.Duration(1 * time.Second)
|
||||
timeout := options.Duration(options.DefaultUpstreamTimeout)
|
||||
upstream := options.Upstream{
|
||||
ID: "websocketProxy",
|
||||
PassHostHeader: &truth,
|
||||
ProxyWebSockets: &truth,
|
||||
InsecureSkipTLSVerify: false,
|
||||
FlushInterval: &flush,
|
||||
Timeout: &timeout,
|
||||
}
|
||||
|
||||
u, err := url.Parse(serverAddr)
|
||||
|
||||
Reference in New Issue
Block a user