simplejwt

module
v0.0.0-...-2df4315 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Aug 3, 2026 License: MIT

README

simplejwt

A small Go library for generating JWKs and signing/encrypting/verifying/decrypting typed payloads as JWS/JWE, built on top of go-jose.

Each Go type you want to serialize gets its own JwtTokenConfig (which key to sign/encrypt with, and which algorithms to use), registered on a ConfigResolver. A Manager combines that ConfigResolver with a KeyStore of JWKs to serialize and parse tokens.

Installation

go get github.com/index0h/simplejwt@latest
# or
go get -tool github.com/index0h/simplejwt/cmd/simplejwt

Concepts

  • KeyGenerator — generates a *jose.JSONWebKey for a given key ID and JWA algorithm (RSA/RSA-PSS, ECDSA, EdDSA, HMAC and symmetric key-wrapping algorithms for JWE).
  • KeyStore — an in-memory collection of JWKs, keyed by KeyID. Supports looking up a key by exact ID (GetById, used to verify/decrypt) or the newest key with a given prefix (GetNewest, used to sign/encrypt with key rotation in mind — see Key rotation).
  • ConfigResolver — maps a Go type to its JwtTokenConfig (which KeyID prefix and algorithm to sign/encrypt with). Register one entry per token type with Register, look it up with Resolve, or iterate all of them with All.
  • Manager — wraps a KeyStore and a ConfigResolver and exposes SerializeJws/UnserializeJws (JWS, signed) and SerializeJwe/UnserializeJwe (JWE, encrypted) for any t any payload that is JSON-serializable.

Usage

package main

import (
	"fmt"

	"github.com/go-jose/go-jose/v4"

	"github.com/index0h/simplejwt/simplejwt"
)

type AccessToken struct {
	Subject string `json:"sub"`
}

func main() {
	// 1. Generate (or load) JWKs.
	generator := simplejwt.NewKeyGenerator()

	signKey, err := generator.Generate("access_20260803", string(jose.EdDSA))
	if err != nil {
		panic(err)
	}

	// 2. Put them in a KeyStore.
	keyStore := simplejwt.NewKeyStore([]*jose.JSONWebKey{signKey})

	// 3. Register a JwtTokenConfig per token type.
	configResolver := simplejwt.NewConfigResolver()
	configResolver.Register(&AccessToken{}, simplejwt.JwtTokenConfig{
		SignKeyId:     "access_", // GetNewest looks up the newest key with this prefix
		SignAlgorithm: jose.EdDSA,
	})

	// 4. Serialize / parse tokens through the Manager.
	manager := simplejwt.NewManager(keyStore, configResolver)

	token := &AccessToken{Subject: "user-1"}

	data, err := manager.SerializeJws(token)
	if err != nil {
		panic(err)
	}

	fmt.Println(string(data))

	parsed := &AccessToken{}
	if err := manager.UnserializeJws(data, parsed); err != nil {
		panic(err)
	}

	fmt.Println(parsed.Subject)
}

SerializeJwe/UnserializeJwe work the same way, driven by EncryptKeyId, EncryptKeyAlgorithm and EncryptContentAlgorithm on JwtTokenConfig.

Key rotation

KeyStore.GetNewest(prefix) returns the lexicographically greatest KeyID starting with prefix. The intended pattern is to suffix each generated key with a sortable date, e.g. access_20260803, and configure SignKeyId/EncryptKeyId in JwtTokenConfig with just the prefix (access_). Signing/encrypting always picks up the newest key for that prefix, while verifying/decrypting (GetById) works against any previously issued KeyID, so tokens signed with older keys remain valid until you drop them from the KeyStore.

CLI

cmd/simplejwt generates a new JWK and prints it as JSON:

go run ./cmd/simplejwt jwk-generate --key-id=access_20260803 --algorithm=EdDSA

Supported --algorithm values are any jose.SignatureAlgorithm/jose.KeyAlgorithm string accepted by KeyGenerator.Generate (see simplejwt/key_generator.go), e.g. EdDSA, RS256, RS384, RS512, PS256, PS384, PS512, ES256, ES384, ES512, HS256, HS384, HS512 for signing keys, and RSA1_5, RSA-OAEP, RSA-OAEP-256, A128KW, A192KW, A256KW, A128GCMKW, A192GCMKW, A256GCMKW, ECDH-ES, ECDH-ES+A128KW, ECDH-ES+A192KW, ECDH-ES+A256KW for encryption keys.

Development

go build ./...
go vet ./...
go test ./...

Directories

Path Synopsis
cmd
simplejwt command

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL