diff options
Diffstat (limited to 'pkg')
| -rw-r--r-- | pkg/oidc/id_token.go | 60 | ||||
| -rw-r--r-- | pkg/oidc/oidc.go | 11 | ||||
| -rw-r--r-- | pkg/oidc/oidc_test.go | 33 | ||||
| -rw-r--r-- | pkg/oidc/tokens.go | 4 | ||||
| -rw-r--r-- | pkg/oidc/tokens_test.go | 20 | ||||
| -rw-r--r-- | pkg/test/oidc_server.go | 61 | ||||
| -rw-r--r-- | pkg/web/middleware/unpack_token.go | 13 | ||||
| -rw-r--r-- | pkg/web/middleware/unpack_token_test.go | 17 |
8 files changed, 119 insertions, 100 deletions
diff --git a/pkg/oidc/id_token.go b/pkg/oidc/id_token.go index 5fc1e63..ce4ae22 100644 --- a/pkg/oidc/id_token.go +++ b/pkg/oidc/id_token.go @@ -1,39 +1,33 @@ package oidc -import ( - "bytes" - "encoding/base64" - "errors" - "strings" - "time" +import "github.com/coreos/go-oidc/v3/oidc" - "github.com/xlgmokha/x/pkg/serde" -) +type IDToken = oidc.IDToken -type IDToken struct { - Audience string `json:"aud"` - Email string `json:"email"` - EmailVerified bool `json:"email_verified"` - ExpiredAt int64 `json:"exp"` - IssuedAt int64 `json:"iat"` - Issuer string `json:"iss"` - Name string `json:"name"` - Nickname string `json:"nickname"` - Picture string `json:"picture"` - Subject string `json:"sub"` - UpdatedAt time.Time `json:"updated_at"` -} +// type IDToken struct { +// Audience string `json:"aud"` +// Email string `json:"email"` +// EmailVerified bool `json:"email_verified"` +// ExpiredAt int64 `json:"exp"` +// IssuedAt int64 `json:"iat"` +// Issuer string `json:"iss"` +// Name string `json:"name"` +// Nickname string `json:"nickname"` +// Picture string `json:"picture"` +// Subject string `json:"sub"` +// UpdatedAt time.Time `json:"updated_at"` +// } -func NewIDToken(raw string) (*IDToken, error) { - sections := strings.SplitN(raw, ".", 3) - if len(sections) != 3 { - return nil, errors.New("Invalid token") - } - b, err := base64.RawURLEncoding.DecodeString(sections[1]) - if err != nil { - return nil, err - } +// func NewIDToken(raw string) (*IDToken, error) { +// sections := strings.SplitN(raw, ".", 3) +// if len(sections) != 3 { +// return nil, errors.New("Invalid token") +// } +// b, err := base64.RawURLEncoding.DecodeString(sections[1]) +// if err != nil { +// return nil, err +// } - token, err := serde.FromJSON[*IDToken](bytes.NewReader(b)) - return token, err -} +// token, err := serde.FromJSON[*IDToken](bytes.NewReader(b)) +// return token, err +// } diff --git a/pkg/oidc/oidc.go b/pkg/oidc/oidc.go index 0526142..200db69 100644 --- a/pkg/oidc/oidc.go +++ b/pkg/oidc/oidc.go @@ -4,14 +4,18 @@ import ( "context" "github.com/coreos/go-oidc/v3/oidc" + xcontext "github.com/xlgmokha/x/pkg/context" "golang.org/x/oauth2" ) type OpenID struct { - Provider *oidc.Provider - Config *oauth2.Config + Provider *oidc.Provider + Config *oauth2.Config + OIDCConfig *oidc.Config } +var IDTokenKey xcontext.Key[*IDToken] = xcontext.Key[*IDToken]("id_token") + func New(ctx context.Context, issuer string, clientID, clientSecret, callbackURL string) (*OpenID, error) { provider, err := oidc.NewProvider(ctx, issuer) if err != nil { @@ -27,5 +31,8 @@ func New(ctx context.Context, issuer string, clientID, clientSecret, callbackURL Endpoint: provider.Endpoint(), Scopes: []string{oidc.ScopeOpenID, "profile", "email"}, }, + OIDCConfig: &oidc.Config{ + ClientID: clientID, + }, }, nil } diff --git a/pkg/oidc/oidc_test.go b/pkg/oidc/oidc_test.go index ef6a4f6..b7715cf 100644 --- a/pkg/oidc/oidc_test.go +++ b/pkg/oidc/oidc_test.go @@ -2,48 +2,21 @@ package oidc import ( "context" - "net/http" - "net/http/httptest" "testing" "github.com/stretchr/testify/assert" "github.com/stretchr/testify/require" - "github.com/xlgmokha/x/pkg/serde" + "gitlab.com/gitlab-org/software-supply-chain-security/authorization/sparkled/pkg/test" ) func TestOpenID(t *testing.T) { t.Run("GET /.well-known/openid-configuration", func(t *testing.T) { - srv := httptest.NewServer(nil) - srv.Config = &http.Server{ - Handler: http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { - require.Equal(t, "/.well-known/openid-configuration", r.URL.Path) - require.NoError(t, serde.ToJSON(w, &Metadata{ - AuthorizationEndpoint: srv.URL + "/authorize", - ClaimsSupported: []string{"aud"}, - CodeChallengeMethodsSupported: []string{"plain"}, - DeviceAuthorizationEndpoint: srv.URL + "/device/authorize", - IDTokenSigningAlgValuesSupported: []string{"RS256"}, - Issuer: srv.URL, - JWKSURI: srv.URL + "/jwks", - MFAChallengeEndpoint: srv.URL + "/mfa", - RegistrationEndpoint: srv.URL + "/users/new", - RequestURIParameterSupported: false, - ResponseModesSupported: []string{"query"}, - ResponseTypeSupported: []string{"code"}, - RevocationEndpoint: srv.URL + "/revoke", - ScopesSupported: []string{"oidc"}, - SubjectTypesSupported: []string{"public"}, - TokenEndpoint: srv.URL + "/token", - TokenEndpointAuthMethodsSupported: []string{"client_secret_post"}, - UserInfoEndpoint: srv.URL + "/users/me", - })) - }), - } + srv := test.OIDCServer() defer srv.Close() openID, err := New(context.Background(), srv.URL, "client_id", "client_secret", "https://example.com/oauth/callback") require.NoError(t, err) - assert.Equal(t, srv.URL+"/authorize", openID.Provider.Endpoint().AuthURL) + assert.Equal(t, srv.URL+"/oauth/authorize", openID.Provider.Endpoint().AuthURL) }) } diff --git a/pkg/oidc/tokens.go b/pkg/oidc/tokens.go index a326ff2..7ff3c07 100644 --- a/pkg/oidc/tokens.go +++ b/pkg/oidc/tokens.go @@ -22,10 +22,6 @@ func (t *Tokens) ToBase64String() (string, error) { return base64.URLEncoding.EncodeToString(data), nil } -func (t *Tokens) ParseIDToken() (*IDToken, error) { - return NewIDToken(t.IDToken) -} - func TokensFromBase64String(encoded string) (*Tokens, error) { decoded, err := base64.URLEncoding.DecodeString(encoded) if err != nil { diff --git a/pkg/oidc/tokens_test.go b/pkg/oidc/tokens_test.go index 3191f97..a7c5e13 100644 --- a/pkg/oidc/tokens_test.go +++ b/pkg/oidc/tokens_test.go @@ -4,7 +4,6 @@ import ( "bytes" "encoding/json" "testing" - "time" "github.com/stretchr/testify/assert" "github.com/stretchr/testify/require" @@ -70,23 +69,4 @@ func TestTokens(t *testing.T) { assert.Equal(t, "eyJ0eXAiOiJKV1QiLCJraWQiOiJ0ZDBTbWRKUTRxUGg1cU5Lek0yNjBDWHgyVWgtd2hHLU1Eam9PS1dmdDhFIiwiYWxnIjoiUlMyNTYifQ.eyJpc3MiOiJodHRwOi8vZ2RrLnRlc3Q6MzAwMCIsInN1YiI6IjEiLCJhdWQiOiJlMzFlMWRhMGI4ZjZiNmUzNWNhNzBjNzkwYjEzYzA0MDZlNDRhY2E2YjJiZjY3ZjU1ZGU3MzU1YTk3OWEyMjRmIiwiZXhwIjoxNzQ0NzM3NDI3LCJpYXQiOjE3NDQ3MzczMDcsImF1dGhfdGltZSI6MTc0NDczNDY0OSwic3ViX2xlZ2FjeSI6IjI0NzRjZjBiMjIxMTY4OGE1NzI5N2FjZTBlMjYwYTE1OTQ0NzU0ZDE2YjFiZDQyYzlkNjc3OWM5MDAzNjc4MDciLCJuYW1lIjoiQWRtaW5pc3RyYXRvciIsIm5pY2tuYW1lIjoicm9vdCIsInByZWZlcnJlZF91c2VybmFtZSI6InJvb3QiLCJlbWFpbCI6ImFkbWluQGV4YW1wbGUuY29tIiwiZW1haWxfdmVyaWZpZWQiOnRydWUsInByb2ZpbGUiOiJodHRwOi8vZ2RrLnRlc3Q6MzAwMC9yb290IiwicGljdHVyZSI6Imh0dHBzOi8vd3d3LmdyYXZhdGFyLmNvbS9hdmF0YXIvMjU4ZDhkYzkxNmRiOGNlYTJjYWZiNmMzY2QwY2IwMjQ2ZWZlMDYxNDIxZGJkODNlYzNhMzUwNDI4Y2FiZGE0Zj9zPTgwJmQ9aWRlbnRpY29uIiwiZ3JvdXBzX2RpcmVjdCI6WyJ0b29sYm94IiwiZ2l0bGFiLW9yZyIsImdudXdnZXQiLCJDb21taXQ0NTEiLCJqYXNoa2VuYXMiLCJmbGlnaHRqcyIsInR3aXR0ZXIiLCJnaXRsYWItZXhhbXBsZXMiLCJnaXRsYWItZXhhbXBsZXMvc2VjdXJpdHkiLCI0MTI3MDgiLCJnaXRsYWItZXhhbXBsZXMvZGVtby1ncm91cCIsImN1c3RvbS1yb2xlcy1yb290LWdyb3VwIiwiNDM0MDQ0LWdyb3VwLTEiLCI0MzQwNDQtZ3JvdXAtMiIsImdpdGxhYi1vcmcxIiwiZ2l0bGFiLW9yZy9zZWN1cmUiLCJnaXRsYWItb3JnL3NlY3VyZS9tYW5hZ2VycyIsImdpdGxhYi1vcmcvc2VjdXJpdHktcHJvZHVjdHMiLCJnaXRsYWItb3JnL3NlY3VyaXR5LXByb2R1Y3RzL2FuYWx5emVycyIsImN1c3RvbS1yb2xlcy1yb290LWdyb3VwL2FhIiwiY3VzdG9tLXJvbGVzLXJvb3QtZ3JvdXAvYWEvYWFhIiwibWFzc19pbnNlcnRfZ3JvdXBfXzBfMTAwIl19.SZu_l7tQ2Kkeogq0z8cRaDWPfv52JTo-RkiExbnud_lrfrXXneS77BIzaGKX_bzq4SM_oO_Q63AzK66B1r6Gp7ACo4DjOUEIWETg7ZBKcDzEZnresB7kmI_MJ5rfIJTmnH75GOfc_pl5l8T896TbaShN6zSpaXXIVEfhyUrflSWb4hhA7Hbwy2b6laXiaDv0qpcn1udPVYMTsll8I5ni_2yzuEPSVRgrcQoQ46OwVDZIi9tlfdT2qNVjH6FxJ3mkBcxtIVjf3_JYAawFEscg2uvQYwFWj9T6LleMknAh3QFJJMrS6mPqlXJGPUE5pTQgsBInfEikfm9PXxezA-IY6g", result.IDToken) }) }) - - t.Run("ParseIDToken", func(t *testing.T) { - tokens := &Tokens{IDToken: "eyJ0eXAiOiJKV1QiLCJraWQiOiJ0ZDBTbWRKUTRxUGg1cU5Lek0yNjBDWHgyVWgtd2hHLU1Eam9PS1dmdDhFIiwiYWxnIjoiUlMyNTYifQ.eyJpc3MiOiJodHRwOi8vZ2RrLnRlc3Q6MzAwMCIsInN1YiI6IjEiLCJhdWQiOiJlMzFlMWRhMGI4ZjZiNmUzNWNhNzBjNzkwYjEzYzA0MDZlNDRhY2E2YjJiZjY3ZjU1ZGU3MzU1YTk3OWEyMjRmIiwiZXhwIjoxNzQ0NzM3NDI3LCJpYXQiOjE3NDQ3MzczMDcsImF1dGhfdGltZSI6MTc0NDczNDY0OSwic3ViX2xlZ2FjeSI6IjI0NzRjZjBiMjIxMTY4OGE1NzI5N2FjZTBlMjYwYTE1OTQ0NzU0ZDE2YjFiZDQyYzlkNjc3OWM5MDAzNjc4MDciLCJuYW1lIjoiQWRtaW5pc3RyYXRvciIsIm5pY2tuYW1lIjoicm9vdCIsInByZWZlcnJlZF91c2VybmFtZSI6InJvb3QiLCJlbWFpbCI6ImFkbWluQGV4YW1wbGUuY29tIiwiZW1haWxfdmVyaWZpZWQiOnRydWUsInByb2ZpbGUiOiJodHRwOi8vZ2RrLnRlc3Q6MzAwMC9yb290IiwicGljdHVyZSI6Imh0dHBzOi8vd3d3LmdyYXZhdGFyLmNvbS9hdmF0YXIvMjU4ZDhkYzkxNmRiOGNlYTJjYWZiNmMzY2QwY2IwMjQ2ZWZlMDYxNDIxZGJkODNlYzNhMzUwNDI4Y2FiZGE0Zj9zPTgwJmQ9aWRlbnRpY29uIiwiZ3JvdXBzX2RpcmVjdCI6WyJ0b29sYm94IiwiZ2l0bGFiLW9yZyIsImdudXdnZXQiLCJDb21taXQ0NTEiLCJqYXNoa2VuYXMiLCJmbGlnaHRqcyIsInR3aXR0ZXIiLCJnaXRsYWItZXhhbXBsZXMiLCJnaXRsYWItZXhhbXBsZXMvc2VjdXJpdHkiLCI0MTI3MDgiLCJnaXRsYWItZXhhbXBsZXMvZGVtby1ncm91cCIsImN1c3RvbS1yb2xlcy1yb290LWdyb3VwIiwiNDM0MDQ0LWdyb3VwLTEiLCI0MzQwNDQtZ3JvdXAtMiIsImdpdGxhYi1vcmcxIiwiZ2l0bGFiLW9yZy9zZWN1cmUiLCJnaXRsYWItb3JnL3NlY3VyZS9tYW5hZ2VycyIsImdpdGxhYi1vcmcvc2VjdXJpdHktcHJvZHVjdHMiLCJnaXRsYWItb3JnL3NlY3VyaXR5LXByb2R1Y3RzL2FuYWx5emVycyIsImN1c3RvbS1yb2xlcy1yb290LWdyb3VwL2FhIiwiY3VzdG9tLXJvbGVzLXJvb3QtZ3JvdXAvYWEvYWFhIiwibWFzc19pbnNlcnRfZ3JvdXBfXzBfMTAwIl19.SZu_l7tQ2Kkeogq0z8cRaDWPfv52JTo-RkiExbnud_lrfrXXneS77BIzaGKX_bzq4SM_oO_Q63AzK66B1r6Gp7ACo4DjOUEIWETg7ZBKcDzEZnresB7kmI_MJ5rfIJTmnH75GOfc_pl5l8T896TbaShN6zSpaXXIVEfhyUrflSWb4hhA7Hbwy2b6laXiaDv0qpcn1udPVYMTsll8I5ni_2yzuEPSVRgrcQoQ46OwVDZIi9tlfdT2qNVjH6FxJ3mkBcxtIVjf3_JYAawFEscg2uvQYwFWj9T6LleMknAh3QFJJMrS6mPqlXJGPUE5pTQgsBInfEikfm9PXxezA-IY6g"} - - idToken, err := tokens.ParseIDToken() - require.NoError(t, err) - - assert.Equal(t, "e31e1da0b8f6b6e35ca70c790b13c0406e44aca6b2bf67f55de7355a979a224f", idToken.Audience) - assert.Equal(t, "admin@example.com", idToken.Email) - assert.Equal(t, true, idToken.EmailVerified) - assert.Equal(t, int64(1744737427), idToken.ExpiredAt) - assert.Equal(t, int64(1744737307), idToken.IssuedAt) - assert.Equal(t, "http://gdk.test:3000", idToken.Issuer) - assert.Equal(t, "Administrator", idToken.Name) - assert.Equal(t, "root", idToken.Nickname) - assert.Equal(t, "https://www.gravatar.com/avatar/258d8dc916db8cea2cafb6c3cd0cb0246efe061421dbd83ec3a350428cabda4f?s=80&d=identicon", idToken.Picture) - assert.Equal(t, "1", idToken.Subject) - assert.Equal(t, time.Time{}, idToken.UpdatedAt) - }) } diff --git a/pkg/test/oidc_server.go b/pkg/test/oidc_server.go new file mode 100644 index 0000000..142d143 --- /dev/null +++ b/pkg/test/oidc_server.go @@ -0,0 +1,61 @@ +package test + +import ( + "net/http" + "net/http/httptest" + "time" + + "github.com/xlgmokha/x/pkg/serde" +) + +func OIDCServer() *httptest.Server { + srv := httptest.NewServer(nil) + srv.Config = &http.Server{ + Handler: http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { + switch r.URL.Path { + case "/.well-known/openid-configuration": + metadata := map[string]interface{}{ + "authorization_endpoint": srv.URL + "/oauth/authorize", + "claims_supported": []string{"aud"}, + "code_challenge_methods_supported": []string{"plain"}, + "device_authorization_endpoint": srv.URL + "/device/authorize", + "id_token_signing_alg_values_supported": []string{"RS256"}, + "issuer": srv.URL, + "jwks_uri": srv.URL + "/jwks", + "mfa_challenge_endpoint": srv.URL + "/mfa", + "registration_endpoint": srv.URL + "/users/new", + "request_uri_parameter_supported": false, + "response_modes_supported": []string{"query"}, + "response_types_supported": []string{"code"}, + "revocation_endpoint": srv.URL + "/revoke", + "scopes_supported": []string{"oidc"}, + "subject_types_supported": []string{"public"}, + "token_endpoint": srv.URL + "/token", + "token_endpoint_auth_methods_supported": []string{"client_secret_post"}, + "userinfo_endpoint": srv.URL + "/users/me", + } + + serde.ToJSON(w, metadata) + case "/token": + if err := r.ParseForm(); err != nil { + w.WriteHeader(http.StatusBadRequest) + return + } + if r.Form["grant_type"][0] == "authorization_code" && r.Form["code"][0] == "code" { + w.Header().Add("Content-Type", "application/json") + serde.ToJSON(w, map[string]string{ + "access_token": "14fa6e71afaabbe5e31ef2b47ccab7ca7a3c26f8dfdb74acce3eca30099af028", + "token_type": "Bearer", + "refresh_token": "365b261d4b25ba37e7c1e14e6501902aeecfb7fffc4602c44d6ac22b4c715b0f", + // "expiry": "2025-04-15T19:16:38.78960504-06:00" + "expiry": time.Now().Add(1 * time.Hour).Format(time.RFC3339), + "id_token": "eyJ0eXAiOiJKV1QiLCJraWQiOiJ0ZDBTbWRKUTRxUGg1cU5Lek0yNjBDWHgyVWgtd2hHLU1Eam9PS1dmdDhFIiwiYWxnIjoiUlMyNTYifQ.eyJpc3MiOiJodHRwOi8vZ2RrLnRlc3Q6MzAwMCIsInN1YiI6IjEiLCJhdWQiOiJlMzFlMWRhMGI4ZjZiNmUzNWNhNzBjNzkwYjEzYzA0MDZlNDRhY2E2YjJiZjY3ZjU1ZGU3MzU1YTk3OWEyMjRmIiwiZXhwIjoxNzQ0NzM3NDI3LCJpYXQiOjE3NDQ3MzczMDcsImF1dGhfdGltZSI6MTc0NDczNDY0OSwic3ViX2xlZ2FjeSI6IjI0NzRjZjBiMjIxMTY4OGE1NzI5N2FjZTBlMjYwYTE1OTQ0NzU0ZDE2YjFiZDQyYzlkNjc3OWM5MDAzNjc4MDciLCJuYW1lIjoiQWRtaW5pc3RyYXRvciIsIm5pY2tuYW1lIjoicm9vdCIsInByZWZlcnJlZF91c2VybmFtZSI6InJvb3QiLCJlbWFpbCI6ImFkbWluQGV4YW1wbGUuY29tIiwiZW1haWxfdmVyaWZpZWQiOnRydWUsInByb2ZpbGUiOiJodHRwOi8vZ2RrLnRlc3Q6MzAwMC9yb290IiwicGljdHVyZSI6Imh0dHBzOi8vd3d3LmdyYXZhdGFyLmNvbS9hdmF0YXIvMjU4ZDhkYzkxNmRiOGNlYTJjYWZiNmMzY2QwY2IwMjQ2ZWZlMDYxNDIxZGJkODNlYzNhMzUwNDI4Y2FiZGE0Zj9zPTgwJmQ9aWRlbnRpY29uIiwiZ3JvdXBzX2RpcmVjdCI6WyJ0b29sYm94IiwiZ2l0bGFiLW9yZyIsImdudXdnZXQiLCJDb21taXQ0NTEiLCJqYXNoa2VuYXMiLCJmbGlnaHRqcyIsInR3aXR0ZXIiLCJnaXRsYWItZXhhbXBsZXMiLCJnaXRsYWItZXhhbXBsZXMvc2VjdXJpdHkiLCI0MTI3MDgiLCJnaXRsYWItZXhhbXBsZXMvZGVtby1ncm91cCIsImN1c3RvbS1yb2xlcy1yb290LWdyb3VwIiwiNDM0MDQ0LWdyb3VwLTEiLCI0MzQwNDQtZ3JvdXAtMiIsImdpdGxhYi1vcmcxIiwiZ2l0bGFiLW9yZy9zZWN1cmUiLCJnaXRsYWItb3JnL3NlY3VyZS9tYW5hZ2VycyIsImdpdGxhYi1vcmcvc2VjdXJpdHktcHJvZHVjdHMiLCJnaXRsYWItb3JnL3NlY3VyaXR5LXByb2R1Y3RzL2FuYWx5emVycyIsImN1c3RvbS1yb2xlcy1yb290LWdyb3VwL2FhIiwiY3VzdG9tLXJvbGVzLXJvb3QtZ3JvdXAvYWEvYWFhIiwibWFzc19pbnNlcnRfZ3JvdXBfXzBfMTAwIl19.SZu_l7tQ2Kkeogq0z8cRaDWPfv52JTo-RkiExbnud_lrfrXXneS77BIzaGKX_bzq4SM_oO_Q63AzK66B1r6Gp7ACo4DjOUEIWETg7ZBKcDzEZnresB7kmI_MJ5rfIJTmnH75GOfc_pl5l8T896TbaShN6zSpaXXIVEfhyUrflSWb4hhA7Hbwy2b6laXiaDv0qpcn1udPVYMTsll8I5ni_2yzuEPSVRgrcQoQ46OwVDZIi9tlfdT2qNVjH6FxJ3mkBcxtIVjf3_JYAawFEscg2uvQYwFWj9T6LleMknAh3QFJJMrS6mPqlXJGPUE5pTQgsBInfEikfm9PXxezA-IY6g", + }) + } + default: + w.WriteHeader(http.StatusNotFound) + } + }), + } + return srv +} diff --git a/pkg/web/middleware/unpack_token.go b/pkg/web/middleware/unpack_token.go index b53d5d3..f3d20a0 100644 --- a/pkg/web/middleware/unpack_token.go +++ b/pkg/web/middleware/unpack_token.go @@ -1,16 +1,14 @@ package middleware import ( + "fmt" "net/http" - "github.com/xlgmokha/x/pkg/context" "github.com/xlgmokha/x/pkg/log" "gitlab.com/gitlab-org/software-supply-chain-security/authorization/sparkled/pkg/oidc" ) -var IDTokenContextKey context.Key[*oidc.IDToken] = context.Key[*oidc.IDToken]("id_token") - -func UnpackToken() func(http.Handler) http.Handler { +func UnpackToken(cfg *oidc.OpenID) func(http.Handler) http.Handler { return func(next http.Handler) http.Handler { return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { cookies := r.CookiesNamed("session") @@ -21,8 +19,11 @@ func UnpackToken() func(http.Handler) http.Handler { return } - idToken, err := tokens.ParseIDToken() + ctx := r.Context() + verifier := cfg.Provider.VerifierContext(ctx, cfg.OIDCConfig) + idToken, err := verifier.Verify(ctx, tokens.IDToken) if err != nil { + fmt.Printf("%v\n", err) next.ServeHTTP(w, r) return } @@ -30,7 +31,7 @@ func UnpackToken() func(http.Handler) http.Handler { log.WithFields(r.Context(), log.Fields{"id_token": idToken}) next.ServeHTTP( w, - r.WithContext(IDTokenContextKey.With(r.Context(), idToken)), + r.WithContext(oidc.IDTokenKey.With(r.Context(), idToken)), ) } else { next.ServeHTTP(w, r) diff --git a/pkg/web/middleware/unpack_token_test.go b/pkg/web/middleware/unpack_token_test.go index a6f591e..ac3d50c 100644 --- a/pkg/web/middleware/unpack_token_test.go +++ b/pkg/web/middleware/unpack_token_test.go @@ -1,6 +1,7 @@ package middleware import ( + "context" "net/http" "testing" "time" @@ -14,7 +15,13 @@ import ( ) func TestUnpackToken(t *testing.T) { - middleware := UnpackToken() + srv := test.OIDCServer() + defer srv.Close() + + openID, err := oidc.New(context.Background(), srv.URL, "client_id", "client_secret", "https://example.com/oauth/callback") + require.NoError(t, err) + + middleware := UnpackToken(openID) t.Run("when an active session cookie is provided", func(t *testing.T) { t.Run("attaches the token to the request context", func(t *testing.T) { @@ -22,9 +29,9 @@ func TestUnpackToken(t *testing.T) { encoded := x.Must(tokens.ToBase64String()) server := middleware(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { - token := IDTokenContextKey.From(r.Context()) + token := oidc.IDTokenKey.From(r.Context()) require.NotNil(t, token) - assert.Equal(t, "root", token.Nickname) + assert.Equal(t, "root", token.Issuer) w.WriteHeader(http.StatusTeapot) })) @@ -43,7 +50,7 @@ func TestUnpackToken(t *testing.T) { t.Run("when an invalid session cookie is provided", func(t *testing.T) { t.Run("forwards the request", func(t *testing.T) { server := middleware(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { - require.Nil(t, IDTokenContextKey.From(r.Context())) + require.Nil(t, oidc.IDTokenKey.From(r.Context())) w.WriteHeader(http.StatusTeapot) })) @@ -62,7 +69,7 @@ func TestUnpackToken(t *testing.T) { t.Run("when no cookies are provided", func(t *testing.T) { t.Run("forwards the request", func(t *testing.T) { server := middleware(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { - require.Nil(t, IDTokenContextKey.From(r.Context())) + require.Nil(t, oidc.IDTokenKey.From(r.Context())) w.WriteHeader(http.StatusTeapot) })) |
