10 "github.com/golang-jwt/jwt/v5"
11 "github.com/oauth2-proxy/mockoidc"
12 "github.com/oauth2-proxy/oauth2-proxy/v7/pkg/apis/options"
13 "github.com/oauth2-proxy/oauth2-proxy/v7/pkg/util/ptr"
14 . "github.com/onsi/gomega"
19 clientSecret = "xyzzyplugh"
20 providerID = "providerID"
22 msIssuerURL = "https://login.microsoftonline.com/fabrikamb2c.onmicrosoft.com/v2.0/"
23 msKeysURL = "https://login.microsoftonline.com/fabrikamb2c.onmicrosoft.com/discovery/v2.0/keys"
24 msAuthURL = "https://login.microsoftonline.com/fabrikamb2c.onmicrosoft.com/oauth2/v2.0/authorize?p=b2c_1_sign_in"
25 msTokenURL = "https://login.microsoftonline.com/fabrikamb2c.onmicrosoft.com/oauth2/v2.0/token?p=b2c_1_sign_in"
28func TestClientSecretFileOptionFails(t *testing.T) {
31 providerConfig := options.Provider{
35 ClientSecretFile: clientSecret,
38 p, err := newProviderDataFromConfig(providerConfig)
39 g.Expect(err).ToNot(HaveOccurred())
40 g.Expect(p.ClientSecretFile).To(Equal(clientSecret))
41 g.Expect(p.ClientSecret).To(BeEmpty())
43 s, err := p.GetClientSecret()
44 g.Expect(err).To(HaveOccurred())
45 g.Expect(s).To(BeEmpty())
48func TestClientSecretFileOption(t *testing.T) {
51 f, err := os.CreateTemp("", "client_secret_temp_file_")
52 g.Expect(err).ToNot(HaveOccurred())
54 clientSecretFileName := f.Name()
57 g.Expect(f.Close()).To(Succeed())
58 g.Expect(os.Remove(clientSecretFileName)).To(Succeed())
61 _, err = f.WriteString("testcase")
62 g.Expect(err).ToNot(HaveOccurred())
64 providerConfig := options.Provider{
68 ClientSecretFile: clientSecretFileName,
71 p, err := newProviderDataFromConfig(providerConfig)
72 g.Expect(err).ToNot(HaveOccurred())
73 g.Expect(p.ClientSecretFile).To(Equal(clientSecretFileName))
74 g.Expect(p.ClientSecret).To(BeEmpty())
76 s, err := p.GetClientSecret()
77 g.Expect(err).ToNot(HaveOccurred())
78 g.Expect(s).To(Equal("testcase"))
81func TestSkipOIDCDiscovery(t *testing.T) {
83 providerConfig := options.Provider{
87 ClientSecretFile: clientSecret,
88 OIDCConfig: options.OIDCOptions{
89 IssuerURL: msIssuerURL,
90 SkipDiscovery: ptr.To(true),
94 _, err := newProviderDataFromConfig(providerConfig)
95 g.Expect(err).To(MatchError("error building OIDC ProviderVerifier: invalid provider verifier options: missing required setting: jwks-url or public-key-files"))
97 providerConfig.LoginURL = msAuthURL
98 providerConfig.RedeemURL = msTokenURL
99 providerConfig.OIDCConfig.JwksURL = msKeysURL
101 _, err = newProviderDataFromConfig(providerConfig)
102 g.Expect(err).ToNot(HaveOccurred())
105func TestURLsCorrectlyParsed(t *testing.T) {
108 providerConfig := options.Provider{
112 ClientSecretFile: clientSecret,
114 RedeemURL: msTokenURL,
115 OIDCConfig: options.OIDCOptions{
116 IssuerURL: msIssuerURL,
117 SkipDiscovery: ptr.To(true),
122 pd, err := newProviderDataFromConfig(providerConfig)
123 g.Expect(err).ToNot(HaveOccurred())
125 g.Expect(pd.LoginURL.String()).To(Equal(msAuthURL))
126 g.Expect(pd.RedeemURL.String()).To(Equal(msTokenURL))
129func TestEnabledSigningAlgsAreAppliedToProviderVerifier(t *testing.T) {
132 m, err := mockoidc.NewServer(nil)
133 g.Expect(err).ToNot(HaveOccurred())
134 m.AddMiddleware(newSigningAlgsIssuerMiddleware(m, []string{"RS256", "HS256"}))
136 listener, err := net.Listen("tcp", "127.0.0.1:0")
137 g.Expect(err).ToNot(HaveOccurred())
138 g.Expect(m.Start(listener, nil)).To(Succeed())
140 g.Expect(m.Shutdown()).To(Succeed())
143 providerConfig := options.Provider{
146 ClientID: m.Config().ClientID,
147 ClientSecretFile: clientSecret,
148 OIDCConfig: options.OIDCOptions{
149 IssuerURL: m.Issuer(),
150 AudienceClaims: []string{"aud"},
151 EnabledSigningAlgs: []string{"HS256"},
155 pd, err := newProviderDataFromConfig(providerConfig)
156 g.Expect(err).ToNot(HaveOccurred())
158 rawIDToken, err := m.Keypair.SignJWT(jwt.RegisteredClaims{
159 Audience: jwt.ClaimStrings{m.Config().ClientID},
161 ExpiresAt: jwt.NewNumericDate(time.Now().Add(time.Hour)),
162 IssuedAt: jwt.NewNumericDate(time.Now()),
165 g.Expect(err).ToNot(HaveOccurred())
167 _, err = pd.Verifier.Verify(context.Background(), rawIDToken)
168 g.Expect(err).To(HaveOccurred())
169 g.Expect(err.Error()).To(ContainSubstring("unexpected signature algorithm"))
172func TestEnabledSigningAlgsRejectUnsupportedTokens(t *testing.T) {
175 m, err := mockoidc.Run()
176 g.Expect(err).ToNot(HaveOccurred())
178 g.Expect(m.Shutdown()).To(Succeed())
181 providerConfig := options.Provider{
184 ClientID: m.Config().ClientID,
185 ClientSecretFile: clientSecret,
186 LoginURL: m.AuthorizationEndpoint(),
187 RedeemURL: m.TokenEndpoint(),
188 OIDCConfig: options.OIDCOptions{
189 IssuerURL: m.Issuer(),
190 SkipDiscovery: ptr.To(true),
191 JwksURL: m.JWKSEndpoint(),
192 AudienceClaims: []string{"aud"},
193 EnabledSigningAlgs: []string{"HS256"},
197 pd, err := newProviderDataFromConfig(providerConfig)
198 g.Expect(err).ToNot(HaveOccurred())
200 rawIDToken, err := m.Keypair.SignJWT(jwt.RegisteredClaims{
201 Audience: jwt.ClaimStrings{m.Config().ClientID},
203 ExpiresAt: jwt.NewNumericDate(time.Now().Add(time.Hour)),
204 IssuedAt: jwt.NewNumericDate(time.Now()),
207 g.Expect(err).ToNot(HaveOccurred())
209 _, err = pd.Verifier.Verify(context.Background(), rawIDToken)
210 g.Expect(err).To(HaveOccurred())
211 g.Expect(err.Error()).To(ContainSubstring("unexpected signature algorithm"))
214func TestScope(t *testing.T) {
217 testCases := []struct {
219 configuredType options.ProviderType
220 configuredScope string
222 allowedGroups []string
225 name: "oidc: with no scope provided",
226 configuredType: "oidc",
228 expectedScope: "openid email profile",
231 name: "oidc: with no scope provided and allowed groups",
232 configuredType: "oidc",
234 expectedScope: "openid email profile groups",
235 allowedGroups: []string{"foo"},
238 name: "oidc: with custom scope including groups without allowed groups",
239 configuredType: "oidc",
240 configuredScope: "myscope groups",
241 expectedScope: "myscope groups",
244 name: "oidc: with custom scope without groups but allowed groups",
245 configuredType: "oidc",
246 configuredScope: "myscope",
247 expectedScope: "myscope",
248 allowedGroups: []string{"foo"},
251 name: "oidc: with custom scope with groups and allowed groups",
252 configuredType: "oidc",
253 configuredScope: "myscope groups",
254 expectedScope: "myscope groups",
255 allowedGroups: []string{"foo"},
258 name: "oidc: with a configured scope provided",
259 configuredType: "oidc",
260 configuredScope: "openid",
261 expectedScope: "openid",
264 name: "github: with no scope provided",
265 configuredType: "github",
267 expectedScope: "user:email read:org",
270 name: "github: with a configured scope provided",
271 configuredType: "github",
272 configuredScope: "read:user read:org",
273 expectedScope: "read:user read:org",
276 name: "keycloak: with no scope provided and groups",
277 configuredType: "keycloak-oidc",
279 expectedScope: "openid email profile groups",
280 allowedGroups: []string{"foo"},
283 name: "keycloak: with custom scope and groups",
284 configuredType: "keycloak-oidc",
285 configuredScope: "myscope",
286 expectedScope: "myscope",
287 allowedGroups: []string{"foo"},
290 name: "keycloak: with custom scope and groups scope",
291 configuredType: "keycloak-oidc",
292 configuredScope: "myscope groups",
293 expectedScope: "myscope groups",
294 allowedGroups: []string{"foo"},
298 for _, tc := range testCases {
299 providerConfig := options.Provider{
301 Type: tc.configuredType,
303 ClientSecretFile: clientSecret,
305 RedeemURL: msTokenURL,
306 Scope: tc.configuredScope,
307 AllowedGroups: tc.allowedGroups,
308 OIDCConfig: options.OIDCOptions{
309 IssuerURL: msIssuerURL,
310 SkipDiscovery: ptr.To(true),
315 pd, err := NewProvider(providerConfig)
316 g.Expect(err).ToNot(HaveOccurred())
318 g.Expect(pd.Data().Scope).To(Equal(tc.expectedScope))
322func TestForcedMethodS256(t *testing.T) {
324 options := options.NewOptions()
325 options.Providers[0].CodeChallengeMethod = CodeChallengeMethodS256
326 method := parseCodeChallengeMethod(options.Providers[0])
328 g.Expect(method).To(Equal(CodeChallengeMethodS256))
331func TestForcedMethodPlain(t *testing.T) {
333 options := options.NewOptions()
334 options.Providers[0].CodeChallengeMethod = CodeChallengeMethodPlain
335 method := parseCodeChallengeMethod(options.Providers[0])
337 g.Expect(method).To(Equal(CodeChallengeMethodPlain))
340func TestPrefersS256(t *testing.T) {
342 options := options.NewOptions()
343 method := parseCodeChallengeMethod(options.Providers[0])
345 g.Expect(method).To(Equal(""))
348func TestCanOverwriteS256(t *testing.T) {
350 options := options.NewOptions()
351 options.Providers[0].CodeChallengeMethod = "plain"
352 method := parseCodeChallengeMethod(options.Providers[0])
354 g.Expect(method).To(Equal(CodeChallengeMethodPlain))
357func TestEmailClaimCorrectlySet(t *testing.T) {
360 testCases := []struct {
364 expectedEmailClaim string
367 name: "do not override EmailClaim if UserIDClaim is empty",
370 expectedEmailClaim: "email",
373 name: "set EmailClaim to UserIDClaim",
374 userIDClaim: "user_id_claim",
376 expectedEmailClaim: "user_id_claim",
380 for _, tc := range testCases {
381 t.Run(tc.name, func(t *testing.T) {
382 providerConfig := options.Provider{
386 ClientSecretFile: clientSecret,
388 RedeemURL: msTokenURL,
389 OIDCConfig: options.OIDCOptions{
390 IssuerURL: msIssuerURL,
391 SkipDiscovery: ptr.To(true),
393 UserIDClaim: tc.userIDClaim,
394 EmailClaim: tc.emailClaim,
398 pd, err := newProviderDataFromConfig(providerConfig)
399 g.Expect(err).ToNot(HaveOccurred())
401 g.Expect(pd.EmailClaim).To(Equal(tc.expectedEmailClaim))
keysesc to close
- j k
- move down, up
- enter
- open
- esc
- back, or up a level
- 1 2 3 4
- readme, files, commits, refs
- /
- filter
- y
- copy the clone command
- c
- compare the chosen commit with another (or shift-click both)
- ?
- show or hide this list