github.com/tommi2day/gomodules@v1.13.2-0.20240423190010-b7d55d252a27/pwlib/vault.go (about)

     1  package pwlib
     2  
     3  import (
     4  	"context"
     5  	"fmt"
     6  	"strings"
     7  
     8  	vault "github.com/hashicorp/vault/api"
     9  	log "github.com/sirupsen/logrus"
    10  )
    11  
    12  // VaultData is the data structure
    13  type VaultData map[string]interface{}
    14  
    15  // VaultConfig create a new vault client
    16  func VaultConfig(address string, token string) (client *vault.Client, err error) {
    17  	config := vault.DefaultConfig()
    18  	if address != "" {
    19  		config.Address = address
    20  	}
    21  	client, err = vault.NewClient(config)
    22  	if err != nil {
    23  		err = fmt.Errorf("vault client for %s failed:%s", address, err)
    24  		return
    25  	}
    26  	if client == nil {
    27  		err = fmt.Errorf("vault client for %s not created", address)
    28  		return
    29  	}
    30  	if token != "" {
    31  		log.Debugf("set token to %s", token)
    32  		client.SetToken(token)
    33  	}
    34  	log.Debugf("vault client for %s created", address)
    35  	return
    36  }
    37  
    38  // VaultKVRead read a KVv2 secret from given mount and path
    39  func VaultKVRead(client *vault.Client, mount string, secretPath string) (vaultSecret *vault.KVSecret, err error) {
    40  	vaultSecret, err = client.KVv2(mount).Get(context.Background(), secretPath)
    41  	if err != nil {
    42  		err = fmt.Errorf("read vault secret failed:%s", err)
    43  		return
    44  	}
    45  	log.Debugf("got secret on path %s ", secretPath)
    46  	return
    47  }
    48  
    49  // VaultKVWrite write a KVv2 secret to given mount and path
    50  func VaultKVWrite(client *vault.Client, mount string, secretPath string, data map[string]interface{}) (err error) {
    51  	_, err = client.KVv2(mount).Put(context.Background(), secretPath, data)
    52  	if err != nil {
    53  		err = fmt.Errorf("write vault secret to %s failed:%s", secretPath, err)
    54  		return
    55  	}
    56  	log.Debugf("write secret to path %s successfully", secretPath)
    57  	return
    58  }
    59  
    60  // VaultRead logical read path value
    61  func VaultRead(client *vault.Client, path string) (vaultSecret *vault.Secret, err error) {
    62  	vaultSecret, err = client.Logical().Read(path)
    63  	if err != nil {
    64  		err = fmt.Errorf("read vault secret failed:%s", err)
    65  		return
    66  	}
    67  	log.Debugf("read on path %s OK", path)
    68  	return
    69  }
    70  
    71  // VaultList logical list path
    72  func VaultList(client *vault.Client, path string) (vaultSecret *vault.Secret, err error) {
    73  	vaultSecret, err = client.Logical().List(path)
    74  	if err != nil {
    75  		err = fmt.Errorf("read vault secret failed:%s", err)
    76  		return
    77  	}
    78  	log.Debugf("read on path %s OK", path)
    79  	return
    80  }
    81  
    82  // VaultWrite write a value to the given path
    83  func VaultWrite(client *vault.Client, path string, data map[string]interface{}) (err error) {
    84  	_, err = client.Logical().Write(path, data)
    85  	if err != nil {
    86  		err = fmt.Errorf("write to %s failed:%s", path, err)
    87  		return
    88  	}
    89  	log.Debugf("write to path %s successfully", path)
    90  	return
    91  }
    92  
    93  // GetVaultSecret reads a vault path as system via logical method and returns secret keys and values as plaintext format
    94  func GetVaultSecret(vaultPath string, vaultAddr string, vaultToken string) (content string, err error) {
    95  	var vc *vault.Client
    96  	var vs *vault.Secret
    97  	var vaultdata map[string]interface{}
    98  	log.Debugf("Vault Read entered for path '%s'", vaultPath)
    99  	vc, _ = VaultConfig(vaultAddr, vaultToken)
   100  	vs, err = VaultRead(vc, vaultPath)
   101  	if err == nil {
   102  		sysKey := strings.ReplaceAll(vaultPath, ":", "_")
   103  		if vs != nil {
   104  			log.Debug("Vault Read OK")
   105  			vaultdata = vs.Data["data"].(map[string]interface{})
   106  			for k, v := range vaultdata {
   107  				content += fmt.Sprintf("%s:%s:%v\n", sysKey, k, v.(string))
   108  			}
   109  		} else {
   110  			err = fmt.Errorf("no entries returned")
   111  		}
   112  	}
   113  	return
   114  }