Files
kubelogin/pkg/adaptors/jwtdecoder/decoder_test.go
2020-02-21 09:58:01 +09:00

90 lines
2.4 KiB
Go

package jwtdecoder
import (
"crypto/rsa"
"crypto/x509"
"encoding/pem"
"io/ioutil"
"testing"
"time"
"github.com/dgrijalva/jwt-go"
)
func TestDecoder_Decode(t *testing.T) {
var decoder Decoder
t.Run("ValidToken", func(t *testing.T) {
expiry := time.Now().Round(time.Second)
idToken := newIDToken(t, "https://issuer.example.com", expiry)
decodedToken, err := decoder.Decode(idToken)
if err != nil {
t.Fatalf("Decode error: %s", err)
}
if decodedToken.Expiry != expiry {
t.Errorf("Expiry wants %s but got %s", expiry, decodedToken.Expiry)
}
if decodedToken.Subject != "SUBJECT" {
t.Errorf("Subject wants %s but got %s", "SUBJECT", decodedToken.Expiry)
}
t.Logf("Pretty=%+v", decodedToken.Pretty)
})
t.Run("InvalidToken", func(t *testing.T) {
decodedToken, err := decoder.Decode("HEADER.INVALID_TOKEN.SIGNATURE")
if err == nil {
t.Errorf("error wants non-nil but nil")
} else {
t.Logf("expected error: %+v", err)
}
if decodedToken != nil {
t.Errorf("decodedToken wants nil but %+v", decodedToken)
}
})
}
func newIDToken(t *testing.T, issuer string, expiry time.Time) string {
t.Helper()
var claims struct {
jwt.StandardClaims
// aud claim is either a string or an array of strings.
// https://tools.ietf.org/html/rfc7519#section-4.1.3
Audience []string `json:"aud"`
Nonce string `json:"nonce"`
Groups []string `json:"groups"`
EmailVerified bool `json:"email_verified"`
}
claims.Issuer = issuer
claims.Subject = "SUBJECT"
claims.IssuedAt = time.Now().Unix()
claims.ExpiresAt = expiry.Unix()
claims.Audience = []string{"kubernetes", "system"}
claims.Nonce = "NONCE"
claims.Groups = []string{"admin", "users"}
token := jwt.NewWithClaims(jwt.SigningMethodRS256, claims)
s, err := token.SignedString(readPrivateKey(t, "testdata/jws.key"))
if err != nil {
t.Fatalf("Could not sign the claims: %s", err)
}
return s
}
func readPrivateKey(t *testing.T, name string) *rsa.PrivateKey {
t.Helper()
b, err := ioutil.ReadFile(name)
if err != nil {
t.Fatalf("could not read the file: %s", err)
}
block, rest := pem.Decode(b)
if block == nil {
t.Fatalf("could not decode PEM")
}
if len(rest) > 0 {
t.Fatalf("PEM should contain single key but multiple keys")
}
k, err := x509.ParsePKCS1PrivateKey(block.Bytes)
if err != nil {
t.Fatalf("could not parse the key: %s", err)
}
return k
}