From 9a14186a26cb7a12e51d39ed3a10ff0299d5e354 Mon Sep 17 00:00:00 2001 From: Jan Larwig Date: Mon, 8 Jun 2026 12:54:40 +0200 Subject: [PATCH 1/2] chore(goconsts): use proper constants for http methods Signed-off-by: Jan Larwig --- oauthproxy.go | 4 +- oauthproxy_test.go | 150 +++++++++---------- pkg/apis/options/load.go | 2 +- pkg/authentication/hmacauth/hmacauth_test.go | 2 +- pkg/requests/builder_test.go | 30 ++-- providers/azure.go | 4 +- providers/google.go | 4 +- providers/logingov.go | 3 +- providers/ms_entra_id.go | 3 +- providers/provider_default.go | 3 +- providers/srht.go | 3 +- 11 files changed, 106 insertions(+), 102 deletions(-) diff --git a/oauthproxy.go b/oauthproxy.go index e2357c8d..f8dc5471 100644 --- a/oauthproxy.go +++ b/oauthproxy.go @@ -587,7 +587,7 @@ func (p *OAuthProxy) ErrorPage(rw http.ResponseWriter, req *http.Request, code i // IsAllowedRequest is used to check if auth should be skipped for this request func (p *OAuthProxy) IsAllowedRequest(req *http.Request) bool { - isPreflightRequestAllowed := p.skipAuthPreflight && req.Method == "OPTIONS" + isPreflightRequestAllowed := p.skipAuthPreflight && req.Method == http.MethodOptions return isPreflightRequestAllowed || p.isAllowedRoute(req) || p.isTrustedIP(req) } @@ -669,7 +669,7 @@ func (p *OAuthProxy) SignInPage(rw http.ResponseWriter, req *http.Request, code // ManualSignIn handles basic auth logins to the proxy func (p *OAuthProxy) ManualSignIn(req *http.Request) (string, bool, int) { - if req.Method != "POST" || p.basicAuthValidator == nil { + if req.Method != http.MethodPost || p.basicAuthValidator == nil { return "", false, http.StatusOK } user := req.FormValue("username") diff --git a/oauthproxy_test.go b/oauthproxy_test.go index e1235a4e..b3271e5b 100644 --- a/oauthproxy_test.go +++ b/oauthproxy_test.go @@ -54,7 +54,7 @@ func TestRobotsTxt(t *testing.T) { t.Fatal(err) } rw := httptest.NewRecorder() - req, _ := http.NewRequest("GET", "/robots.txt", nil) + req, _ := http.NewRequest(http.MethodGet, "/robots.txt", nil) proxy.ServeHTTP(rw, req) assert.Equal(t, 200, rw.Code) assert.Equal(t, "User-agent: *\nDisallow: /\n", rw.Body.String()) @@ -241,7 +241,7 @@ func TestBasicAuthPassword(t *testing.T) { // Save the required session rw := httptest.NewRecorder() - req, _ := http.NewRequest("GET", "/", nil) + req, _ := http.NewRequest(http.MethodGet, "/", nil) err = proxy.sessionStore.Save(rw, req, &sessions.SessionState{ Email: emailAddress, }) @@ -250,7 +250,7 @@ func TestBasicAuthPassword(t *testing.T) { // Extract the cookie value to inject into the test request cookie := rw.Header().Values("Set-Cookie")[0] - req, _ = http.NewRequest("GET", "/", nil) + req, _ = http.NewRequest(http.MethodGet, "/", nil) req.Header.Set("Cookie", cookie) rw = httptest.NewRecorder() proxy.ServeHTTP(rw, req) @@ -300,14 +300,14 @@ func TestPassGroupsHeadersWithGroups(t *testing.T) { // Save the required session rw := httptest.NewRecorder() - req, _ := http.NewRequest("GET", "/", nil) + req, _ := http.NewRequest(http.MethodGet, "/", nil) err = proxy.sessionStore.Save(rw, req, session) assert.NoError(t, err) // Extract the cookie value to inject into the test request cookie := rw.Header().Values("Set-Cookie")[0] - req, _ = http.NewRequest("GET", "/", nil) + req, _ = http.NewRequest(http.MethodGet, "/", nil) req.Header.Set("Cookie", cookie) rw = httptest.NewRecorder() proxy.ServeHTTP(rw, req) @@ -457,7 +457,7 @@ func (patTest *PassAccessTokenTest) getEndpointWithCookie(cookie string, endpoin return 0, "" } - req, err := http.NewRequest("GET", endpoint, strings.NewReader("")) + req, err := http.NewRequest(http.MethodGet, endpoint, strings.NewReader("")) if err != nil { return 0, "" } @@ -608,7 +608,7 @@ func NewSignInPageTest(skipProvider bool) (*SignInPageTest, error) { func (sipTest *SignInPageTest) GetEndpoint(endpoint string) (int, string) { rw := httptest.NewRecorder() - req, _ := http.NewRequest("GET", endpoint, strings.NewReader("")) + req, _ := http.NewRequest(http.MethodGet, endpoint, strings.NewReader("")) sipTest.proxy.ServeHTTP(rw, req) return rw.Code, rw.Body.String() } @@ -894,7 +894,7 @@ func NewProcessCookieTest(opts ProcessCookieTestOpts, modifiers ...OptionsModifi // access_token validation. pcTest.proxy.CookieOptions.Refresh = time.Duration(0) pcTest.rw = httptest.NewRecorder() - pcTest.req, _ = http.NewRequest("GET", "/", strings.NewReader("")) + pcTest.req, _ = http.NewRequest(http.MethodGet, "/", strings.NewReader("")) pcTest.validateUser = true return &pcTest, nil } @@ -1027,7 +1027,7 @@ func NewUserInfoEndpointTest() (*ProcessCookieTest, error) { if err != nil { return nil, err } - pcTest.req, _ = http.NewRequest("GET", + pcTest.req, _ = http.NewRequest(http.MethodGet, pcTest.opts.ProxyPrefix+"/userinfo", nil) return pcTest, nil } @@ -1135,7 +1135,7 @@ func NewAuthOnlyEndpointTest(querystring string, modifiers ...OptionsModifier) ( return nil, err } pcTest.req, _ = http.NewRequest( - "GET", + http.MethodGet, fmt.Sprintf("%s/auth%s", pcTest.opts.ProxyPrefix, querystring), nil) return pcTest, nil @@ -1274,7 +1274,7 @@ func TestAuthOnlyEndpointSetXAuthRequestHeaders(t *testing.T) { pcTest.validateUser = true pcTest.rw = httptest.NewRecorder() - pcTest.req, _ = http.NewRequest("GET", + pcTest.req, _ = http.NewRequest(http.MethodGet, pcTest.opts.ProxyPrefix+authOnlyPath, nil) created := time.Now() @@ -1367,7 +1367,7 @@ func TestAuthOnlyEndpointSetBasicAuthTrueRequestHeaders(t *testing.T) { pcTest.validateUser = true pcTest.rw = httptest.NewRecorder() - pcTest.req, _ = http.NewRequest("GET", + pcTest.req, _ = http.NewRequest(http.MethodGet, pcTest.opts.ProxyPrefix+authOnlyPath, nil) created := time.Now() @@ -1447,7 +1447,7 @@ func TestAuthOnlyEndpointSetBasicAuthFalseRequestHeaders(t *testing.T) { pcTest.validateUser = true pcTest.rw = httptest.NewRecorder() - pcTest.req, _ = http.NewRequest("GET", + pcTest.req, _ = http.NewRequest(http.MethodGet, pcTest.opts.ProxyPrefix+authOnlyPath, nil) created := time.Now() @@ -1495,7 +1495,7 @@ func TestAuthSkippedForPreflightRequests(t *testing.T) { } proxy.provider = NewTestProvider(upstreamURL, "") rw := httptest.NewRecorder() - req, _ := http.NewRequest("OPTIONS", "/preflight-request", nil) + req, _ := http.NewRequest(http.MethodOptions, "/preflight-request", nil) proxy.ServeHTTP(rw, req) assert.Equal(t, 200, rw.Code) @@ -1652,19 +1652,19 @@ func TestRequestSignature(t *testing.T) { resp string }{ "No request signature": { - method: "GET", + method: http.MethodGet, body: "", key: "", resp: "no signature received", }, "Get request": { - method: "GET", + method: http.MethodGet, body: "", key: "7d9e1aa87a5954e6f9fc59266b3af9d7c35fda2d", resp: "signatures match", }, "Post request": { - method: "POST", + method: http.MethodPost, body: `{ "hello": "world!" }`, key: "d90df39e2d19282840252612dd7c81421a372f61", resp: "signatures match", @@ -2189,7 +2189,7 @@ func TestTrustedIPs(t *testing.T) { reverseProxy: false, realClientIPHeader: "X-Real-IP", // Default value req: func() *http.Request { - req, _ := http.NewRequest("GET", "/", nil) + req, _ := http.NewRequest(http.MethodGet, "/", nil) return req }(), expectTrusted: false, @@ -2201,7 +2201,7 @@ func TestTrustedIPs(t *testing.T) { reverseProxy: false, realClientIPHeader: "X-Real-IP", req: func() *http.Request { - req, _ := http.NewRequest("GET", "/", nil) + req, _ := http.NewRequest(http.MethodGet, "/", nil) req.RemoteAddr = "@" return req }(), @@ -2214,7 +2214,7 @@ func TestTrustedIPs(t *testing.T) { reverseProxy: false, realClientIPHeader: "X-Real-IP", req: func() *http.Request { - req, _ := http.NewRequest("GET", "/", nil) + req, _ := http.NewRequest(http.MethodGet, "/", nil) req.RemoteAddr = "@" return req }(), @@ -2227,7 +2227,7 @@ func TestTrustedIPs(t *testing.T) { reverseProxy: false, realClientIPHeader: "X-Real-IP", // Default value req: func() *http.Request { - req, _ := http.NewRequest("GET", "/", nil) + req, _ := http.NewRequest(http.MethodGet, "/", nil) req.RemoteAddr = "127.0.0.1:43670" return req }(), @@ -2240,7 +2240,7 @@ func TestTrustedIPs(t *testing.T) { reverseProxy: true, realClientIPHeader: "X-Real-IP", // Default value req: func() *http.Request { - req, _ := http.NewRequest("GET", "/", nil) + req, _ := http.NewRequest(http.MethodGet, "/", nil) req.RemoteAddr = "127.0.0.1:44324" return req }(), @@ -2253,7 +2253,7 @@ func TestTrustedIPs(t *testing.T) { reverseProxy: true, realClientIPHeader: "X-Forwarded-For", req: func() *http.Request { - req, _ := http.NewRequest("GET", "/", nil) + req, _ := http.NewRequest(http.MethodGet, "/", nil) req.Header.Add("X-Forwarded-For", "127.0.0.1") return req }(), @@ -2266,7 +2266,7 @@ func TestTrustedIPs(t *testing.T) { reverseProxy: true, realClientIPHeader: "X-Forwarded-For", req: func() *http.Request { - req, _ := http.NewRequest("GET", "/", nil) + req, _ := http.NewRequest(http.MethodGet, "/", nil) req.Header.Add("X-Forwarded-For", "::1") return req }(), @@ -2279,7 +2279,7 @@ func TestTrustedIPs(t *testing.T) { reverseProxy: true, realClientIPHeader: "X-Forwarded-For", req: func() *http.Request { - req, _ := http.NewRequest("GET", "/", nil) + req, _ := http.NewRequest(http.MethodGet, "/", nil) req.Header.Add("X-Forwarded-For", "12.34.56.78") return req }(), @@ -2292,7 +2292,7 @@ func TestTrustedIPs(t *testing.T) { reverseProxy: true, realClientIPHeader: "X-Forwarded-For", req: func() *http.Request { - req, _ := http.NewRequest("GET", "/", nil) + req, _ := http.NewRequest(http.MethodGet, "/", nil) req.Header.Add("X-Forwarded-For", "::2") return req }(), @@ -2305,7 +2305,7 @@ func TestTrustedIPs(t *testing.T) { reverseProxy: true, realClientIPHeader: "X-Forwarded-For", req: func() *http.Request { - req, _ := http.NewRequest("GET", "/", nil) + req, _ := http.NewRequest(http.MethodGet, "/", nil) req.Header.Add("X-Real-IP", "::1") return req }(), @@ -2318,7 +2318,7 @@ func TestTrustedIPs(t *testing.T) { reverseProxy: true, realClientIPHeader: "X-Forwarded-For", req: func() *http.Request { - req, _ := http.NewRequest("GET", "/", nil) + req, _ := http.NewRequest(http.MethodGet, "/", nil) req.Header.Add("X-Forwarded-For", "adsfljk29242as!!") return req }(), @@ -2331,7 +2331,7 @@ func TestTrustedIPs(t *testing.T) { reverseProxy: false, realClientIPHeader: "X-Real-IP", req: func() *http.Request { - req, _ := http.NewRequest("GET", "/", nil) + req, _ := http.NewRequest(http.MethodGet, "/", nil) req.RemoteAddr = "adsfljk29242as!!" return req }(), @@ -2427,12 +2427,12 @@ func Test_buildRoutesAllowlist(t *testing.T) { }, expectedRoutes: []expectedAllowedRoute{ { - method: "GET", + method: http.MethodGet, negate: false, regexString: "^/foo/bar", }, { - method: "POST", + method: http.MethodPost, negate: false, regexString: "^/baz/[0-9]+/thing", }, @@ -2485,11 +2485,11 @@ func Test_buildRoutesAllowlist(t *testing.T) { regexString: "^/baz/[0-9]+/thing/regex", }, { - method: "GET", + method: http.MethodGet, regexString: "^/foo/bar", }, { - method: "POST", + method: http.MethodPost, regexString: "^/baz/[0-9]+/thing", }, { @@ -2641,7 +2641,7 @@ func TestApiRoutes(t *testing.T) { for _, tc := range testCases { t.Run(tc.name, func(t *testing.T) { - req, err := http.NewRequest("GET", tc.url, nil) + req, err := http.NewRequest(http.MethodGet, tc.url, nil) req.Header.Set("Accept", tc.contentType) assert.NoError(t, err) @@ -2700,37 +2700,37 @@ func TestAllowedRequest(t *testing.T) { }{ { name: "Regex GET allowed", - method: "GET", + method: http.MethodGet, url: "/skip/auth/regex", allowed: true, }, { name: "Regex POST allowed ", - method: "POST", + method: http.MethodPost, url: "/skip/auth/regex", allowed: true, }, { name: "Regex denied", - method: "GET", + method: http.MethodGet, url: "/wrong/denied", allowed: false, }, { name: "Regex allowed with fragment-free path", - method: "GET", + method: http.MethodGet, url: "/public/legit/endpoint", allowed: true, }, { name: "Regex denied when path contains encoded fragment suffix", - method: "GET", + method: http.MethodGet, url: "/public/secret%23/endpoint", allowed: false, }, { name: "Route allowed", - method: "GET", + method: http.MethodGet, url: "/skip/auth/routes/get", allowed: true, }, @@ -2742,25 +2742,25 @@ func TestAllowedRequest(t *testing.T) { }, { name: "Route denied with wrong path", - method: "GET", + method: http.MethodGet, url: "/skip/auth/routes/wrong/path", allowed: false, }, { name: "Route denied with wrong path and method", - method: "POST", + method: http.MethodPost, url: "/skip/auth/routes/wrong/path", allowed: false, }, { name: "Route allowed with fragment-free path", - method: "GET", + method: http.MethodGet, url: "/foo/public/bar", allowed: true, }, { name: "Route denied when path contains encoded fragment suffix", - method: "GET", + method: http.MethodGet, url: "/foo/secret%23/bar", allowed: false, }, @@ -2825,37 +2825,37 @@ func TestAllowedRequestWithForwardedUriHeader(t *testing.T) { }{ { name: "Regex GET allowed", - method: "GET", + method: http.MethodGet, url: "/skip/auth/regex", allowed: true, }, { name: "Regex POST allowed ", - method: "POST", + method: http.MethodPost, url: "/skip/auth/regex", allowed: true, }, { name: "Regex denied", - method: "GET", + method: http.MethodGet, url: "/wrong/denied", allowed: false, }, { name: "Regex allowed with fragment-free path", - method: "GET", + method: http.MethodGet, url: "/public/legit/endpoint", allowed: true, }, { name: "Regex denied when X-Forwarded-Uri contains an encoded fragment suffix", - method: "GET", + method: http.MethodGet, url: "/public/secret%23/endpoint", allowed: false, }, { name: "Route allowed", - method: "GET", + method: http.MethodGet, url: "/skip/auth/routes/get", allowed: true, }, @@ -2867,25 +2867,25 @@ func TestAllowedRequestWithForwardedUriHeader(t *testing.T) { }, { name: "Route denied with wrong path", - method: "GET", + method: http.MethodGet, url: "/skip/auth/routes/wrong/path", allowed: false, }, { name: "Route denied with wrong path and method", - method: "POST", + method: http.MethodPost, url: "/skip/auth/routes/wrong/path", allowed: false, }, { name: "Route allowed with fragment-free path", - method: "GET", + method: http.MethodGet, url: "/foo/public/bar", allowed: true, }, { name: "Route denied when X-Forwarded-Uri contains an encoded fragment suffix", - method: "GET", + method: http.MethodGet, url: "/foo/secret%23/bar", allowed: false, }, @@ -2986,37 +2986,37 @@ func TestAllowedRequestNegateWithoutMethod(t *testing.T) { }{ { name: "Some static file allowed", - method: "GET", + method: http.MethodGet, url: "/static/file.txt", allowed: true, }, { name: "POST to contact form allowed", - method: "POST", + method: http.MethodPost, url: "/contact", allowed: true, }, { name: "Regex POST allowed", - method: "POST", + method: http.MethodPost, url: "/api/public-entity", allowed: true, }, { name: "Regex POST with trailing slash allowed", - method: "POST", + method: http.MethodPost, url: "/api/public-entity/", allowed: true, }, { name: "Regex GET api route denied", - method: "GET", + method: http.MethodGet, url: "/api/users", allowed: false, }, { name: "Regex POST api route denied", - method: "POST", + method: http.MethodPost, url: "/api/users", allowed: false, }, @@ -3086,37 +3086,37 @@ func TestAllowedRequestNegateWithMethod(t *testing.T) { }{ { name: "Some static file allowed", - method: "GET", + method: http.MethodGet, url: "/static/file.txt", allowed: true, }, { name: "POST to contact form not allowed", - method: "POST", + method: http.MethodPost, url: "/contact", allowed: false, }, { name: "Regex POST allowed", - method: "POST", + method: http.MethodPost, url: "/api/public-entity", allowed: true, }, { name: "Regex POST with trailing slash allowed", - method: "POST", + method: http.MethodPost, url: "/api/public-entity/", allowed: true, }, { name: "Regex GET api route denied", - method: "GET", + method: http.MethodGet, url: "/api/users", allowed: false, }, { name: "Regex POST api route denied", - method: "POST", + method: http.MethodPost, url: "/api/users", allowed: false, }, @@ -3256,7 +3256,7 @@ func TestProxyAllowedGroups(t *testing.T) { t.Fatal(err) } - test.req, _ = http.NewRequest("GET", fmt.Sprintf("/%s", tt.querystring), nil) + test.req, _ = http.NewRequest(http.MethodGet, fmt.Sprintf("/%s", tt.querystring), nil) test.req.Header.Add("accept", applicationJSON) err = test.SaveSession(session) @@ -3400,7 +3400,7 @@ func TestAuthOnlyAllowedGroupsWithSkipMethods(t *testing.T) { { name: "UserWithGroupSkipAuthPreflight", groups: []string{"a", "c"}, - method: "OPTIONS", + method: http.MethodOptions, ip: "1.2.3.5:43670", withSession: true, expectedStatusCode: http.StatusAccepted, @@ -3408,7 +3408,7 @@ func TestAuthOnlyAllowedGroupsWithSkipMethods(t *testing.T) { { name: "UserWithGroupTrustedIp", groups: []string{"a", "c"}, - method: "GET", + method: http.MethodGet, ip: "1.2.3.4:43670", withSession: true, expectedStatusCode: http.StatusAccepted, @@ -3416,7 +3416,7 @@ func TestAuthOnlyAllowedGroupsWithSkipMethods(t *testing.T) { { name: "UserWithoutGroupSkipAuthPreflight", groups: []string{"c"}, - method: "OPTIONS", + method: http.MethodOptions, ip: "1.2.3.5:43670", withSession: true, expectedStatusCode: http.StatusForbidden, @@ -3424,21 +3424,21 @@ func TestAuthOnlyAllowedGroupsWithSkipMethods(t *testing.T) { { name: "UserWithoutGroupTrustedIp", groups: []string{"c"}, - method: "GET", + method: http.MethodGet, ip: "1.2.3.4:43670", withSession: true, expectedStatusCode: http.StatusForbidden, }, { name: "UserWithoutSessionSkipAuthPreflight", - method: "OPTIONS", + method: http.MethodOptions, ip: "1.2.3.5:43670", withSession: false, expectedStatusCode: http.StatusAccepted, }, { name: "UserWithoutSessionTrustedIp", - method: "GET", + method: http.MethodGet, ip: "1.2.3.4:43670", withSession: false, expectedStatusCode: http.StatusAccepted, @@ -3790,14 +3790,14 @@ func TestIdTokenPlaceholderInSignOut(t *testing.T) { // Save the required session rw := httptest.NewRecorder() - req, _ := http.NewRequest("GET", "/", nil) + req, _ := http.NewRequest(http.MethodGet, "/", nil) err = proxy.sessionStore.Save(rw, req, session) assert.NoError(t, err) rw = httptest.NewRecorder() rdUrl := url.QueryEscape("https://my-oidc-provider.example.com/sign_out_page?id_token_hint={id_token}&post_logout_redirect_uri=https://my-app.example.com/") - req, _ = http.NewRequest("GET", "/oauth2/sign_out?rd="+rdUrl, nil) + req, _ = http.NewRequest(http.MethodGet, "/oauth2/sign_out?rd="+rdUrl, nil) req = middlewareapi.AddRequestScope(req, &middlewareapi.RequestScope{ RequestID: "11111111-2222-4333-8444-555555555555", Session: session, diff --git a/pkg/apis/options/load.go b/pkg/apis/options/load.go index d0dd22df..f5b300b0 100644 --- a/pkg/apis/options/load.go +++ b/pkg/apis/options/load.go @@ -145,7 +145,7 @@ func loadAndSubstituteEnvs(configFileName string) ([]byte, error) { func registerFlags(v *viper.Viper, prefix string, flagSet *pflag.FlagSet, options interface{}) error { val := reflect.ValueOf(options) var typ reflect.Type - if val.Kind() == reflect.Ptr { + if val.Kind() == reflect.Pointer { typ = val.Elem().Type() } else { typ = val.Type() diff --git a/pkg/authentication/hmacauth/hmacauth_test.go b/pkg/authentication/hmacauth/hmacauth_test.go index 84f257d9..00cce008 100644 --- a/pkg/authentication/hmacauth/hmacauth_test.go +++ b/pkg/authentication/hmacauth/hmacauth_test.go @@ -286,7 +286,7 @@ func TestSendAuthenticatedPostRequestToServer(t *testing.T) { upstream := httptest.NewServer( http.HandlerFunc(authenticator.Authenticate)) - req, err := http.NewRequest("POST", upstream.URL+"/foo/bar", + req, err := http.NewRequest(http.MethodPost, upstream.URL+"/foo/bar", io.NopCloser(&fakeNetConn{reqBody: payload})) if err != nil { panic(err) diff --git a/pkg/requests/builder_test.go b/pkg/requests/builder_test.go index fc12209f..4fd85f5f 100644 --- a/pkg/requests/builder_test.go +++ b/pkg/requests/builder_test.go @@ -31,7 +31,7 @@ var _ = Describe("Builder suite", func() { Context("with a basic request", func() { assertSuccessfulRequest(getBuilder, testHTTPRequest{ - Method: "GET", + Method: http.MethodGet, Header: baseHeaders, Body: []byte{}, RequestURI: "/json/path", @@ -52,7 +52,7 @@ var _ = Describe("Builder suite", func() { }) assertSuccessfulRequest(getBuilder, testHTTPRequest{ - Method: "GET", + Method: http.MethodGet, Header: baseHeaders, Body: []byte{}, RequestURI: "/json/path", @@ -78,7 +78,7 @@ var _ = Describe("Builder suite", func() { }) assertSuccessfulRequest(getBuilder, testHTTPRequest{ - Method: "GET", + Method: http.MethodGet, Header: header, Body: []byte(body), RequestURI: "/json/path", @@ -93,11 +93,11 @@ var _ = Describe("Builder suite", func() { BeforeEach(func() { buf := bytes.NewBuffer([]byte(body)) - b = b.WithMethod("POST").WithBody(buf) + b = b.WithMethod(http.MethodPost).WithBody(buf) }) assertSuccessfulRequest(getBuilder, testHTTPRequest{ - Method: "POST", + Method: http.MethodPost, Header: header, Body: []byte(body), RequestURI: "/json/path", @@ -109,11 +109,11 @@ var _ = Describe("Builder suite", func() { header.Set("Content-Length", "0") BeforeEach(func() { - b = b.WithMethod("POST") + b = b.WithMethod(http.MethodPost) }) assertSuccessfulRequest(getBuilder, testHTTPRequest{ - Method: "POST", + Method: http.MethodPost, Header: header, Body: []byte{}, RequestURI: "/json/path", @@ -122,11 +122,11 @@ var _ = Describe("Builder suite", func() { Context("OPTIONS", func() { BeforeEach(func() { - b = b.WithMethod("OPTIONS") + b = b.WithMethod(http.MethodOptions) }) assertSuccessfulRequest(getBuilder, testHTTPRequest{ - Method: "OPTIONS", + Method: http.MethodOptions, Header: baseHeaders, Body: []byte{}, RequestURI: "/json/path", @@ -152,7 +152,7 @@ var _ = Describe("Builder suite", func() { }) assertSuccessfulRequest(getBuilder, testHTTPRequest{ - Method: "GET", + Method: http.MethodGet, Header: header, Body: []byte{}, RequestURI: "/json/path", @@ -170,7 +170,7 @@ var _ = Describe("Builder suite", func() { }) assertSuccessfulRequest(getBuilder, testHTTPRequest{ - Method: "GET", + Method: http.MethodGet, Header: replacementHeaders, Body: []byte{}, RequestURI: "/json/path", @@ -190,7 +190,7 @@ var _ = Describe("Builder suite", func() { }) assertSuccessfulRequest(getBuilder, testHTTPRequest{ - Method: "GET", + Method: http.MethodGet, Header: replacementHeaders, Body: []byte{}, RequestURI: "/json/path", @@ -205,7 +205,7 @@ var _ = Describe("Builder suite", func() { }) assertSuccessfulRequest(getBuilder, testHTTPRequest{ - Method: "GET", + Method: http.MethodGet, Header: header, Body: []byte{}, RequestURI: "/json/path", @@ -219,12 +219,12 @@ var _ = Describe("Builder suite", func() { result := b.Do() Expect(result.Error()).ToNot(HaveOccurred()) - b.WithMethod("POST") + b.WithMethod(http.MethodPost) }) Context("should not redo the request", func() { assertSuccessfulRequest(getBuilder, testHTTPRequest{ - Method: "GET", + Method: http.MethodGet, Header: baseHeaders, Body: []byte{}, RequestURI: "/json/path", diff --git a/providers/azure.go b/providers/azure.go index b5610cfa..ff22ebc3 100644 --- a/providers/azure.go +++ b/providers/azure.go @@ -166,7 +166,7 @@ func (p *AzureProvider) Redeem(ctx context.Context, redirectURL, code, codeVerif err = requests.New(p.RedeemURL.String()). WithContext(ctx). - WithMethod("POST"). + WithMethod(http.MethodPost). WithBody(bytes.NewBufferString(params.Encode())). SetHeader("Content-Type", "application/x-www-form-urlencoded"). Do(). @@ -334,7 +334,7 @@ func (p *AzureProvider) redeemRefreshToken(ctx context.Context, s *sessions.Sess err = requests.New(p.RedeemURL.String()). WithContext(ctx). - WithMethod("POST"). + WithMethod(http.MethodPost). WithBody(bytes.NewBufferString(params.Encode())). SetHeader("Content-Type", "application/x-www-form-urlencoded"). Do(). diff --git a/providers/google.go b/providers/google.go index d8e4dec8..d28fb62d 100644 --- a/providers/google.go +++ b/providers/google.go @@ -219,7 +219,7 @@ func (p *GoogleProvider) Redeem(ctx context.Context, redirectURL, code, codeVeri err = requests.New(p.RedeemURL.String()). WithContext(ctx). - WithMethod("POST"). + WithMethod(http.MethodPost). WithBody(bytes.NewBufferString(params.Encode())). SetHeader("Content-Type", "application/x-www-form-urlencoded"). Do(). @@ -543,7 +543,7 @@ func (p *GoogleProvider) redeemRefreshToken(ctx context.Context, s *sessions.Ses err = requests.New(p.RedeemURL.String()). WithContext(ctx). - WithMethod("POST"). + WithMethod(http.MethodPost). WithBody(bytes.NewBufferString(params.Encode())). SetHeader("Content-Type", "application/x-www-form-urlencoded"). Do(). diff --git a/providers/logingov.go b/providers/logingov.go index eb848218..e80989f4 100644 --- a/providers/logingov.go +++ b/providers/logingov.go @@ -8,6 +8,7 @@ import ( "errors" "fmt" "math/big" + "net/http" "net/url" "os" "time" @@ -237,7 +238,7 @@ func (p *LoginGovProvider) Redeem(ctx context.Context, _, code, codeVerifier str } err = requests.New(p.RedeemURL.String()). WithContext(ctx). - WithMethod("POST"). + WithMethod(http.MethodPost). WithBody(bytes.NewBufferString(params.Encode())). SetHeader("Content-Type", "application/x-www-form-urlencoded"). Do(). diff --git a/providers/ms_entra_id.go b/providers/ms_entra_id.go index f30176fd..97a18e48 100644 --- a/providers/ms_entra_id.go +++ b/providers/ms_entra_id.go @@ -5,6 +5,7 @@ import ( "context" "encoding/json" "fmt" + "net/http" "net/url" "os" "regexp" @@ -304,7 +305,7 @@ func (p *MicrosoftEntraIDProvider) checkTenantMatchesTenantList(tenant string, a func (p *MicrosoftEntraIDProvider) fetchToken(ctx context.Context, params url.Values) (*oauth2.Token, error) { resp := requests.New(p.RedeemURL.String()). WithContext(ctx). - WithMethod("POST"). + WithMethod(http.MethodPost). WithBody(bytes.NewBufferString(params.Encode())). SetHeader("Content-Type", "application/x-www-form-urlencoded"). Do() diff --git a/providers/provider_default.go b/providers/provider_default.go index dbd93c91..8db79b54 100644 --- a/providers/provider_default.go +++ b/providers/provider_default.go @@ -5,6 +5,7 @@ import ( "context" "errors" "fmt" + "net/http" "net/url" "github.com/oauth2-proxy/oauth2-proxy/v7/pkg/apis/middleware" @@ -71,7 +72,7 @@ func (p *ProviderData) Redeem(ctx context.Context, redirectURL, code, codeVerifi result := requests.New(p.RedeemURL.String()). WithContext(ctx). - WithMethod("POST"). + WithMethod(http.MethodPost). WithBody(bytes.NewBufferString(params.Encode())). SetHeader("Content-Type", "application/x-www-form-urlencoded"). Do() diff --git a/providers/srht.go b/providers/srht.go index aa72229c..e927629e 100644 --- a/providers/srht.go +++ b/providers/srht.go @@ -4,6 +4,7 @@ import ( "bytes" "context" "fmt" + "net/http" "net/url" "github.com/oauth2-proxy/oauth2-proxy/v7/pkg/apis/sessions" @@ -75,7 +76,7 @@ func NewSourceHutProvider(p *ProviderData) *SourceHutProvider { func (p *SourceHutProvider) EnrichSession(ctx context.Context, s *sessions.SessionState) error { json, err := requests.New(p.ProfileURL.String()). WithContext(ctx). - WithMethod("POST"). + WithMethod(http.MethodPost). SetHeader("Content-Type", "application/json"). SetHeader("Authorization", "Bearer "+s.AccessToken). WithBody(bytes.NewBufferString(`{"query": "{ me { username, email } }"}`)). From 0de18825f64ddd37dd6795c33fef69487e9f9868 Mon Sep 17 00:00:00 2001 From: Jan Larwig Date: Mon, 8 Jun 2026 13:57:21 +0200 Subject: [PATCH 2/2] chore(deps): bump Go to 1.26 and migrate upstream reverse proxies to Rewrite Signed-off-by: Jan Larwig --- .devcontainer/Dockerfile | 2 +- CHANGELOG.md | 2 + go.mod | 60 +++++++++++------------ go.sum | 62 ++++++++++++++++++++++++ pkg/upstream/http.go | 75 ++++++++++++++++++++++------- pkg/upstream/http_test.go | 56 ++++++++++++++++++++- pkg/upstream/proxy_test.go | 2 +- pkg/upstream/upstream_suite_test.go | 2 +- pkg/validation/sessions_test.go | 4 +- 9 files changed, 211 insertions(+), 54 deletions(-) diff --git a/.devcontainer/Dockerfile b/.devcontainer/Dockerfile index 7b6d5bba..022c919c 100644 --- a/.devcontainer/Dockerfile +++ b/.devcontainer/Dockerfile @@ -1,4 +1,4 @@ -FROM mcr.microsoft.com/vscode/devcontainers/go:1-1.25 +FROM mcr.microsoft.com/vscode/devcontainers/go:1-1.26 SHELL ["/bin/bash", "-o", "pipefail", "-c"] diff --git a/CHANGELOG.md b/CHANGELOG.md index 320ba697..21addc80 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -8,6 +8,8 @@ ## Changes since v7.15.2 +- [#3477](https://github.com/oauth2-proxy/oauth2-proxy/pull/3477) chore(dep): bump go to 1.26 and migrate of reverse proxy handling + # V7.15.2 ## Release Highlights diff --git a/go.mod b/go.mod index ade9c4e8..fba46d82 100644 --- a/go.mod +++ b/go.mod @@ -1,17 +1,17 @@ module github.com/oauth2-proxy/oauth2-proxy/v7 -go 1.25.0 +go 1.26.0 require ( cloud.google.com/go/compute/metadata v0.9.0 github.com/Bose/minisentinel v0.0.0-20200130220412-917c5a9223bb github.com/a8m/envsubst v1.4.3 - github.com/alicebob/miniredis/v2 v2.37.0 + github.com/alicebob/miniredis/v2 v2.38.0 github.com/bitly/go-simplejson v0.5.1 - github.com/bsm/redislock v0.9.4 + github.com/bsm/redislock v0.10.0 github.com/coreos/go-oidc/v3 v3.18.0 github.com/coreos/go-systemd v0.0.0-20191104093116-d3cd4ed1dbcf - github.com/fsnotify/fsnotify v1.9.0 + github.com/fsnotify/fsnotify v1.10.1 github.com/go-jose/go-jose/v3 v3.0.5 github.com/go-jose/go-jose/v4 v4.1.4 github.com/go-viper/mapstructure/v2 v2.5.0 @@ -21,30 +21,30 @@ require ( github.com/gorilla/mux v1.8.1 github.com/justinas/alice v1.2.0 github.com/oauth2-proxy/mockoidc v0.0.0-20240214162133-caebfff84d25 - github.com/onsi/ginkgo/v2 v2.28.1 - github.com/onsi/gomega v1.39.1 - github.com/pierrec/lz4/v4 v4.1.26 + github.com/onsi/ginkgo/v2 v2.29.0 + github.com/onsi/gomega v1.41.0 + github.com/pierrec/lz4/v4 v4.1.27 github.com/prometheus/client_golang v1.23.2 - github.com/redis/go-redis/v9 v9.18.0 + github.com/redis/go-redis/v9 v9.20.0 github.com/spf13/cast v1.10.0 github.com/spf13/pflag v1.0.10 github.com/spf13/viper v1.21.0 github.com/stretchr/testify v1.11.1 github.com/vmihailenco/msgpack/v5 v5.4.1 go.yaml.in/yaml/v3 v3.0.4 - golang.org/x/crypto v0.50.0 - golang.org/x/net v0.53.0 + golang.org/x/crypto v0.52.0 + golang.org/x/net v0.55.0 golang.org/x/oauth2 v0.36.0 golang.org/x/sync v0.20.0 - google.golang.org/api v0.275.0 + google.golang.org/api v0.283.0 gopkg.in/natefinch/lumberjack.v2 v2.2.1 - k8s.io/apimachinery v0.35.3 + k8s.io/apimachinery v0.36.1 ) require ( cloud.google.com/go/auth v0.20.0 // indirect cloud.google.com/go/auth/oauth2adapt v0.2.8 // indirect - github.com/Masterminds/semver/v3 v3.4.0 // indirect + github.com/Masterminds/semver/v3 v3.5.0 // indirect github.com/beorn7/perks v1.0.1 // indirect github.com/cespare/xxhash/v2 v2.3.0 // indirect github.com/davecgh/go-spew v1.1.2-0.20180830191138-d8f796af33cc // indirect @@ -53,35 +53,35 @@ require ( github.com/go-logr/logr v1.4.3 // indirect github.com/go-logr/stdr v1.2.2 // indirect github.com/go-task/slim-sprig/v3 v3.0.0 // indirect - github.com/google/pprof v0.0.0-20260402051712-545e8a4df936 // indirect + github.com/google/pprof v0.0.0-20260604005048-7023385849c0 // indirect github.com/google/s2a-go v0.1.9 // indirect - github.com/googleapis/enterprise-certificate-proxy v0.3.14 // indirect - github.com/googleapis/gax-go/v2 v2.21.0 // indirect + github.com/googleapis/enterprise-certificate-proxy v0.3.16 // indirect + github.com/googleapis/gax-go/v2 v2.22.0 // indirect github.com/kylelemons/godebug v1.1.0 // indirect github.com/munnerz/goautoneg v0.0.0-20191010083416-a7dc8b61c822 // indirect - github.com/pelletier/go-toml/v2 v2.3.0 // indirect + github.com/pelletier/go-toml/v2 v2.3.1 // indirect github.com/pmezard/go-difflib v1.0.1-0.20181226105442-5d4384ee4fb2 // indirect github.com/prometheus/client_model v0.6.2 // indirect - github.com/prometheus/common v0.67.5 // indirect + github.com/prometheus/common v0.68.1 // indirect github.com/prometheus/procfs v0.20.1 // indirect github.com/sagikazarmark/locafero v0.12.0 // indirect github.com/spf13/afero v1.15.0 // indirect github.com/subosito/gotenv v1.6.0 // indirect github.com/vmihailenco/tagparser/v2 v2.0.0 // indirect - github.com/yuin/gopher-lua v1.1.1 // indirect + github.com/yuin/gopher-lua v1.1.2 // indirect go.opentelemetry.io/auto/sdk v1.2.1 // indirect - go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.68.0 // indirect - go.opentelemetry.io/otel v1.43.0 // indirect - go.opentelemetry.io/otel/metric v1.43.0 // indirect - go.opentelemetry.io/otel/trace v1.43.0 // indirect + go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.69.0 // indirect + go.opentelemetry.io/otel v1.44.0 // indirect + go.opentelemetry.io/otel/metric v1.44.0 // indirect + go.opentelemetry.io/otel/trace v1.44.0 // indirect go.uber.org/atomic v1.11.0 // indirect go.yaml.in/yaml/v2 v2.4.4 // indirect - golang.org/x/mod v0.35.0 // indirect - golang.org/x/sys v0.43.0 // indirect - golang.org/x/text v0.36.0 // indirect - golang.org/x/tools v0.44.0 // indirect - google.golang.org/genproto/googleapis/rpc v0.0.0-20260406210006-6f92a3bedf2d // indirect - google.golang.org/grpc v1.80.0 // indirect - google.golang.org/protobuf v1.36.11 // indirect + golang.org/x/mod v0.36.0 // indirect + golang.org/x/sys v0.45.0 // indirect + golang.org/x/text v0.37.0 // indirect + golang.org/x/tools v0.45.0 // indirect + google.golang.org/genproto/googleapis/rpc v0.0.0-20260526163538-3dc84a4a5aaa // indirect + google.golang.org/grpc v1.81.1 // indirect + google.golang.org/protobuf v1.36.12-0.20260120151049-f2248ac996af // indirect gopkg.in/yaml.v3 v3.0.1 // indirect ) diff --git a/go.sum b/go.sum index 622f2dac..5b400463 100644 --- a/go.sum +++ b/go.sum @@ -12,12 +12,16 @@ github.com/FZambia/sentinel v1.0.0 h1:KJ0ryjKTZk5WMp0dXvSdNqp3lFaW1fNFuEYfrkLOYI github.com/FZambia/sentinel v1.0.0/go.mod h1:ytL1Am/RLlAoAXG6Kj5LNuw/TRRQrv2rt2FT26vP5gI= github.com/Masterminds/semver/v3 v3.4.0 h1:Zog+i5UMtVoCU8oKka5P7i9q9HgrJeGzI9SA1Xbatp0= github.com/Masterminds/semver/v3 v3.4.0/go.mod h1:4V+yj/TJE1HU9XfppCwVMZq3I84lprf4nC11bSS5beM= +github.com/Masterminds/semver/v3 v3.5.0 h1:kQceYJfbupGfZOKZQg0kou0DgAKhzDg2NZPAwZ/2OOE= +github.com/Masterminds/semver/v3 v3.5.0/go.mod h1:4V+yj/TJE1HU9XfppCwVMZq3I84lprf4nC11bSS5beM= github.com/a8m/envsubst v1.4.3 h1:kDF7paGK8QACWYaQo6KtyYBozY2jhQrTuNNuUxQkhJY= github.com/a8m/envsubst v1.4.3/go.mod h1:4jjHWQlZoaXPoLQUb7H2qT4iLkZDdmEQiOUogdUmqVU= github.com/alicebob/gopher-json v0.0.0-20180125190556-5a6b3ba71ee6/go.mod h1:SGnFV6hVsYE877CKEZ6tDNTjaSXYUk6QqoIK6PrAtcc= github.com/alicebob/miniredis/v2 v2.11.1/go.mod h1:UA48pmi7aSazcGAvcdKcBB49z521IC9VjTTRz2nIaJE= github.com/alicebob/miniredis/v2 v2.37.0 h1:RheObYW32G1aiJIj81XVt78ZHJpHonHLHW7OLIshq68= github.com/alicebob/miniredis/v2 v2.37.0/go.mod h1:TcL7YfarKPGDAthEtl5NBeHZfeUQj6OXMm/+iu5cLMM= +github.com/alicebob/miniredis/v2 v2.38.0 h1:nZAzCR+Lj+Vxk4ZXzm2NuKq2O33RXj1XxJ2e2uP9jiw= +github.com/alicebob/miniredis/v2 v2.38.0/go.mod h1:TcL7YfarKPGDAthEtl5NBeHZfeUQj6OXMm/+iu5cLMM= github.com/beorn7/perks v1.0.1 h1:VlbKKnNfV8bJzeqoa4cOKqO6bYr3WgKZxO8Z16+hsOM= github.com/beorn7/perks v1.0.1/go.mod h1:G2ZrVWU2WbWT9wwq4/hrbKbnv/1ERSJQ0ibhJ6rlkpw= github.com/bitly/go-simplejson v0.5.1 h1:xgwPbetQScXt1gh9BmoJ6j9JMr3TElvuIyjR8pgdoow= @@ -28,6 +32,8 @@ github.com/bsm/gomega v1.27.10 h1:yeMWxP2pV2fG3FgAODIY8EiRE3dy0aeFYt4l7wh6yKA= github.com/bsm/gomega v1.27.10/go.mod h1:JyEr/xRbxbtgWNi8tIEVPUYZ5Dzef52k01W3YH0H+O0= github.com/bsm/redislock v0.9.4 h1:X/Wse1DPpiQgHbVYRE9zv6m070UcKoOGekgvpNhiSvw= github.com/bsm/redislock v0.9.4/go.mod h1:Epf7AJLiSFwLCiZcfi6pWFO/8eAYrYpQXFxEDPoDeAk= +github.com/bsm/redislock v0.10.0 h1:NAe1OHDnwPmWEzD+LpWBZXAdZrWld/xj/wmqEcQednQ= +github.com/bsm/redislock v0.10.0/go.mod h1:M05WZGjPbX/8ne7LmB7AbOsa2kv7Jzx4fqkLpDFZvJs= github.com/cespare/xxhash/v2 v2.3.0 h1:UL815xU9SqsFlibzuggzjXhog7bL6oX9BbNZnL2UFvs= github.com/cespare/xxhash/v2 v2.3.0/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs= github.com/chzyer/logex v1.1.10/go.mod h1:+Ywpsq7O8HXn0nuIou7OrIPyXbp3wmkHB+jjWRnGsAI= @@ -50,6 +56,8 @@ github.com/frankban/quicktest v1.14.6 h1:7Xjx+VpznH+oBnejlPUj8oUpdxnVs4f8XU8WnHk github.com/frankban/quicktest v1.14.6/go.mod h1:4ptaffx2x8+WTWXmUCuVU6aPUX1/Mz7zb5vbUoiM6w0= github.com/fsnotify/fsnotify v1.9.0 h1:2Ml+OJNzbYCTzsxtv8vKSFD9PbJjmhYF14k/jKC7S9k= github.com/fsnotify/fsnotify v1.9.0/go.mod h1:8jBTzvmWwFyi3Pb8djgCCO5IBqzKJ/Jwo8TRcHyHii0= +github.com/fsnotify/fsnotify v1.10.1 h1:b0/UzAf9yR5rhf3RPm9gf3ehBPpf0oZKIjtpKrx59Ho= +github.com/fsnotify/fsnotify v1.10.1/go.mod h1:TLheqan6HD6GBK6PrDWyDPBaEV8LspOxvPSjC+bVfgo= github.com/gkampitakis/ciinfo v0.3.2 h1:JcuOPk8ZU7nZQjdUhctuhQofk7BGHuIy0c9Ez8BNhXs= github.com/gkampitakis/ciinfo v0.3.2/go.mod h1:1NIwaOcFChN4fa/B0hEBdAb6npDlFL8Bwx4dfRLRqAo= github.com/gkampitakis/go-diff v1.3.2 h1:Qyn0J9XJSDTgnsgHRdz9Zp24RaJeKMUHg2+PDZZdC4M= @@ -88,6 +96,8 @@ github.com/google/pprof v0.0.0-20260302011040-a15ffb7f9dcc h1:VBbFa1lDYWEeV5FZKU github.com/google/pprof v0.0.0-20260302011040-a15ffb7f9dcc/go.mod h1:MxpfABSjhmINe3F1It9d+8exIHFvUqtLIRCdOGNXqiI= github.com/google/pprof v0.0.0-20260402051712-545e8a4df936 h1:EwtI+Al+DeppwYX2oXJCETMO23COyaKGP6fHVpkpWpg= github.com/google/pprof v0.0.0-20260402051712-545e8a4df936/go.mod h1:MxpfABSjhmINe3F1It9d+8exIHFvUqtLIRCdOGNXqiI= +github.com/google/pprof v0.0.0-20260604005048-7023385849c0 h1:h1QTMDl6q9wDvDCJVpKQSjgleGFYnd2fOxmg2K+6BGE= +github.com/google/pprof v0.0.0-20260604005048-7023385849c0/go.mod h1:MxpfABSjhmINe3F1It9d+8exIHFvUqtLIRCdOGNXqiI= github.com/google/s2a-go v0.1.9 h1:LGD7gtMgezd8a/Xak7mEWL0PjoTQFvpRudN895yqKW0= github.com/google/s2a-go v0.1.9/go.mod h1:YA0Ei2ZQL3acow2O62kdp9UlnvMmU7kA6Eutn0dXayM= github.com/google/uuid v1.1.1/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= @@ -95,10 +105,14 @@ github.com/google/uuid v1.6.0 h1:NIvaJDMOsjHA8n1jAhLSgzrAzy1Hgr+hNrb57e+94F0= github.com/google/uuid v1.6.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/googleapis/enterprise-certificate-proxy v0.3.14 h1:yh8ncqsbUY4shRD5dA6RlzjJaT4hi3kII+zYw8wmLb8= github.com/googleapis/enterprise-certificate-proxy v0.3.14/go.mod h1:vqVt9yG9480NtzREnTlmGSBmFrA+bzb0yl0TxoBQXOg= +github.com/googleapis/enterprise-certificate-proxy v0.3.16 h1:F/VPrx0YPBdksZJQdCAp0WUsqnNmZpUZszzfYt0M5Dw= +github.com/googleapis/enterprise-certificate-proxy v0.3.16/go.mod h1:9Yb0eAkH/Xqhvv3zbeKf/+wMJqCeocWc6KIhDvEAuYE= github.com/googleapis/gax-go/v2 v2.19.0 h1:fYQaUOiGwll0cGj7jmHT/0nPlcrZDFPrZRhTsoCr8hE= github.com/googleapis/gax-go/v2 v2.19.0/go.mod h1:w2ROXVdfGEVFXzmlciUU4EdjHgWvB5h2n6x/8XSTTJA= github.com/googleapis/gax-go/v2 v2.21.0 h1:h45NjjzEO3faG9Lg/cFrBh2PgegVVgzqKzuZl/wMbiI= github.com/googleapis/gax-go/v2 v2.21.0/go.mod h1:But/NJU6TnZsrLai/xBAQLLz+Hc7fHZJt/hsCz3Fih4= +github.com/googleapis/gax-go/v2 v2.22.0 h1:PjIWBpgGIVKGoCXuiCoP64altEJCj3/Ei+kSU5vlZD4= +github.com/googleapis/gax-go/v2 v2.22.0/go.mod h1:irWBbALSr0Sk3qlqb9SyJ1h68WjgeFuiOzI4Rqw5+aY= github.com/gorilla/mux v1.8.1 h1:TuBL49tXwgrFYWhqrNgrUNEY92u81SPhu7sTdzQEiWY= github.com/gorilla/mux v1.8.1/go.mod h1:AKf9I4AEqPTmMytcMc0KkNouC66V3BtZ4qD5fmWSiMQ= github.com/joshdk/go-junit v1.0.0 h1:S86cUKIdwBHWwA6xCmFlf3RTLfVXYQfvanM5Uh+K6GE= @@ -109,6 +123,7 @@ github.com/klauspost/compress v1.18.0 h1:c/Cqfb0r+Yi+JtIEq73FWXVkRonBlf0CRNYc8Zt github.com/klauspost/compress v1.18.0/go.mod h1:2Pp+KzxcywXVXMr50+X0Q/Lsb43OQHYWRCY2AiWywWQ= github.com/klauspost/cpuid/v2 v2.0.9 h1:lgaqFMSdTdQYdZ04uHyN2d/eKdOMyi2YLSvlQIBFYa4= github.com/klauspost/cpuid/v2 v2.0.9/go.mod h1:FInQzS24/EEf25PyTYn52gqo7WaD8xa0213Md/qVLRg= +github.com/klauspost/cpuid/v2 v2.2.10 h1:tBs3QSyvjDyFTq3uoc/9xFpCuOsJQFNPiAhYdw2skhE= github.com/kr/pretty v0.3.1 h1:flRD4NNwYAUpkphVc1HcthR4KEIFJ65n8Mw5qdRn3LE= github.com/kr/pretty v0.3.1/go.mod h1:hoEshYVHaxMs3cyo3Yncou5ZscifuDolrwPKZanG3xk= github.com/kr/text v0.2.0 h1:5Nx0Ya0ZqY2ygV366QzturHI13Jq95ApcVaJBhpS+AY= @@ -127,14 +142,22 @@ github.com/oauth2-proxy/mockoidc v0.0.0-20240214162133-caebfff84d25 h1:9bCMuD3Tc github.com/oauth2-proxy/mockoidc v0.0.0-20240214162133-caebfff84d25/go.mod h1:eDjgYHYDJbPLBLsyZ6qRaugP0mX8vePOhZ5id1fdzJw= github.com/onsi/ginkgo/v2 v2.28.1 h1:S4hj+HbZp40fNKuLUQOYLDgZLwNUVn19N3Atb98NCyI= github.com/onsi/ginkgo/v2 v2.28.1/go.mod h1:CLtbVInNckU3/+gC8LzkGUb9oF+e8W8TdUsxPwvdOgE= +github.com/onsi/ginkgo/v2 v2.29.0 h1:rfh+ZFjgJhYWRoIqVf3Uwx/W20yLrcrE2h2GmYVRaag= +github.com/onsi/ginkgo/v2 v2.29.0/go.mod h1:+aXOY+vzZ5mu2iI2HpTZUPmM//oQfsNFX6gU9kNcA44= github.com/onsi/gomega v1.39.1 h1:1IJLAad4zjPn2PsnhH70V4DKRFlrCzGBNrNaru+Vf28= github.com/onsi/gomega v1.39.1/go.mod h1:hL6yVALoTOxeWudERyfppUcZXjMwIMLnuSfruD2lcfg= +github.com/onsi/gomega v1.41.0 h1:OwKp4pXNgVxf6sCplzYo794OFNuoL2q2SBMU5NSWOjA= +github.com/onsi/gomega v1.41.0/go.mod h1:M/Uqpu/8qTjtzCLUA2zJHX9Iilrau25x1PdoSRbWh5A= github.com/pelletier/go-toml/v2 v2.2.4 h1:mye9XuhQ6gvn5h28+VilKrrPoQVanw5PMw/TB0t5Ec4= github.com/pelletier/go-toml/v2 v2.2.4/go.mod h1:2gIqNv+qfxSVS7cM2xJQKtLSTLUE9V8t9Stt+h56mCY= github.com/pelletier/go-toml/v2 v2.3.0 h1:k59bC/lIZREW0/iVaQR8nDHxVq8OVlIzYCOJf421CaM= github.com/pelletier/go-toml/v2 v2.3.0/go.mod h1:2gIqNv+qfxSVS7cM2xJQKtLSTLUE9V8t9Stt+h56mCY= +github.com/pelletier/go-toml/v2 v2.3.1 h1:MYEvvGnQjeNkRF1qUuGolNtNExTDwct51yp7olPtrEc= +github.com/pelletier/go-toml/v2 v2.3.1/go.mod h1:2gIqNv+qfxSVS7cM2xJQKtLSTLUE9V8t9Stt+h56mCY= github.com/pierrec/lz4/v4 v4.1.26 h1:GrpZw1gZttORinvzBdXPUXATeqlJjqUG/D87TKMnhjY= github.com/pierrec/lz4/v4 v4.1.26/go.mod h1:EoQMVJgeeEOMsCqCzqFm2O0cJvljX2nGZjcRIPL34O4= +github.com/pierrec/lz4/v4 v4.1.27 h1:+PhzhWDrjRj89TH2sw43nE3+4+W8lSxIuQadEHZyjUk= +github.com/pierrec/lz4/v4 v4.1.27/go.mod h1:EoQMVJgeeEOMsCqCzqFm2O0cJvljX2nGZjcRIPL34O4= github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= github.com/pmezard/go-difflib v1.0.1-0.20181226105442-5d4384ee4fb2 h1:Jamvg5psRIccs7FGNTlIRMkT8wgtp5eCXdBlqhYGL6U= github.com/pmezard/go-difflib v1.0.1-0.20181226105442-5d4384ee4fb2/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= @@ -144,10 +167,14 @@ github.com/prometheus/client_model v0.6.2 h1:oBsgwpGs7iVziMvrGhE53c/GrLUsZdHnqNw github.com/prometheus/client_model v0.6.2/go.mod h1:y3m2F6Gdpfy6Ut/GBsUqTWZqCUvMVzSfMLjcu6wAwpE= github.com/prometheus/common v0.67.5 h1:pIgK94WWlQt1WLwAC5j2ynLaBRDiinoAb86HZHTUGI4= github.com/prometheus/common v0.67.5/go.mod h1:SjE/0MzDEEAyrdr5Gqc6G+sXI67maCxzaT3A2+HqjUw= +github.com/prometheus/common v0.68.1 h1:omjRRl4QP4komogpXuhfeOiisQg7xdy8VM1UY+pStaY= +github.com/prometheus/common v0.68.1/go.mod h1:ZzL3f6u94qUxh9p+tJTrF+FvBS1XXbbRAZCQkytAL0Y= github.com/prometheus/procfs v0.20.1 h1:XwbrGOIplXW/AU3YhIhLODXMJYyC1isLFfYCsTEycfc= github.com/prometheus/procfs v0.20.1/go.mod h1:o9EMBZGRyvDrSPH1RqdxhojkuXstoe4UlK79eF5TGGo= github.com/redis/go-redis/v9 v9.18.0 h1:pMkxYPkEbMPwRdenAzUNyFNrDgHx9U+DrBabWNfSRQs= github.com/redis/go-redis/v9 v9.18.0/go.mod h1:k3ufPphLU5YXwNTUcCRXGxUoF1fqxnhFQmscfkCoDA0= +github.com/redis/go-redis/v9 v9.20.0 h1:WnQYxLkgO2xiXTCJY0ldIiI8dNqCDlQAG+AtaH7a2a0= +github.com/redis/go-redis/v9 v9.20.0/go.mod h1:v/M13XI1PVCDcm01VtPFOADfZtHf8YW3baQf57KlIkA= github.com/rogpeppe/go-internal v1.14.1 h1:UQB4HGPB6osV0SQTLymcB4TgvyWu6ZyliaW0tI/otEQ= github.com/rogpeppe/go-internal v1.14.1/go.mod h1:MaRKkUm5W0goXpeCfT7UZI6fk/L7L7so1lCWt35ZSgc= github.com/sagikazarmark/locafero v0.12.0 h1:/NQhBAkUb4+fH1jivKHWusDYFjMOOKU88eegjfxfHb4= @@ -183,8 +210,11 @@ github.com/yuin/gopher-lua v0.0.0-20190206043414-8bfc7677f583/go.mod h1:gqRgreBU github.com/yuin/gopher-lua v0.0.0-20191213034115-f46add6fdb5c/go.mod h1:gqRgreBUhTSL0GeU64rtZ3Uq3wtjOa/TB2YfrtkCbVQ= github.com/yuin/gopher-lua v1.1.1 h1:kYKnWBjvbNP4XLT3+bPEwAXJx262OhaHDWDVOPjL46M= github.com/yuin/gopher-lua v1.1.1/go.mod h1:GBR0iDaNXjAgGg9zfCvksxSRnQx76gclCIb7kdAd1Pw= +github.com/yuin/gopher-lua v1.1.2 h1:yF/FjE3hD65tBbt0VXLE13HWS9h34fdzJmrWRXwobGA= +github.com/yuin/gopher-lua v1.1.2/go.mod h1:7aRmXIWl37SqRf0koeyylBEzJ+aPt8A+mmkQ4f1ntR8= github.com/zeebo/xxh3 v1.0.2 h1:xZmwmqxHZA8AI603jOQ0tMqmBr9lPeFwGg6d+xy9DC0= github.com/zeebo/xxh3 v1.0.2/go.mod h1:5NWz9Sef7zIDm2JHfFlcQvNekmcEl9ekUZQQKCYaDcA= +github.com/zeebo/xxh3 v1.1.0 h1:s7DLGDK45Dyfg7++yxI0khrfwq9661w9EN78eP/UZVs= go.opentelemetry.io/auto/sdk v1.2.1 h1:jXsnJ4Lmnqd11kwkBV2LgLoFMZKizbCi5fNZ/ipaZ64= go.opentelemetry.io/auto/sdk v1.2.1/go.mod h1:KRTj+aOaElaLi+wW1kO/DZRXwkF4C5xPbEe3ZiIhN7Y= go.opentelemetry.io/contrib/instrumentation/google.golang.org/grpc/otelgrpc v0.61.0 h1:q4XOmH/0opmeuJtPsbFNivyl7bCt7yRBbeEm2sC/XtQ= @@ -194,24 +224,34 @@ go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.67.0 h1:Oyrsyzu go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.67.0/go.mod h1:C2NGBr+kAB4bk3xtMXfZ94gqFDtg/GkI7e9zqGh5Beg= go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.68.0 h1:CqXxU8VOmDefoh0+ztfGaymYbhdB/tT3zs79QaZTNGY= go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.68.0/go.mod h1:BuhAPThV8PBHBvg8ZzZ/Ok3idOdhWIodywz2xEcRbJo= +go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.69.0 h1:8tvICD4vSTOOsNrsI4Ljf6C+6UKvpTEH5XY3JMoyPoo= +go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.69.0/go.mod h1:z9+yiacE0IHRqM4qFfkbt/JYlmYXgss8GY/jXoNuPJI= go.opentelemetry.io/otel v1.42.0 h1:lSQGzTgVR3+sgJDAU/7/ZMjN9Z+vUip7leaqBKy4sho= go.opentelemetry.io/otel v1.42.0/go.mod h1:lJNsdRMxCUIWuMlVJWzecSMuNjE7dOYyWlqOXWkdqCc= go.opentelemetry.io/otel v1.43.0 h1:mYIM03dnh5zfN7HautFE4ieIig9amkNANT+xcVxAj9I= go.opentelemetry.io/otel v1.43.0/go.mod h1:JuG+u74mvjvcm8vj8pI5XiHy1zDeoCS2LB1spIq7Ay0= +go.opentelemetry.io/otel v1.44.0 h1:JjwHmHpA4iZ3wBxluu2fbbE7j4kqlE8jXyAyPXH7HqU= +go.opentelemetry.io/otel v1.44.0/go.mod h1:BMgjTHL9WPRlRjL2oZCBTL4whCGtXch2H4BhOPIAyYc= go.opentelemetry.io/otel/metric v1.42.0 h1:2jXG+3oZLNXEPfNmnpxKDeZsFI5o4J+nz6xUlaFdF/4= go.opentelemetry.io/otel/metric v1.42.0/go.mod h1:RlUN/7vTU7Ao/diDkEpQpnz3/92J9ko05BIwxYa2SSI= go.opentelemetry.io/otel/metric v1.43.0 h1:d7638QeInOnuwOONPp4JAOGfbCEpYb+K6DVWvdxGzgM= go.opentelemetry.io/otel/metric v1.43.0/go.mod h1:RDnPtIxvqlgO8GRW18W6Z/4P462ldprJtfxHxyKd2PY= +go.opentelemetry.io/otel/metric v1.44.0 h1:1w0gILTcHdr3YI+ixLyjemwrVnsMURbTZFrSYCdDdmc= +go.opentelemetry.io/otel/metric v1.44.0/go.mod h1:8O7hanEPBNgEMmybD3s2VBKcgWOCsA6tzHBPODAiquo= go.opentelemetry.io/otel/sdk v1.42.0 h1:LyC8+jqk6UJwdrI/8VydAq/hvkFKNHZVIWuslJXYsDo= go.opentelemetry.io/otel/sdk v1.42.0/go.mod h1:rGHCAxd9DAph0joO4W6OPwxjNTYWghRWmkHuGbayMts= go.opentelemetry.io/otel/sdk v1.43.0 h1:pi5mE86i5rTeLXqoF/hhiBtUNcrAGHLKQdhg4h4V9Dg= +go.opentelemetry.io/otel/sdk v1.44.0 h1:nHYwb9lK+fJPU/dnT6s7W7Z8itMWyqrnVfbheVYrZ58= go.opentelemetry.io/otel/sdk/metric v1.42.0 h1:D/1QR46Clz6ajyZ3G8SgNlTJKBdGp84q9RKCAZ3YGuA= go.opentelemetry.io/otel/sdk/metric v1.42.0/go.mod h1:Ua6AAlDKdZ7tdvaQKfSmnFTdHx37+J4ba8MwVCYM5hc= go.opentelemetry.io/otel/sdk/metric v1.43.0 h1:S88dyqXjJkuBNLeMcVPRFXpRw2fuwdvfCGLEo89fDkw= +go.opentelemetry.io/otel/sdk/metric v1.44.0 h1:3LlKgI+VjbVsjNRFZJZAJ30WjXC5VkNRks6si09iEfI= go.opentelemetry.io/otel/trace v1.42.0 h1:OUCgIPt+mzOnaUTpOQcBiM/PLQ/Op7oq6g4LenLmOYY= go.opentelemetry.io/otel/trace v1.42.0/go.mod h1:f3K9S+IFqnumBkKhRJMeaZeNk9epyhnCmQh/EysQCdc= go.opentelemetry.io/otel/trace v1.43.0 h1:BkNrHpup+4k4w+ZZ86CZoHHEkohws8AY+WTX09nk+3A= go.opentelemetry.io/otel/trace v1.43.0/go.mod h1:/QJhyVBUUswCphDVxq+8mld+AvhXZLhe+8WVFxiFff0= +go.opentelemetry.io/otel/trace v1.44.0 h1:jxF5CsGYCe74MCRx2X4g7WsY/VBKRqqpNvXlX/6gtIk= +go.opentelemetry.io/otel/trace v1.44.0/go.mod h1:oLl1jrMQAVo6v3GAggN+1VH9VIz9iUSvW53sW1Q8PIE= go.uber.org/atomic v1.11.0 h1:ZvwS0R+56ePWxUNi+Atn9dWONBPp/AUETXlHW0DxSjE= go.uber.org/atomic v1.11.0/go.mod h1:LUxbIzbOniOlMKjJjyPfpl4v+PKK2cNJn91OQbhoJI0= go.uber.org/goleak v1.3.0 h1:2K3zAYmnTNqV73imy9J1T3WC+gmCePx2hEGkimedGto= @@ -227,12 +267,16 @@ golang.org/x/crypto v0.49.0 h1:+Ng2ULVvLHnJ/ZFEq4KdcDd/cfjrrjjNSXNzxg0Y4U4= golang.org/x/crypto v0.49.0/go.mod h1:ErX4dUh2UM+CFYiXZRTcMpEcN8b/1gxEuv3nODoYtCA= golang.org/x/crypto v0.50.0 h1:zO47/JPrL6vsNkINmLoo/PH1gcxpls50DNogFvB5ZGI= golang.org/x/crypto v0.50.0/go.mod h1:3muZ7vA7PBCE6xgPX7nkzzjiUq87kRItoJQM1Yo8S+Q= +golang.org/x/crypto v0.52.0 h1:RMs7fP2rXdep0CftQlK8Uf+kibLm7qkCcradZWYz988= +golang.org/x/crypto v0.52.0/go.mod h1:1QgfPxDqh0T2M/elOJtp9RvuR95kVjir0e6/BvEmGbc= golang.org/x/mod v0.6.0-dev.0.20220419223038-86c51ed26bb4/go.mod h1:jJ57K6gSWd91VN4djpZkiMVwK6gcyfeH4XE8wZrZaV4= golang.org/x/mod v0.8.0/go.mod h1:iBbtSCu2XBx23ZKBPSOrRkjjQPZFPuis4dIYUhu/chs= golang.org/x/mod v0.34.0 h1:xIHgNUUnW6sYkcM5Jleh05DvLOtwc6RitGHbDk4akRI= golang.org/x/mod v0.34.0/go.mod h1:ykgH52iCZe79kzLLMhyCUzhMci+nQj+0XkbXpNYtVjY= golang.org/x/mod v0.35.0 h1:Ww1D637e6Pg+Zb2KrWfHQUnH2dQRLBQyAtpr/haaJeM= golang.org/x/mod v0.35.0/go.mod h1:+GwiRhIInF8wPm+4AoT6L0FA1QWAad3OMdTRx4tFYlU= +golang.org/x/mod v0.36.0 h1:JJjpVx6myfUsUdAzZuOSTTmRE0PfZeNWzzvKrP7amb4= +golang.org/x/mod v0.36.0/go.mod h1:moc6ELqsWcOw5Ef3xVprK5ul/MvtVvkIXLziUOICjUQ= golang.org/x/net v0.0.0-20190620200207-3b0461eec859/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= golang.org/x/net v0.0.0-20210226172049-e18ecbb05110/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg= golang.org/x/net v0.0.0-20220722155237-a158d28d115b/go.mod h1:XRhObCWvk6IyKnWLug+ECip1KBveYUHfp+8e9klMJ9c= @@ -242,6 +286,8 @@ golang.org/x/net v0.52.0 h1:He/TN1l0e4mmR3QqHMT2Xab3Aj3L9qjbhRm78/6jrW0= golang.org/x/net v0.52.0/go.mod h1:R1MAz7uMZxVMualyPXb+VaqGSa3LIaUqk0eEt3w36Sw= golang.org/x/net v0.53.0 h1:d+qAbo5L0orcWAr0a9JweQpjXF19LMXJE8Ey7hwOdUA= golang.org/x/net v0.53.0/go.mod h1:JvMuJH7rrdiCfbeHoo3fCQU24Lf5JJwT9W3sJFulfgs= +golang.org/x/net v0.55.0 h1:bcvxaJn3e1U6InsFWt1JUq1aSjnRxLzT2rtD2KfkDF8= +golang.org/x/net v0.55.0/go.mod h1:L5U2KuzuOe1lY7Z+aWVIKK6qEeJXnXV9yzGA+WCHJww= golang.org/x/oauth2 v0.36.0 h1:peZ/1z27fi9hUOFCAZaHyrpWG5lwe0RJEEEeH0ThlIs= golang.org/x/oauth2 v0.36.0/go.mod h1:YDBUJMTkDnJS+A4BP4eZBjCqtokkg1hODuPjwiGPO7Q= golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= @@ -262,6 +308,8 @@ golang.org/x/sys v0.42.0 h1:omrd2nAlyT5ESRdCLYdm3+fMfNFE/+Rf4bDIQImRJeo= golang.org/x/sys v0.42.0/go.mod h1:4GL1E5IUh+htKOUEOaiffhrAeqysfVGipDYzABqnCmw= golang.org/x/sys v0.43.0 h1:Rlag2XtaFTxp19wS8MXlJwTvoh8ArU6ezoyFsMyCTNI= golang.org/x/sys v0.43.0/go.mod h1:4GL1E5IUh+htKOUEOaiffhrAeqysfVGipDYzABqnCmw= +golang.org/x/sys v0.45.0 h1:dO4czNzziLiiXplLQgBCEpCvXQ3dnkn0SdaZSYdQ+FY= +golang.org/x/sys v0.45.0/go.mod h1:4GL1E5IUh+htKOUEOaiffhrAeqysfVGipDYzABqnCmw= golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= golang.org/x/term v0.0.0-20210927222741-03fcf44c2211/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8= golang.org/x/term v0.5.0/go.mod h1:jMB1sMXY+tzblOD4FWmEbocvup2/aLOaQEp7JmGp78k= @@ -277,6 +325,8 @@ golang.org/x/text v0.35.0 h1:JOVx6vVDFokkpaq1AEptVzLTpDe9KGpj5tR4/X+ybL8= golang.org/x/text v0.35.0/go.mod h1:khi/HExzZJ2pGnjenulevKNX1W67CUy0AsXcNubPGCA= golang.org/x/text v0.36.0 h1:JfKh3XmcRPqZPKevfXVpI1wXPTqbkE5f7JA92a55Yxg= golang.org/x/text v0.36.0/go.mod h1:NIdBknypM8iqVmPiuco0Dh6P5Jcdk8lJL0CUebqK164= +golang.org/x/text v0.37.0 h1:Cqjiwd9eSg8e0QAkyCaQTNHFIIzWtidPahFWR83rTrc= +golang.org/x/text v0.37.0/go.mod h1:a5sjxXGs9hsn/AJVwuElvCAo9v8QYLzvavO5z2PiM38= golang.org/x/time v0.15.0 h1:bbrp8t3bGUeFOx08pvsMYRTCVSMk89u4tKbNOZbp88U= golang.org/x/time v0.15.0/go.mod h1:Y4YMaQmXwGQZoFaVFk4YpCt4FLQMYKZe9oeV/f4MSno= golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= @@ -287,6 +337,8 @@ golang.org/x/tools v0.43.0 h1:12BdW9CeB3Z+J/I/wj34VMl8X+fEXBxVR90JeMX5E7s= golang.org/x/tools v0.43.0/go.mod h1:uHkMso649BX2cZK6+RpuIPXS3ho2hZo4FVwfoy1vIk0= golang.org/x/tools v0.44.0 h1:UP4ajHPIcuMjT1GqzDWRlalUEoY+uzoZKnhOjbIPD2c= golang.org/x/tools v0.44.0/go.mod h1:KA0AfVErSdxRZIsOVipbv3rQhVXTnlU6UhKxHd1seDI= +golang.org/x/tools v0.45.0 h1:18qN3FAooORvApf5XjCXgsuayZOEtXf6JK18I3+ONa8= +golang.org/x/tools v0.45.0/go.mod h1:LuUGqqaXcXMEFEruIVJVm5mgDD8vww/z/SR1gQ4uE/0= golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= gonum.org/v1/gonum v0.16.0 h1:5+ul4Swaf3ESvrOnidPp4GZbzf0mxVQpDCYUQE7OJfk= gonum.org/v1/gonum v0.16.0/go.mod h1:fef3am4MQ93R2HHpKnLk4/Tbh/s0+wqD5nfa6Pnwy4E= @@ -295,6 +347,8 @@ google.golang.org/api v0.272.0 h1:eLUQZGnAS3OHn31URRf9sAmRk3w2JjMx37d2k8AjJmA= google.golang.org/api v0.272.0/go.mod h1:wKjowi5LNJc5qarNvDCvNQBn3rVK8nSy6jg2SwRwzIA= google.golang.org/api v0.275.0 h1:vfY5d9vFVJeWEZT65QDd9hbndr7FyZ2+6mIzGAh71NI= google.golang.org/api v0.275.0/go.mod h1:Fnag/EWUPIcJXuIkP1pjoTgS5vdxlk3eeemL7Do6bvw= +google.golang.org/api v0.283.0 h1:0lkp8u0MPwJVHqRL+nJlMAoZVVzbmiXmFHXMOTmSPik= +google.golang.org/api v0.283.0/go.mod h1:6Wssta4c5n9qHq5CBhmlai5h/PUa1djdDAIhYEHyvcM= google.golang.org/genproto v0.0.0-20260316180232-0b37fe3546d5 h1:JNfk58HZ8lfmXbYK2vx/UvsqIL59TzByCxPIX4TDmsE= google.golang.org/genproto v0.0.0-20260316180232-0b37fe3546d5/go.mod h1:x5julN69+ED4PcFk/XWayw35O0lf/nGa4aNgODCmNmw= google.golang.org/genproto v0.0.0-20260319201613-d00831a3d3e7 h1:XzmzkmB14QhVhgnawEVsOn6OFsnpyxNPRY9QV01dNB0= @@ -305,12 +359,18 @@ google.golang.org/genproto/googleapis/rpc v0.0.0-20260319201613-d00831a3d3e7 h1: google.golang.org/genproto/googleapis/rpc v0.0.0-20260319201613-d00831a3d3e7/go.mod h1:4Hqkh8ycfw05ld/3BWL7rJOSfebL2Q+DVDeRgYgxUU8= google.golang.org/genproto/googleapis/rpc v0.0.0-20260406210006-6f92a3bedf2d h1:wT2n40TBqFY6wiwazVK9/iTWbsQrgk5ZfCSVFLO9LQA= google.golang.org/genproto/googleapis/rpc v0.0.0-20260406210006-6f92a3bedf2d/go.mod h1:4Hqkh8ycfw05ld/3BWL7rJOSfebL2Q+DVDeRgYgxUU8= +google.golang.org/genproto/googleapis/rpc v0.0.0-20260526163538-3dc84a4a5aaa h1:mZHHdPZl0dbGHCflZgAq/Q468DWVFcU2whhB2KAo8fk= +google.golang.org/genproto/googleapis/rpc v0.0.0-20260526163538-3dc84a4a5aaa/go.mod h1:4Hqkh8ycfw05ld/3BWL7rJOSfebL2Q+DVDeRgYgxUU8= google.golang.org/grpc v1.79.3 h1:sybAEdRIEtvcD68Gx7dmnwjZKlyfuc61Dyo9pGXXkKE= google.golang.org/grpc v1.79.3/go.mod h1:KmT0Kjez+0dde/v2j9vzwoAScgEPx/Bw1CYChhHLrHQ= google.golang.org/grpc v1.80.0 h1:Xr6m2WmWZLETvUNvIUmeD5OAagMw3FiKmMlTdViWsHM= google.golang.org/grpc v1.80.0/go.mod h1:ho/dLnxwi3EDJA4Zghp7k2Ec1+c2jqup0bFkw07bwF4= +google.golang.org/grpc v1.81.1 h1:VnnIIZ88UzOOKLukQi+ImGz8O1Wdp8nAGGnvOfEIWQQ= +google.golang.org/grpc v1.81.1/go.mod h1:xGH9GfzOyMTGIOXBJmXt+BX/V0kcdQbdcuwQ/zNw42I= google.golang.org/protobuf v1.36.11 h1:fV6ZwhNocDyBLK0dj+fg8ektcVegBBuEolpbTQyBNVE= google.golang.org/protobuf v1.36.11/go.mod h1:HTf+CrKn2C3g5S8VImy6tdcUvCska2kB7j23XfzDpco= +google.golang.org/protobuf v1.36.12-0.20260120151049-f2248ac996af h1:+5/Sw3GsDNlEmu7TfklWKPdQ0Ykja5VEmq2i817+jbI= +google.golang.org/protobuf v1.36.12-0.20260120151049-f2248ac996af/go.mod h1:HTf+CrKn2C3g5S8VImy6tdcUvCska2kB7j23XfzDpco= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c h1:Hei/4ADfdWqJk1ZMxUNpqntNwaWcugrBjAiHlqqRiVk= gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c/go.mod h1:JHkPIbrfpd72SG/EVd6muEfDQjcINNoR0C8j2r3qZ4Q= @@ -321,3 +381,5 @@ gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA= gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= k8s.io/apimachinery v0.35.3 h1:MeaUwQCV3tjKP4bcwWGgZ/cp/vpsRnQzqO6J6tJyoF8= k8s.io/apimachinery v0.35.3/go.mod h1:jQCgFZFR1F4Ik7hvr2g84RTJSZegBc8yHgFWKn//hns= +k8s.io/apimachinery v0.36.1 h1:G63Gjx2W+q0YD+72Vo8oY0nDnePVwnuzTmmy5ENrVSA= +k8s.io/apimachinery v0.36.1/go.mod h1:ibYOR00vW/I1kzvi5SF0dRuJ52BvKtfvRdOn35GPQ+8= diff --git a/pkg/upstream/http.go b/pkg/upstream/http.go index 9112756e..ca77d543 100644 --- a/pkg/upstream/http.go +++ b/pkg/upstream/http.go @@ -123,7 +123,7 @@ func (t *unixRoundTripper) RoundTrip(req *http.Request) (*http.Response, error) // The proxy should render an error page if there are failures connecting to the // upstream server. func newReverseProxy(target *url.URL, upstream options.Upstream, errorHandler ProxyErrorHandler) http.Handler { - proxy := httputil.NewSingleHostReverseProxy(target) + proxy := newSingleHostReverseProxy(target) // Inherit default transport options from Go's stdlib transport := http.DefaultTransport.(*http.Transport).Clone() @@ -155,7 +155,7 @@ func newReverseProxy(target *url.URL, upstream options.Upstream, errorHandler Pr } // Ensure we always pass the original request path - setProxyDirector(proxy) + setProxyRewrite(proxy) // TODO (@tuunit) - this should be inverted or get a better name in the future to set the upstream host header // only if PassHostHeader is explicitly set to true. Currently this would be a breaking change. @@ -179,32 +179,71 @@ func newReverseProxy(target *url.URL, upstream options.Upstream, errorHandler Pr return proxy } -// setProxyUpstreamHostHeader sets the proxy.Director so that upstream requests -// receive a host header matching the target URL. -func setProxyUpstreamHostHeader(proxy *httputil.ReverseProxy, target *url.URL) { - director := proxy.Director - proxy.Director = func(req *http.Request) { - director(req) - req.Host = target.Host +func newSingleHostReverseProxy(target *url.URL) *httputil.ReverseProxy { + return &httputil.ReverseProxy{ + Rewrite: func(proxyReq *httputil.ProxyRequest) { + proxyReq.SetURL(target) + proxyReq.Out.Host = proxyReq.In.Host + setProxyForwardingHeaders(proxyReq) + }, } } -// setProxyDirector sets the proxy.Director so that request URIs are escaped +// setProxyUpstreamHostHeader sets the proxy.Rewrite so that upstream requests +// receive a host header matching the target URL. +func setProxyUpstreamHostHeader(proxy *httputil.ReverseProxy, target *url.URL) { + rewrite := proxy.Rewrite + proxy.Rewrite = func(proxyReq *httputil.ProxyRequest) { + rewrite(proxyReq) + proxyReq.Out.Host = target.Host + } +} + +// setProxyRewrite sets the proxy.Rewrite so that request URIs are escaped // when proxying to usptream servers. -func setProxyDirector(proxy *httputil.ReverseProxy) { - director := proxy.Director - proxy.Director = func(req *http.Request) { - director(req) +func setProxyRewrite(proxy *httputil.ReverseProxy) { + rewrite := proxy.Rewrite + proxy.Rewrite = func(proxyReq *httputil.ProxyRequest) { + rewrite(proxyReq) // use RequestURI so that we aren't unescaping encoded slashes in the request path - req.URL.Opaque = req.RequestURI - req.URL.RawQuery = "" - req.URL.ForceQuery = false + proxyReq.Out.URL.Opaque = proxyReq.In.RequestURI + proxyReq.Out.URL.RawQuery = "" + proxyReq.Out.URL.ForceQuery = false + } +} + +func setProxyForwardingHeaders(proxyReq *httputil.ProxyRequest) { + // TODO (@tuunit): Preserve the legacy Director-based forwarding header behavior + // for backwards compatibility. Harden this with saner defaults and/or + // explicit flags in the future. + for _, header := range []string{"Forwarded", "X-Forwarded-Host", "X-Forwarded-Proto"} { + if values, ok := proxyReq.In.Header[header]; ok { + proxyReq.Out.Header[header] = append([]string(nil), values...) + } + } + + prior, ok := proxyReq.In.Header["X-Forwarded-For"] + if ok { + proxyReq.Out.Header["X-Forwarded-For"] = append([]string(nil), prior...) + } + + clientIP, _, err := net.SplitHostPort(proxyReq.In.RemoteAddr) + if err != nil { + return + } + + omit := ok && prior == nil + if len(prior) > 0 { + clientIP = strings.Join(prior, ", ") + ", " + clientIP + } + if !omit { + proxyReq.Out.Header.Set("X-Forwarded-For", clientIP) } } // newWebSocketReverseProxy creates a new reverse proxy for proxying websocket connections. func newWebSocketReverseProxy(u *url.URL, skipTLSVerify *bool, passHostHeader *bool) http.Handler { - wsProxy := httputil.NewSingleHostReverseProxy(u) + wsProxy := newSingleHostReverseProxy(u) // Inherit default transport options from Go's stdlib transport := http.DefaultTransport.(*http.Transport).Clone() diff --git a/pkg/upstream/http_test.go b/pkg/upstream/http_test.go index 70af9e7e..92d61df5 100644 --- a/pkg/upstream/http_test.go +++ b/pkg/upstream/http_test.go @@ -361,7 +361,12 @@ var _ = Describe("HTTP Upstream Suite", func() { return http.HandlerFunc(func(_ http.ResponseWriter, req *http.Request) { proxy, ok := h.(*httputil.ReverseProxy) Expect(ok).To(BeTrue()) - proxy.Director(req) + outReq := req.Clone(req.Context()) + proxy.Rewrite(&httputil.ProxyRequest{ + In: req, + Out: outReq, + }) + req.Host = outReq.Host }) } httpUpstream.handler = requestInterceptor(httpUpstream.handler) @@ -370,6 +375,54 @@ var _ = Describe("HTTP Upstream Suite", func() { Expect(req.Host).To(Equal(strings.TrimPrefix(serverAddr, "http://"))) }) + It("ServeHTTP preserves forwarding headers when using Rewrite", func() { + req := httptest.NewRequest("", "http://example.localhost/foo", nil) + req.RemoteAddr = "192.0.2.10:1234" + req.Header.Set("Forwarded", "for=192.0.2.1;proto=https;host=example.localhost") + req.Header.Set("X-Forwarded-Host", "forwarded.example.localhost") + req.Header.Set("X-Forwarded-Proto", "https") + req.Header.Set("X-Forwarded-For", "192.0.2.1") + req = middlewareapi.AddRequestScope(req, &middlewareapi.RequestScope{}) + rw := httptest.NewRecorder() + + upstream := options.Upstream{ + ID: "preserveForwardedHeaders", + PassHostHeader: ptr.To(true), + ProxyWebSockets: ptr.To(false), + InsecureSkipTLSVerify: ptr.To(false), + FlushInterval: &defaultFlushInterval, + Timeout: &defaultTimeout, + } + + u, err := url.Parse(serverAddr) + Expect(err).ToNot(HaveOccurred()) + + handler := newHTTPUpstreamProxy(upstream, u, nil, nil) + httpUpstream, ok := handler.(*httpUpstreamProxy) + Expect(ok).To(BeTrue()) + + requestInterceptor := func(h http.Handler) http.Handler { + return http.HandlerFunc(func(_ http.ResponseWriter, req *http.Request) { + proxy, ok := h.(*httputil.ReverseProxy) + Expect(ok).To(BeTrue()) + + outReq := req.Clone(req.Context()) + proxy.Rewrite(&httputil.ProxyRequest{ + In: req, + Out: outReq, + }) + + Expect(outReq.Header.Values("Forwarded")).To(Equal([]string{"for=192.0.2.1;proto=https;host=example.localhost"})) + Expect(outReq.Header.Values("X-Forwarded-Host")).To(Equal([]string{"forwarded.example.localhost"})) + Expect(outReq.Header.Values("X-Forwarded-Proto")).To(Equal([]string{"https"})) + Expect(outReq.Header.Values("X-Forwarded-For")).To(Equal([]string{"192.0.2.1, 192.0.2.10"})) + }) + } + httpUpstream.handler = requestInterceptor(httpUpstream.handler) + + httpUpstream.ServeHTTP(rw, req) + }) + type newUpstreamTableInput struct { proxyWebSockets bool flushInterval time.Duration @@ -405,6 +458,7 @@ var _ = Describe("HTTP Upstream Suite", func() { proxy, ok := upstreamProxy.handler.(*httputil.ReverseProxy) Expect(ok).To(BeTrue()) + Expect(proxy.Rewrite).ToNot(BeNil()) Expect(proxy.FlushInterval).To(Equal(in.flushInterval)) transport, ok := proxy.Transport.(*http.Transport) Expect(ok).To(BeTrue()) diff --git a/pkg/upstream/proxy_test.go b/pkg/upstream/proxy_test.go index aba4a730..92286605 100644 --- a/pkg/upstream/proxy_test.go +++ b/pkg/upstream/proxy_test.go @@ -79,7 +79,7 @@ var _ = Describe("Proxy Suite", func() { { ID: "bad-http-backend", Path: "/bad-http/", - URI: "http://::1", + URI: invalidServer, }, { ID: "single-path-backend", diff --git a/pkg/upstream/upstream_suite_test.go b/pkg/upstream/upstream_suite_test.go index 56aa98b1..0ca23941 100644 --- a/pkg/upstream/upstream_suite_test.go +++ b/pkg/upstream/upstream_suite_test.go @@ -24,7 +24,7 @@ var ( serverAddr string unixServer *httptest.Server unixServerAddr string - invalidServer = "http://::1" + invalidServer = "http://127.0.0.1:1" ) func TestUpstreamSuite(t *testing.T) { diff --git a/pkg/validation/sessions_test.go b/pkg/validation/sessions_test.go index cb54c571..6f590ac5 100644 --- a/pkg/validation/sessions_test.go +++ b/pkg/validation/sessions_test.go @@ -193,8 +193,8 @@ var _ = Describe("Sessions", func() { unreachableRedisDelMsg = "unable to delete the redis initialization key: dial tcp 127.0.0.1:65535: connect: connection refused" unreachableSentinelSetMsg = "unable to set a redis initialization key: redis: all sentinels specified in configuration are unreachable: redis: nil" unrechableSentinelDelMsg = "unable to delete the redis initialization key: redis: all sentinels specified in configuration are unreachable: redis: nil" - refusedSentinelSetMsg = "unable to set a redis initialization key: redis: all sentinels specified in configuration are unreachable: context deadline exceeded" - refusedSentinelDelMsg = "unable to delete the redis initialization key: redis: all sentinels specified in configuration are unreachable: context deadline exceeded" + refusedSentinelSetMsg = "unable to set a redis initialization key: redis: all sentinels specified in configuration are unreachable: dial tcp 127.0.0.1:65535: connect: connection refused" + refusedSentinelDelMsg = "unable to delete the redis initialization key: redis: all sentinels specified in configuration are unreachable: dial tcp 127.0.0.1:65535: connect: connection refused" ) type redisStoreTableInput struct {