core/jwt_test.go

187 lines
5.1 KiB
Go

package core
import (
"fmt"
"testing"
"time"
)
func TestNewJWT(t *testing.T) {
j := newJWT(JWTOptions{
SigningKey: "testsigning",
LifetimeMinutes: 2,
})
if fmt.Sprintf("%T", j) != "*core.JWT" {
t.Errorf("failed testing new jwt")
}
}
func TestResolveJWT(t *testing.T) {
initiateJWTHelper(t)
j := resolveJWT()
if fmt.Sprintf("%T", j) != "*core.JWT" {
t.Errorf("failed testing resolve jwt")
}
}
func TestGenerateToken(t *testing.T) {
j := initiateJWTHelper(t)
token, err := j.GenerateToken(map[string]interface{}{
"testKey": "testVal",
})
if err != nil || token == "" {
t.Errorf("error testing generate jwt token")
}
d, err := j.DecodeToken(token)
if err != nil {
t.Errorf("error testing generate jwt token: %v", err.Error())
}
if d["testKey"] != "testVal" {
t.Errorf("error testing generate jwt token: %v", err.Error())
}
}
func TestDecodeToken(t *testing.T) {
expiredToken := "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJKIjoiZXlKMFpYTjBTMlY1SWpvaWRHVnpkRlpoYkNKOSIsImV4cCI6MTY4NDkyMzQwOX0.v2aM9OTDJ48L4KnGjfLH3JAFQw4Gkgj5z7cA7txPNag"
j := initiateJWTHelper(t)
_, err := j.DecodeToken(expiredToken)
if err == nil {
t.Errorf("failed test decode token")
}
token, err := j.GenerateToken(map[string]interface{}{
"testKey": "testVal",
})
if err != nil || token == "" {
t.Errorf("failed testing decode token")
}
d, err := j.DecodeToken(token)
if err != nil {
t.Errorf("error testing decode jwt token")
}
if d["testKey"] != "testVal" {
t.Errorf("error testing decode jwt token")
}
d, err = j.DecodeToken("test-token")
if err == nil {
t.Errorf("error testing decode jwt token")
}
}
func TestHasExpired(t *testing.T) {
expiredToken := "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJKIjoiZXlKMFpYTjBTMlY1SWpvaWRHVnpkRlpoYkNKOSIsImV4cCI6MTY4NDkyMzQwOX0.v2aM9OTDJ48L4KnGjfLH3JAFQw4Gkgj5z7cA7txPNag"
j := initiateJWTHelper(t)
tokenHasExpired, err := j.HasExpired(expiredToken)
if !tokenHasExpired {
t.Errorf("failed test token has expired check")
}
if tokenHasExpired && err != nil {
t.Errorf("failed test decode token: %v", err.Error())
}
token, err := j.GenerateToken(map[string]interface{}{
"testKey": "testVal",
})
if err != nil || token == "" {
t.Errorf("failed testing decode token")
}
_, err = j.HasExpired(token)
if err != nil {
t.Errorf("error testing decode jwt token")
}
}
func TestMapClaims(t *testing.T) {
c, err := mapClaims(map[string]interface{}{
"testKey": "testVal",
}, time.Now())
if err != nil {
t.Errorf("failed testing map claims")
}
if fmt.Sprintf("%T", c) != "core.claims" {
t.Errorf("failed testing map claims")
}
}
func TestLifetimeMinutes(t *testing.T) {
j := newJWT(JWTOptions{
SigningKey: "testsigning",
LifetimeMinutes: 42,
})
if j.LifetimeMinutes() != 42 {
t.Errorf("expected lifetime 42, got %d", j.LifetimeMinutes())
}
}
func TestExpiresAtIgnoreExpiry(t *testing.T) {
j := initiateJWTHelper(t)
token, err := j.GenerateToken(map[string]interface{}{
"userID": 1,
})
if err != nil {
t.Fatalf("failed generating token: %v", err)
}
exp, err := j.ExpiresAtIgnoreExpiry(token)
if err != nil {
t.Fatalf("failed testing expires at ignore expiry: %v", err)
}
expected := time.Now().Add(time.Duration(j.LifetimeMinutes()) * time.Minute)
if diff := exp.Sub(expected); diff > time.Minute || diff < -time.Minute {
t.Errorf("expected expiration close to %v, got %v", expected, exp)
}
// An expired token must still return its expiration (no validation performed).
expiredToken := "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJKIjoiZXlKMFpYTjBTMlY1SWpvaWRHVnpkRlpoYkNKOSIsImV4cCI6MTY4NDkyMzQwOX0.v2aM9OTDJ48L4KnGjfLH3JAFQw4Gkgj5z7cA7txPNag"
_, err = j.ExpiresAtIgnoreExpiry(expiredToken)
if err != nil {
t.Errorf("expected to read expiration of an expired token, got error: %v", err)
}
}
func TestExpiresAtIgnoreExpiryInvalid(t *testing.T) {
j := initiateJWTHelper(t)
_, err := j.ExpiresAtIgnoreExpiry("not-a-token")
if err == nil {
t.Errorf("expected error for an invalid token")
}
}
func TestDecodeTokenIgnoreExpiry(t *testing.T) {
j := initiateJWTHelper(t)
// An already expired token should still be decodable.
expiredToken := "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJKIjoiZXlKMFpYTjBTMlY1SWpvaWRHVnpkRlpoYkNKOSIsImV4cCI6MTY4NDkyMzQwOX0.v2aM9OTDJ48L4KnGjfLH3JAFQw4Gkgj5z7cA7txPNag"
_, err := j.DecodeTokenIgnoreExpiry(expiredToken)
if err != nil {
t.Errorf("expected to decode an expired token ignoring expiry, got: %v", err)
}
token, err := j.GenerateToken(map[string]interface{}{
"userID": 99,
})
if err != nil {
t.Fatalf("failed generating token: %v", err)
}
payload, err := j.DecodeTokenIgnoreExpiry(token)
if err != nil {
t.Fatalf("failed decoding token ignoring expiry: %v", err)
}
if fmt.Sprintf("%v", payload["userID"]) != "99" {
t.Errorf("expected userID 99, got %v", payload["userID"])
}
// An invalid token must fail.
if _, err := j.DecodeTokenIgnoreExpiry("invalid"); err == nil {
t.Errorf("expected error decoding an invalid token")
}
}
func initiateJWTHelper(t *testing.T) *JWT {
t.Helper()
j := newJWT(JWTOptions{
SigningKey: "testsigning",
LifetimeMinutes: 2,
})
return j
}