Skip to content

Instantly share code, notes, and snippets.

@rafaelcn
Created October 20, 2022 22:19
Show Gist options
  • Save rafaelcn/c481c79ef10ea39f946107b116e6777c to your computer and use it in GitHub Desktop.
Save rafaelcn/c481c79ef10ea39f946107b116e6777c to your computer and use it in GitHub Desktop.
Working token issuing
package main
import (
"encoding/json"
"fmt"
"log"
"os"
"time"
"github.com/smallstep/certificates/api"
"github.com/smallstep/certificates/ca"
"go.step.sm/cli-utils/token"
"go.step.sm/cli-utils/token/provision"
"github.com/square/go-jose"
)
const (
URL = "<url"
SAN = "<san>"
fingerprint = "<fingerprint>"
)
type (
Key struct {
Use string `json:"use"`
KTY string `json:"kty"`
KID string `json:"kid"`
CRV string `json:"crv"`
ALG string `json:"alg"`
X string `json:"x"`
Y string `json:"y"`
D string `json:"d"`
}
JWK struct {
Type string `json:"type"`
Name string `json:"name"`
Key Key `json:"key"`
EncryptedKey string `json:"encryptedKey"`
}
)
func main() {
client, err := ca.NewClient(URL, ca.WithRootSHA256(fingerprint))
if err != nil {
log.Printf("failed to create step client: %v\n", err)
panic(err)
}
data, err := os.ReadFile("provisioner.jwk")
if err != nil {
log.Printf("failed to read file, reason %v", err)
return
}
jwk := JWK{}
json.Unmarshal(data, &jwk)
jwe, err := jose.ParseEncrypted(jwk.EncryptedKey)
if err != nil {
log.Printf("failed to parse jwk, reason %v", err)
return
}
decrypted, err := jwe.Decrypt([]byte("<jwk provisioner password>"))
if err != nil {
log.Printf("failed to decrypt data, reason %v", err)
return
}
printResponse("JWE", jwe)
jsonWebKey := new(jose.JSONWebKey)
if err = json.Unmarshal(decrypted, jsonWebKey); err != nil {
log.Printf("failed to unmarshal decrypted data, reason %v", err)
}
tokenOptions := []token.Options{
token.WithKid(jwk.Key.KID),
token.WithIssuer("jwk-provisioner"),
token.WithSANS([]string{SAN}),
token.WithSubject(SAN),
token.WithAudience(URL + "/1.0/sign"),
token.WithValidity(time.Now(), time.Now().Add(token.DefaultValidity)),
}
token, err := provision.New(jsonWebKey.Algorithm, tokenOptions...)
if err != nil {
panic(err)
}
jwt, err := token.SignedString(jsonWebKey.Algorithm, jsonWebKey.Key)
if err != nil {
panic(err)
}
fmt.Printf("token %v\n\n", jwt)
// my implementation of a certificate sign request object
csrClient := NewCSR()
cr, err := csrClient.GeneratePrivateKey("2001120001000303", "m17641935")
sr := api.SignRequest{
CsrPEM: api.CertificateRequest{CertificateRequest: cr},
OTT: jwt,
}
signResponse, err := client.Sign(&sr)
if err != nil {
panic(err)
}
printResponse("SIGNATURE", signResponse)
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment