From a43491e07d9f5e077b629eeee1c742da48622a68 Mon Sep 17 00:00:00 2001 From: SoXX Date: Sun, 5 Jan 2025 22:41:15 +0100 Subject: [PATCH] refactor: Vault client functions to return client instance and improve error handling --- cmd/otter-cage/main.go | 47 ++++++++++++++++++++++++++++-- internal/vault/vault.go | 63 ++++++++++++++++++++++++++++++++++------- 2 files changed, 97 insertions(+), 13 deletions(-) diff --git a/cmd/otter-cage/main.go b/cmd/otter-cage/main.go index e291355..f234a62 100644 --- a/cmd/otter-cage/main.go +++ b/cmd/otter-cage/main.go @@ -53,7 +53,7 @@ func main() { var ctx = context.Background() // Set up the logger based on the configuration - utils.SetupLogger(otterCage.LogLevel, otterCage.LogFormat) + utils.SetupLogger("TRACE", otterCage.LogFormat) ctx, span := tracer.Start(ctx, "main") defer span.End() @@ -62,8 +62,49 @@ func main() { ginRouter := setupRouter(ctx) - token := vault.GetJWTToken("b7dc7146-88ce-47ba-98c1-ea8184a49be1", "Ni49FqnH_GIi0EIfneuIxDNKm", "https://laughing-banach-ptdsgdxqjf.projects.oryapis.com/oauth2/token") - vault.VaultWithJWT(ctx, "", token) + // TODO: Groups are not generated via the roles, this needs to be fixed + + /* + # roles for application + vault write -address "http://localhost:8200" auth/jwt/role/manager \ + role_type="jwt" \ + bound_subject="b7dc7146-88ce-47ba-98c1-ea8184a49be1" \ + allowed_redirect_uris="http://localhost:8250/oidc/callback" \ + user_claim="client_id" \ + groups_claim="/ext/roles" \ + token_type="batch" + */ + + /* + # ACL policies + path "e621.net/*" { + capabilities = [ "create", "update", "list" ] + } + + path "e621.net/*" { + capabilities = [ "read" ] + } + */ + + token := vault.GetJWTToken("b7dc7146-88ce-47ba-98c1-ea8184a49be1", + "Ni49FqnH_GIi0EIfneuIxDNKm", + "https://laughing-banach-ptdsgdxqjf.projects.oryapis.com/oauth2/token") + + log.WithField("token", token).Trace("API Token") + + client := vault.VaultWithJWT(ctx, "manager", token) + + secret := vault.SecretData[vault.E621]{ + UserID: "1", + UserSourceID: "2", + Secret: vault.E621{ + APIKey: "test", + }, + } + err := vault.WritingAPIKeyToVault[vault.E621](ctx, client, secret) + if err != nil { + log.WithError(err).Panic("cant write API key to vault") + } server := &http.Server{ Addr: ":8080", diff --git a/internal/vault/vault.go b/internal/vault/vault.go index bba96eb..3bc3683 100644 --- a/internal/vault/vault.go +++ b/internal/vault/vault.go @@ -2,8 +2,10 @@ package vault import ( "context" + "encoding/json" "fmt" "golang.org/x/oauth2/clientcredentials" + "net/http" "time" "github.com/hashicorp/vault-client-go" @@ -31,7 +33,7 @@ func GetJWTToken(clientID string, clientSecret string, tokenURL string) string { return token.AccessToken } -func VaultWithJWT(ctx context.Context, roles string, jwt string) { +func VaultWithJWT(ctx context.Context, roles string, jwt string) *vault.Client { // prepare a client with the given base address client, err := vault.New( @@ -39,7 +41,7 @@ func VaultWithJWT(ctx context.Context, roles string, jwt string) { vault.WithRequestTimeout(30*time.Second), ) if err != nil { - log.Fatal(err) + log.Panic(err) } request := schema.JwtLoginRequest{ @@ -49,16 +51,18 @@ func VaultWithJWT(ctx context.Context, roles string, jwt string) { resp, err := client.Auth.JwtLogin(ctx, request) if err != nil { - log.Fatal(resp, err) + log.Panic(resp, err) } err = client.SetToken(resp.Auth.ClientToken) if err != nil { - log.Fatal(err) + log.Panic(err) } + + return client } -func VaultWithToken() { +func VaultWithUserPass(ctx context.Context, username, password string) *vault.Client { // prepare a client with the given base address client, err := vault.New( @@ -66,7 +70,41 @@ func VaultWithToken() { vault.WithRequestTimeout(30*time.Second), ) if err != nil { - log.Fatal(err) + log.Panic(err) + } + + client.SetRequestCallbacks(func(req *http.Request) { + log.Println("REQUEST:", *req.URL) + }) + + request := schema.UserpassLoginRequest{ + Password: password, + } + + // authenticate with a root token (insecure) + + resp, err := client.Auth.UserpassLogin(ctx, username, request) + if err != nil { + log.WithError(err).Panic("Problem logging in with username and password") + } + + err = client.SetToken(resp.Auth.ClientToken) + if err != nil { + log.Panic(err) + } + + return client +} + +func VaultWithToken(token string) *vault.Client { + + // prepare a client with the given base address + client, err := vault.New( + vault.WithAddress("http://localhost:8200"), + vault.WithRequestTimeout(30*time.Second), + ) + if err != nil { + log.Panic(err) } //client.SetRequestCallbacks(func(req *http.Request) { @@ -74,9 +112,11 @@ func VaultWithToken() { //}) // authenticate with a root token (insecure) - if err := client.SetToken("hvs.XD2NNAznvWucjo7B8RhtXpQZ"); err != nil { - log.Fatal(err) + if err := client.SetToken(token); err != nil { + log.Panic(err) } + + return client } // WritingAPIKeyToVault writes the API key to a Vault using the given secret data. @@ -102,7 +142,10 @@ func WritingAPIKeyToVault[T SecretDataTypes](ctx context.Context, client *vault. _, err = client.Secrets.KvV2Write(ctx, secretData.UserSourceID, request, vault.WithMountPath(secretData.Secret.GetMountPath())) if err != nil { - log.Fatal(err) + daaata, _ := json.Marshal(client) + log.Trace(string(daaata)) + + log.WithField("mount_path", secretData.Secret.GetMountPath()).Panic(err) } return nil @@ -123,7 +166,7 @@ func WritingAPIKeyToVault[T SecretDataTypes](ctx context.Context, client *vault. func ReadingApiKeyFromVault[T SecretDataTypes](ctx context.Context, client *vault.Client, secretData *SecretData[T]) error { data, err := client.Secrets.KvV2Read(ctx, secretData.UserSourceID, vault.WithMountPath(secretData.Secret.GetMountPath())) if err != nil { - log.Fatal(err) + log.Panic(err) } secret, err := MapToSecret[T](data.Data.Data)