refactor: use struct types for claim related types (#283)
* oidc: add regression tests for token claim json this helps to verify that the same JSON is produced, after these types are refactored. * refactor: use struct types for claim related types BREAKING CHANGE: The following types are changed from interface to struct type: - AccessTokenClaims - IDTokenClaims - IntrospectionResponse - UserInfo and related types. The following methods of OPStorage now take a pointer to a struct type, instead of an interface: - SetUserinfoFromScopes - SetUserinfoFromToken - SetIntrospectionFromToken The following functions are now generic, so that type-safe extension of Claims is now possible: - op.VerifyIDTokenHint - op.VerifyAccessToken - rp.VerifyTokens - rp.VerifyIDToken - Changed UserInfoAddress to pointer in UserInfo and IntrospectionResponse. This was needed to make omitempty work correctly. - Copy or merge maps in IntrospectionResponse and SetUserInfo * op: add example for VerifyAccessToken * fix: rp: wrong assignment in WithIssuedAtMaxAge WithIssuedAtMaxAge assigned its value to v.maxAge, which was wrong. This change fixes that by assiging the duration to v.maxAgeIAT. * rp: add VerifyTokens example * oidc: add standard references to: - IDTokenClaims - IntrospectionResponse - UserInfo * only count coverage for `./pkg/...`
This commit is contained in:
parent
4bd2b742f9
commit
dea8bc96ea
55 changed files with 2358 additions and 1516 deletions
126
pkg/op/verifier_access_token_test.go
Normal file
126
pkg/op/verifier_access_token_test.go
Normal file
|
@ -0,0 +1,126 @@
|
|||
package op
|
||||
|
||||
import (
|
||||
"context"
|
||||
"testing"
|
||||
"time"
|
||||
|
||||
"github.com/stretchr/testify/assert"
|
||||
"github.com/stretchr/testify/require"
|
||||
tu "github.com/zitadel/oidc/v2/internal/testutil"
|
||||
"github.com/zitadel/oidc/v2/pkg/oidc"
|
||||
)
|
||||
|
||||
func TestNewAccessTokenVerifier(t *testing.T) {
|
||||
type args struct {
|
||||
issuer string
|
||||
keySet oidc.KeySet
|
||||
opts []AccessTokenVerifierOpt
|
||||
}
|
||||
tests := []struct {
|
||||
name string
|
||||
args args
|
||||
want AccessTokenVerifier
|
||||
}{
|
||||
{
|
||||
name: "simple",
|
||||
args: args{
|
||||
issuer: tu.ValidIssuer,
|
||||
keySet: tu.KeySet{},
|
||||
},
|
||||
want: &accessTokenVerifier{
|
||||
issuer: tu.ValidIssuer,
|
||||
keySet: tu.KeySet{},
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "with signature algorithm",
|
||||
args: args{
|
||||
issuer: tu.ValidIssuer,
|
||||
keySet: tu.KeySet{},
|
||||
opts: []AccessTokenVerifierOpt{
|
||||
WithSupportedAccessTokenSigningAlgorithms("ABC", "DEF"),
|
||||
},
|
||||
},
|
||||
want: &accessTokenVerifier{
|
||||
issuer: tu.ValidIssuer,
|
||||
keySet: tu.KeySet{},
|
||||
supportedSignAlgs: []string{"ABC", "DEF"},
|
||||
},
|
||||
},
|
||||
}
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
got := NewAccessTokenVerifier(tt.args.issuer, tt.args.keySet, tt.args.opts...)
|
||||
assert.Equal(t, tt.want, got)
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func TestVerifyAccessToken(t *testing.T) {
|
||||
verifier := &accessTokenVerifier{
|
||||
issuer: tu.ValidIssuer,
|
||||
maxAgeIAT: 2 * time.Minute,
|
||||
offset: time.Second,
|
||||
supportedSignAlgs: []string{string(tu.SignatureAlgorithm)},
|
||||
keySet: tu.KeySet{},
|
||||
}
|
||||
|
||||
tests := []struct {
|
||||
name string
|
||||
tokenClaims func() (string, *oidc.AccessTokenClaims)
|
||||
wantErr bool
|
||||
}{
|
||||
{
|
||||
name: "success",
|
||||
tokenClaims: tu.ValidAccessToken,
|
||||
},
|
||||
{
|
||||
name: "parse err",
|
||||
tokenClaims: func() (string, *oidc.AccessTokenClaims) { return "~~~~", nil },
|
||||
wantErr: true,
|
||||
},
|
||||
{
|
||||
name: "invalid signature",
|
||||
tokenClaims: func() (string, *oidc.AccessTokenClaims) { return tu.InvalidSignatureToken, nil },
|
||||
wantErr: true,
|
||||
},
|
||||
{
|
||||
name: "wrong issuer",
|
||||
tokenClaims: func() (string, *oidc.AccessTokenClaims) {
|
||||
return tu.NewAccessToken(
|
||||
"foo", tu.ValidSubject, tu.ValidAudience,
|
||||
tu.ValidExpiration, tu.ValidJWTID, tu.ValidClientID,
|
||||
tu.ValidSkew,
|
||||
)
|
||||
},
|
||||
wantErr: true,
|
||||
},
|
||||
{
|
||||
name: "expired",
|
||||
tokenClaims: func() (string, *oidc.AccessTokenClaims) {
|
||||
return tu.NewAccessToken(
|
||||
tu.ValidIssuer, tu.ValidSubject, tu.ValidAudience,
|
||||
tu.ValidExpiration.Add(-time.Hour), tu.ValidJWTID, tu.ValidClientID,
|
||||
tu.ValidSkew,
|
||||
)
|
||||
},
|
||||
wantErr: true,
|
||||
},
|
||||
}
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
token, want := tt.tokenClaims()
|
||||
|
||||
got, err := VerifyAccessToken[*oidc.AccessTokenClaims](context.Background(), token, verifier)
|
||||
if tt.wantErr {
|
||||
assert.Error(t, err)
|
||||
assert.Nil(t, got)
|
||||
return
|
||||
}
|
||||
require.NoError(t, err)
|
||||
require.NotNil(t, got)
|
||||
assert.Equal(t, got, want)
|
||||
})
|
||||
}
|
||||
}
|
Loading…
Add table
Add a link
Reference in a new issue