Skip to content

Instantly share code, notes, and snippets.

@kvedala
Created May 27, 2022 21:03
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save kvedala/ff4d9dfd8e9bc24c7644a64fd6ea3030 to your computer and use it in GitHub Desktop.
Save kvedala/ff4d9dfd8e9bc24c7644a64fd6ea3030 to your computer and use it in GitHub Desktop.
Generating JWT Tokens with random secret key in golang
package main
import (
"crypto/hmac"
"crypto/sha512"
"fmt"
"log"
"math/rand"
"time"
"github.com/golang-jwt/jwt"
)
// For HMAC signing method, the key can be any []byte. It is recommended to generate
// a key using crypto/rand or something equivalent. You need the same key for signing
// and validating.
// const hash.Hash hmacSampleSecret = hmac.New(sha512.New, []byte("my_secret_key"))
var hmacSampleSecret []byte
func ValidMAC(key []byte) {
mac := hmac.New(sha512.New, key)
hmacSampleSecret = mac.Sum(nil)
}
func generateKey() (string, error) {
// Create a new token object, specifying signing method and the claims
// you would like it to contain.
token := jwt.NewWithClaims(jwt.SigningMethodHS512, jwt.MapClaims{
"foo": "bar",
"nbf": time.Now().Unix(),
})
// Sign and get the complete encoded token as a string using the secret
tokenString, err := token.SignedString(hmacSampleSecret)
return tokenString, err
}
func RandomString(n int) string {
var letters = []rune("abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789")
s := make([]rune, n)
for i := range s {
s[i] = letters[rand.Intn(len(letters))]
}
return string(s)
}
func main() {
rand.Seed(time.Now().UnixNano())
ValidMAC([]byte("Awes0meness!"))
// ValidMAC([]byte(RandomString(32)))
log.Println("New key: ", string(hmacSampleSecret))
// sample token string taken from the New example
tokenString, _ := generateKey()
log.Println("Token: ", tokenString)
// Parse takes the token string and a function for looking up the key. The latter is especially
// useful if you use multiple keys for your application. The standard is to use 'kid' in the
// head of the token to identify which key to use, but the parsed token (head and claims) is provided
// to the callback, providing flexibility.
token, err := jwt.Parse(tokenString, func(token *jwt.Token) (interface{}, error) {
// Don't forget to validate the alg is what you expect:
if _, ok := token.Method.(*jwt.SigningMethodHMAC); !ok {
return nil, fmt.Errorf("Unexpected signing method: %v", token.Header["alg"])
}
// hmacSampleSecret is a []byte containing your secret, e.g. []byte("my_secret_key")
return hmacSampleSecret, nil
})
if claims, ok := token.Claims.(jwt.MapClaims); ok && token.Valid {
log.Println(claims["foo"], claims["nbf"])
} else {
log.Println(err)
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment