171 lines
		
	
	
		
			4.9 KiB
		
	
	
	
		
			Go
		
	
	
	
			
		
		
	
	
			171 lines
		
	
	
		
			4.9 KiB
		
	
	
	
		
			Go
		
	
	
	
package cookies
 | 
						|
 | 
						|
import (
 | 
						|
	"fmt"
 | 
						|
	"net/http"
 | 
						|
	"time"
 | 
						|
 | 
						|
	"github.com/oauth2-proxy/oauth2-proxy/v7/pkg/apis/options"
 | 
						|
 | 
						|
	middlewareapi "github.com/oauth2-proxy/oauth2-proxy/v7/pkg/apis/middleware"
 | 
						|
	. "github.com/onsi/ginkgo/v2"
 | 
						|
	. "github.com/onsi/gomega"
 | 
						|
)
 | 
						|
 | 
						|
var _ = Describe("Cookie Tests", func() {
 | 
						|
	Context("GetCookieDomain", func() {
 | 
						|
		type getCookieDomainTableInput struct {
 | 
						|
			host           string
 | 
						|
			xForwardedHost string
 | 
						|
			cookieDomains  []string
 | 
						|
			expectedOutput string
 | 
						|
		}
 | 
						|
 | 
						|
		DescribeTable("should return expected results",
 | 
						|
			func(in getCookieDomainTableInput) {
 | 
						|
				req, err := http.NewRequest(
 | 
						|
					http.MethodGet,
 | 
						|
					fmt.Sprintf("https://%s/%s", in.host, cookiePath),
 | 
						|
					nil,
 | 
						|
				)
 | 
						|
				Expect(err).ToNot(HaveOccurred())
 | 
						|
 | 
						|
				if in.xForwardedHost != "" {
 | 
						|
					req.Header.Add("X-Forwarded-Host", in.xForwardedHost)
 | 
						|
					req = middlewareapi.AddRequestScope(req, &middlewareapi.RequestScope{
 | 
						|
						ReverseProxy: true,
 | 
						|
					})
 | 
						|
				}
 | 
						|
 | 
						|
				Expect(GetCookieDomain(req, in.cookieDomains)).To(Equal(in.expectedOutput))
 | 
						|
			},
 | 
						|
			Entry("a single exact match for the Host header", getCookieDomainTableInput{
 | 
						|
				host:           "www.cookies.test",
 | 
						|
				cookieDomains:  []string{"www.cookies.test"},
 | 
						|
				expectedOutput: "www.cookies.test",
 | 
						|
			}),
 | 
						|
			Entry("a single exact match for the X-Forwarded-Host header", getCookieDomainTableInput{
 | 
						|
				host:           "backend.cookies.internal",
 | 
						|
				xForwardedHost: "www.cookies.test",
 | 
						|
				cookieDomains:  []string{"www.cookies.test"},
 | 
						|
				expectedOutput: "www.cookies.test",
 | 
						|
			}),
 | 
						|
			Entry("a single suffix match for the Host header", getCookieDomainTableInput{
 | 
						|
				host:           "www.cookies.test",
 | 
						|
				cookieDomains:  []string{".cookies.test"},
 | 
						|
				expectedOutput: ".cookies.test",
 | 
						|
			}),
 | 
						|
			Entry("a single suffix match for the X-Forwarded-Host header", getCookieDomainTableInput{
 | 
						|
				host:           "backend.cookies.internal",
 | 
						|
				xForwardedHost: "www.cookies.test",
 | 
						|
				cookieDomains:  []string{".cookies.test"},
 | 
						|
				expectedOutput: ".cookies.test",
 | 
						|
			}),
 | 
						|
			Entry("the first match is used", getCookieDomainTableInput{
 | 
						|
				host:           "www.cookies.test",
 | 
						|
				cookieDomains:  []string{"www.cookies.test", ".cookies.test"},
 | 
						|
				expectedOutput: "www.cookies.test",
 | 
						|
			}),
 | 
						|
			Entry("the only match is used", getCookieDomainTableInput{
 | 
						|
				host:           "www.cookies.test",
 | 
						|
				cookieDomains:  []string{".cookies.wrong", ".cookies.test"},
 | 
						|
				expectedOutput: ".cookies.test",
 | 
						|
			}),
 | 
						|
			Entry("blank is returned for no matches", getCookieDomainTableInput{
 | 
						|
				host:           "www.cookies.test",
 | 
						|
				cookieDomains:  []string{".cookies.wrong", ".cookies.false"},
 | 
						|
				expectedOutput: "",
 | 
						|
			}),
 | 
						|
		)
 | 
						|
	})
 | 
						|
 | 
						|
	Context("MakeCookieFromOptions", func() {
 | 
						|
		type makeCookieFromOptionsTableInput struct {
 | 
						|
			host           string
 | 
						|
			name           string
 | 
						|
			value          string
 | 
						|
			opts           options.Cookie
 | 
						|
			expiration     time.Duration
 | 
						|
			now            time.Time
 | 
						|
			expectedOutput int
 | 
						|
		}
 | 
						|
 | 
						|
		validName := "_oauth2_proxy"
 | 
						|
		validSecret := "secretthirtytwobytes+abcdefghijk"
 | 
						|
		domains := []string{"www.cookies.test"}
 | 
						|
 | 
						|
		now := time.Now()
 | 
						|
		var expectedMaxAge int
 | 
						|
 | 
						|
		DescribeTable("should return cookies with or without expiration",
 | 
						|
			func(in makeCookieFromOptionsTableInput) {
 | 
						|
				req, err := http.NewRequest(
 | 
						|
					http.MethodGet,
 | 
						|
					fmt.Sprintf("https://%s/%s", in.host, cookiePath),
 | 
						|
					nil,
 | 
						|
				)
 | 
						|
				Expect(err).ToNot(HaveOccurred())
 | 
						|
 | 
						|
				Expect(MakeCookieFromOptions(req, in.name, in.value, &in.opts, in.expiration).MaxAge).To(Equal(in.expectedOutput))
 | 
						|
			},
 | 
						|
			Entry("persistent cookie", makeCookieFromOptionsTableInput{
 | 
						|
				host:  "www.cookies.test",
 | 
						|
				name:  validName,
 | 
						|
				value: "1",
 | 
						|
				opts: options.Cookie{
 | 
						|
					Name:     validName,
 | 
						|
					Secret:   validSecret,
 | 
						|
					Domains:  domains,
 | 
						|
					Path:     "",
 | 
						|
					Expire:   time.Hour,
 | 
						|
					Refresh:  15 * time.Minute,
 | 
						|
					Secure:   true,
 | 
						|
					HTTPOnly: false,
 | 
						|
					SameSite: "",
 | 
						|
				},
 | 
						|
				expiration:     15 * time.Minute,
 | 
						|
				now:            now,
 | 
						|
				expectedOutput: int((15 * time.Minute).Seconds()),
 | 
						|
			}),
 | 
						|
			Entry("persistent cookie to be cleared", makeCookieFromOptionsTableInput{
 | 
						|
				host:  "www.cookies.test",
 | 
						|
				name:  validName,
 | 
						|
				value: "1",
 | 
						|
				opts: options.Cookie{
 | 
						|
					Name:     validName,
 | 
						|
					Secret:   validSecret,
 | 
						|
					Domains:  domains,
 | 
						|
					Path:     "",
 | 
						|
					Expire:   time.Hour * -1,
 | 
						|
					Refresh:  15 * time.Minute,
 | 
						|
					Secure:   true,
 | 
						|
					HTTPOnly: false,
 | 
						|
					SameSite: "",
 | 
						|
				},
 | 
						|
				expiration:     time.Hour * -1,
 | 
						|
				now:            now,
 | 
						|
				expectedOutput: -1,
 | 
						|
			}),
 | 
						|
			Entry("session cookie", makeCookieFromOptionsTableInput{
 | 
						|
				host:  "www.cookies.test",
 | 
						|
				name:  validName,
 | 
						|
				value: "1",
 | 
						|
				opts: options.Cookie{
 | 
						|
					Name:     validName,
 | 
						|
					Secret:   validSecret,
 | 
						|
					Domains:  domains,
 | 
						|
					Path:     "",
 | 
						|
					Expire:   0,
 | 
						|
					Refresh:  15 * time.Minute,
 | 
						|
					Secure:   true,
 | 
						|
					HTTPOnly: false,
 | 
						|
					SameSite: "",
 | 
						|
				},
 | 
						|
				expiration:     0,
 | 
						|
				now:            now,
 | 
						|
				expectedOutput: expectedMaxAge,
 | 
						|
			}),
 | 
						|
		)
 | 
						|
	})
 | 
						|
})
 |