go.mondoo.com/cnquery@v0.0.0-20231005093811-59568235f6ea/providers-sdk/v1/vault/multivault/multivault.go (about)

     1  // Copyright (c) Mondoo, Inc.
     2  // SPDX-License-Identifier: BUSL-1.1
     3  
     4  package multivault
     5  
     6  import (
     7  	"context"
     8  	"errors"
     9  
    10  	"go.mondoo.com/cnquery/providers-sdk/v1/vault"
    11  	"go.mondoo.com/ranger-rpc/codes"
    12  	"go.mondoo.com/ranger-rpc/status"
    13  )
    14  
    15  // New creates a new vault that can query multiple vaults. It is a
    16  // read-only vault that allows the user to have a unified view for secrets
    17  // located in e.g. and inmemory vault and in e.g. a keyring vault. The order
    18  // matters. When a secret is requested, this implementation iterates over
    19  // each vault and returns the first secret with the requested id
    20  func New(vaults ...vault.Vault) *multiVault {
    21  	return &multiVault{
    22  		vaults: vaults,
    23  	}
    24  }
    25  
    26  type multiVault struct {
    27  	vaults []vault.Vault
    28  }
    29  
    30  func (v *multiVault) About(context.Context, *vault.Empty) (*vault.VaultInfo, error) {
    31  	return &vault.VaultInfo{Name: "Multi Vault"}, nil
    32  }
    33  
    34  func (m *multiVault) Set(ctx context.Context, secret *vault.Secret) (*vault.SecretID, error) {
    35  	return nil, errors.New("this vault is read only")
    36  }
    37  
    38  func (m *multiVault) Get(ctx context.Context, id *vault.SecretID) (*vault.Secret, error) {
    39  	if id == nil {
    40  		return nil, errors.New("secret id is empty")
    41  	}
    42  
    43  	// iterate over each vault and return the first finding
    44  	for i := range m.vaults {
    45  		v := m.vaults[i]
    46  		secret, err := v.Get(ctx, id)
    47  		se, _ := status.FromError(err)
    48  		// move to next vault if we could not find the secret
    49  		if se != nil && se.Code() == codes.NotFound {
    50  			continue
    51  		} else if se != nil {
    52  			return nil, err
    53  		}
    54  		return secret, nil
    55  	}
    56  
    57  	return nil, vault.NotFoundError
    58  }