|
4 | 4 | "context" |
5 | 5 | "crypto/rand" |
6 | 6 | "crypto/rsa" |
| 7 | + "crypto/sha512" |
| 8 | + "encoding/base64" |
7 | 9 | "encoding/json" |
8 | 10 | "log/slog" |
9 | 11 | "net/http" |
@@ -488,6 +490,16 @@ func TestAccessTokenHash(t *testing.T) { |
488 | 490 | } |
489 | 491 | } |
490 | 492 |
|
| 493 | +func TestAccessTokenHashEdDSA(t *testing.T) { |
| 494 | + atHash, err := accessTokenHash(jose.EdDSA, googleAccessToken) |
| 495 | + require.NoError(t, err) |
| 496 | + |
| 497 | + // EdDSA (Ed25519) uses SHA-512; at_hash is the base64url of the left-most half. |
| 498 | + sum := sha512.Sum512([]byte(googleAccessToken)) |
| 499 | + want := base64.RawURLEncoding.EncodeToString(sum[:len(sum)/2]) |
| 500 | + require.Equal(t, want, atHash) |
| 501 | +} |
| 502 | + |
491 | 503 | func TestValidRedirectURI(t *testing.T) { |
492 | 504 | tests := []struct { |
493 | 505 | client storage.Client |
@@ -807,6 +819,31 @@ func TestSignerKeySetWithES256LocalSigner(t *testing.T) { |
807 | 819 | require.Equal(t, []byte("payload"), payload) |
808 | 820 | } |
809 | 821 |
|
| 822 | +func TestSignerKeySetWithEdDSALocalSigner(t *testing.T) { |
| 823 | + ctx, cancel := context.WithCancel(context.Background()) |
| 824 | + defer cancel() |
| 825 | + |
| 826 | + logger := slog.New(slog.DiscardHandler) |
| 827 | + store := memory.New(logger) |
| 828 | + |
| 829 | + localConfig := signer.LocalConfig{ |
| 830 | + KeysRotationPeriod: time.Hour.String(), |
| 831 | + Algorithm: jose.EdDSA, |
| 832 | + } |
| 833 | + sig, err := localConfig.Open(ctx, store, time.Hour, time.Now, logger) |
| 834 | + require.NoError(t, err) |
| 835 | + |
| 836 | + sig.Start(ctx) |
| 837 | + |
| 838 | + jwt, err := sig.Sign(ctx, []byte("payload")) |
| 839 | + require.NoError(t, err) |
| 840 | + |
| 841 | + keySet := &signerKeySet{signer: sig} |
| 842 | + payload, err := keySet.VerifySignature(ctx, jwt) |
| 843 | + require.NoError(t, err) |
| 844 | + require.Equal(t, []byte("payload"), payload) |
| 845 | +} |
| 846 | + |
810 | 847 | func TestRedirectedAuthErrHandler(t *testing.T) { |
811 | 848 | tests := []struct { |
812 | 849 | name string |
@@ -1006,6 +1043,48 @@ func TestValidateIDTokenHint(t *testing.T) { |
1006 | 1043 | }) |
1007 | 1044 | } |
1008 | 1045 |
|
| 1046 | +// TestValidateIDTokenHintEdDSA drives the real validateIDTokenHint verifier path |
| 1047 | +// with an EdDSA local signer. Without SupportedSigningAlgs on the oidc.Config, |
| 1048 | +// go-oidc defaults to RS256 only and rejects the EdDSA token as "malformed jwt". |
| 1049 | +func TestValidateIDTokenHintEdDSA(t *testing.T) { |
| 1050 | + ctx, cancel := context.WithCancel(context.Background()) |
| 1051 | + defer cancel() |
| 1052 | + |
| 1053 | + logger := slog.New(slog.DiscardHandler) |
| 1054 | + store := memory.New(logger) |
| 1055 | + |
| 1056 | + localConfig := signer.LocalConfig{ |
| 1057 | + KeysRotationPeriod: time.Hour.String(), |
| 1058 | + Algorithm: jose.EdDSA, |
| 1059 | + } |
| 1060 | + sig, err := localConfig.Open(ctx, store, time.Hour, time.Now, logger) |
| 1061 | + require.NoError(t, err) |
| 1062 | + sig.Start(ctx) |
| 1063 | + |
| 1064 | + issuerURL, err := url.Parse("https://issuer.example.com") |
| 1065 | + require.NoError(t, err) |
| 1066 | + |
| 1067 | + s := &Server{ |
| 1068 | + signer: sig, |
| 1069 | + issuerURL: *issuerURL, |
| 1070 | + logger: slog.Default(), |
| 1071 | + } |
| 1072 | + |
| 1073 | + payload, err := json.Marshal(idTokenClaims{ |
| 1074 | + Issuer: "https://issuer.example.com", |
| 1075 | + Subject: "CgNmb28SA2Jhcg", |
| 1076 | + Expiry: time.Now().Add(time.Hour).Unix(), |
| 1077 | + }) |
| 1078 | + require.NoError(t, err) |
| 1079 | + |
| 1080 | + token, err := sig.Sign(ctx, payload) |
| 1081 | + require.NoError(t, err) |
| 1082 | + |
| 1083 | + idToken, err := s.validateIDTokenHint(ctx, token) |
| 1084 | + require.NoError(t, err) |
| 1085 | + assert.Equal(t, "CgNmb28SA2Jhcg", idToken.Subject) |
| 1086 | +} |
| 1087 | + |
1009 | 1088 | func TestNewIDTokenUsesStoredAlgorithmUntilNextRotation(t *testing.T) { |
1010 | 1089 | ctx, cancel := context.WithCancel(context.Background()) |
1011 | 1090 | defer cancel() |
|
0 commit comments