From 8c64078965e172ba09015c39b3e8bc2ca71d8cd7 Mon Sep 17 00:00:00 2001 From: Dana Axinte <53751979+dana-axinte@users.noreply.github.com> Date: Wed, 14 May 2025 15:24:25 +0100 Subject: [PATCH] SecretsManager: Keeper and secure value contracts, secretkeeper changes (#105379) Co-authored-by: PoorlyDefinedBehaviour Co-authored-by: Matheus Macabu --- pkg/registry/apis/secret/contracts/keeper.go | 87 +++++++++++++++---- .../apis/secret/contracts/secure_value.go | 27 ++++-- .../apis/secret/reststorage/keeper_rest.go | 33 +++++-- .../secret/reststorage/secure_value_rest.go | 44 ++++++++-- .../apis/secret/secretkeeper/secretkeeper.go | 37 +++----- .../secret/secretkeeper/secretkeeper_test.go | 17 ++-- .../secret/secretkeeper/sqlkeeper/keeper.go | 4 +- .../secretkeeper/sqlkeeper/keeper_test.go | 4 +- pkg/storage/secret/metadata/keeper_store.go | 13 +-- .../secret/metadata/secure_value_store.go | 21 +++-- 10 files changed, 204 insertions(+), 83 deletions(-) diff --git a/pkg/registry/apis/secret/contracts/keeper.go b/pkg/registry/apis/secret/contracts/keeper.go index 2ba2cfb05dd..c7f0482e54d 100644 --- a/pkg/registry/apis/secret/contracts/keeper.go +++ b/pkg/registry/apis/secret/contracts/keeper.go @@ -6,7 +6,7 @@ import ( secretv0alpha1 "github.com/grafana/grafana/pkg/apis/secret/v0alpha1" "github.com/grafana/grafana/pkg/registry/apis/secret/xkube" - "k8s.io/apimachinery/pkg/apis/meta/internalversion" + "k8s.io/apimachinery/pkg/util/validation/field" ) var ( @@ -15,23 +15,74 @@ var ( // KeeperMetadataStorage is the interface for wiring and dependency injection. type KeeperMetadataStorage interface { - Create(ctx context.Context, keeper *secretv0alpha1.Keeper) (*secretv0alpha1.Keeper, error) - Read(ctx context.Context, namespace xkube.Namespace, name string) (*secretv0alpha1.Keeper, error) - Update(ctx context.Context, keeper *secretv0alpha1.Keeper) (*secretv0alpha1.Keeper, error) + Create(ctx context.Context, keeper *secretv0alpha1.Keeper, actorUID string) (*secretv0alpha1.Keeper, error) + Read(ctx context.Context, namespace xkube.Namespace, name string, opts ReadOpts) (*secretv0alpha1.Keeper, error) + Update(ctx context.Context, keeper *secretv0alpha1.Keeper, actorUID string) (*secretv0alpha1.Keeper, error) Delete(ctx context.Context, namespace xkube.Namespace, name string) error - List(ctx context.Context, namespace xkube.Namespace, options *internalversion.ListOptions) (*secretv0alpha1.KeeperList, error) + List(ctx context.Context, namespace xkube.Namespace) ([]secretv0alpha1.Keeper, error) + GetKeeperConfig(ctx context.Context, namespace string, name *string, opts ReadOpts) (secretv0alpha1.KeeperConfig, error) } -// KeeperType represents the type of a Keeper. -type KeeperType string +// ErrKeeperInvalidSecureValues is returned when a Keeper references SecureValues that do not exist. +type ErrKeeperInvalidSecureValues struct { + invalidSecureValues map[string]struct{} +} -const ( - SQLKeeperType KeeperType = "sql" - AWSKeeperType KeeperType = "aws" - AzureKeeperType KeeperType = "azure" - GCPKeeperType KeeperType = "gcp" - HashiCorpKeeperType KeeperType = "hashicorp" -) +var _ xkube.ErrorLister = (*ErrKeeperInvalidSecureValues)(nil) + +func NewErrKeeperInvalidSecureValues(invalidSecureValues map[string]struct{}) *ErrKeeperInvalidSecureValues { + return &ErrKeeperInvalidSecureValues{invalidSecureValues: invalidSecureValues} +} + +func (e *ErrKeeperInvalidSecureValues) Error() string { + return e.ErrorList().ToAggregate().Error() +} + +func (e *ErrKeeperInvalidSecureValues) ErrorList() field.ErrorList { + errs := make(field.ErrorList, 0, len(e.invalidSecureValues)) + + path := field.NewPath("secureValueName") + + for sv := range e.invalidSecureValues { + errs = append(errs, field.NotFound(path, sv)) + } + + return errs +} + +// ErrKeeperInvalidSecureValuesReference is returned when a Keeper references SecureValues from a non-SQL Keeper. +type ErrKeeperInvalidSecureValuesReference struct { + invalidSecureValues map[string]string +} + +var _ xkube.ErrorLister = (*ErrKeeperInvalidSecureValuesReference)(nil) + +func NewErrKeeperInvalidSecureValuesReference(invalidSecureValues map[string]string) *ErrKeeperInvalidSecureValuesReference { + return &ErrKeeperInvalidSecureValuesReference{invalidSecureValues: invalidSecureValues} +} + +func (e *ErrKeeperInvalidSecureValuesReference) Error() string { + return e.ErrorList().ToAggregate().Error() +} + +func (e *ErrKeeperInvalidSecureValuesReference) ErrorList() field.ErrorList { + errs := make(field.ErrorList, 0, len(e.invalidSecureValues)) + + path := field.NewPath("secureValueName") + + for sv, keeper := range e.invalidSecureValues { + errs = append( + errs, + field.TypeInvalid( + path, + sv, + `cannot reference third-party keeper "`+keeper+`" in another third-party keeper, use a "sql" keeper instead`, + ), + ) + } + + return errs +} // ExternalID represents either the secure value's GUID or ref (in case of external secret references). // This is saved in the secure_value metadata storage as `external_id`. @@ -50,6 +101,8 @@ type Keeper interface { Delete(ctx context.Context, cfg secretv0alpha1.KeeperConfig, namespace string, externalID ExternalID) error } -const ( - DefaultSQLKeeper = "kp-default-sql" -) +// Service is the interface for secret keeper services. +// This exists because OSS and Enterprise have different amounts of keepers available. +type KeeperService interface { + KeeperForConfig(secretv0alpha1.KeeperConfig) (Keeper, error) +} diff --git a/pkg/registry/apis/secret/contracts/secure_value.go b/pkg/registry/apis/secret/contracts/secure_value.go index a3109e1d44f..c694d2b8d2e 100644 --- a/pkg/registry/apis/secret/contracts/secure_value.go +++ b/pkg/registry/apis/secret/contracts/secure_value.go @@ -6,18 +6,33 @@ import ( secretv0alpha1 "github.com/grafana/grafana/pkg/apis/secret/v0alpha1" "github.com/grafana/grafana/pkg/registry/apis/secret/xkube" - "k8s.io/apimachinery/pkg/apis/meta/internalversion" ) +type DecryptSecureValue struct { + Keeper *string + Ref string + ExternalID string + Decrypters []string +} + var ( - ErrSecureValueNotFound = errors.New("secure value not found") + ErrSecureValueNotFound = errors.New("secure value not found") + ErrSecureValueAlreadyExists = errors.New("secure value already exists") + ErrSecureValueOperationInProgress = errors.New("an operation is already in progress for the secure value") ) +type ReadOpts struct { + ForUpdate bool +} + // SecureValueMetadataStorage is the interface for wiring and dependency injection. type SecureValueMetadataStorage interface { - Create(ctx context.Context, sv *secretv0alpha1.SecureValue) (*secretv0alpha1.SecureValue, error) - Read(ctx context.Context, namespace xkube.Namespace, name string) (*secretv0alpha1.SecureValue, error) - Update(ctx context.Context, sv *secretv0alpha1.SecureValue) (*secretv0alpha1.SecureValue, error) + Create(ctx context.Context, sv *secretv0alpha1.SecureValue, actorUID string) (*secretv0alpha1.SecureValue, error) + Read(ctx context.Context, namespace xkube.Namespace, name string, opts ReadOpts) (*secretv0alpha1.SecureValue, error) + Update(ctx context.Context, sv *secretv0alpha1.SecureValue, actorUID string) (*secretv0alpha1.SecureValue, error) Delete(ctx context.Context, namespace xkube.Namespace, name string) error - List(ctx context.Context, namespace xkube.Namespace, options *internalversion.ListOptions) (*secretv0alpha1.SecureValueList, error) + List(ctx context.Context, namespace xkube.Namespace) (*secretv0alpha1.SecureValueList, error) + SetStatus(ctx context.Context, namespace xkube.Namespace, name string, status secretv0alpha1.SecureValueStatus) error + SetExternalID(ctx context.Context, namespace xkube.Namespace, name string, externalID ExternalID) error + ReadForDecrypt(ctx context.Context, namespace xkube.Namespace, name string) (*DecryptSecureValue, error) } diff --git a/pkg/registry/apis/secret/reststorage/keeper_rest.go b/pkg/registry/apis/secret/reststorage/keeper_rest.go index 4037d57f33e..9bae6d4e95c 100644 --- a/pkg/registry/apis/secret/reststorage/keeper_rest.go +++ b/pkg/registry/apis/secret/reststorage/keeper_rest.go @@ -9,6 +9,7 @@ import ( apierrors "k8s.io/apimachinery/pkg/api/errors" "k8s.io/apimachinery/pkg/apis/meta/internalversion" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" + "k8s.io/apimachinery/pkg/labels" "k8s.io/apimachinery/pkg/runtime" "k8s.io/apimachinery/pkg/util/validation/field" "k8s.io/apiserver/pkg/admission" @@ -79,12 +80,27 @@ func (s *KeeperRest) List(ctx context.Context, options *internalversion.ListOpti return nil, fmt.Errorf("missing namespace") } - keepersList, err := s.storage.List(ctx, xkube.Namespace(namespace), options) + labelSelector := options.LabelSelector + if labelSelector == nil { + labelSelector = labels.Everything() + } + + keepersList, err := s.storage.List(ctx, xkube.Namespace(namespace)) if err != nil { return nil, fmt.Errorf("failed to list keepers: %w", err) } - return keepersList, nil + allowedKeepers := make([]secretv0alpha1.Keeper, 0) + + for _, keeper := range keepersList { + if labelSelector.Matches(labels.Set(keeper.Labels)) { + allowedKeepers = append(allowedKeepers, keeper) + } + } + + return &secretv0alpha1.KeeperList{ + Items: allowedKeepers, + }, nil } // Get calls the inner `store` (persistence) and returns a `Keeper` by `name`. @@ -94,7 +110,8 @@ func (s *KeeperRest) Get(ctx context.Context, name string, options *metav1.GetOp return nil, fmt.Errorf("missing namespace") } - kp, err := s.storage.Read(ctx, xkube.Namespace(namespace), name) + // TODO: readopts + kp, err := s.storage.Read(ctx, xkube.Namespace(namespace), name, contracts.ReadOpts{}) if err != nil { if errors.Is(err, contracts.ErrKeeperNotFound) { return nil, s.resource.NewNotFound(name) @@ -121,7 +138,7 @@ func (s *KeeperRest) Create( return nil, err } - createdKeeper, err := s.storage.Create(ctx, kp) + createdKeeper, err := s.storage.Create(ctx, kp, "todo-user") if err != nil { var kErr xkube.ErrorLister if errors.As(err, &kErr) { @@ -172,7 +189,7 @@ func (s *KeeperRest) Update( newKeeper.Annotations = xkube.CleanAnnotations(newKeeper.Annotations) // Current implementation replaces everything passed in the spec, so it is not a PATCH. Do we want/need to support that? - updatedKeeper, err := s.storage.Update(ctx, newKeeper) + updatedKeeper, err := s.storage.Update(ctx, newKeeper, "todo-user") if err != nil { var kErr xkube.ErrorLister if errors.As(err, &kErr) { @@ -193,7 +210,11 @@ func (s *KeeperRest) Delete(ctx context.Context, name string, deleteValidation r return nil, false, fmt.Errorf("missing namespace") } - if err := s.storage.Delete(ctx, xkube.Namespace(namespace), name); err != nil { + err := s.storage.Delete(ctx, xkube.Namespace(namespace), name) + if err != nil { + if errors.Is(err, contracts.ErrKeeperNotFound) { + return nil, false, s.resource.NewNotFound(name) + } return nil, false, fmt.Errorf("failed to delete keeper: %w", err) } diff --git a/pkg/registry/apis/secret/reststorage/secure_value_rest.go b/pkg/registry/apis/secret/reststorage/secure_value_rest.go index 888398926a9..832c53207fa 100644 --- a/pkg/registry/apis/secret/reststorage/secure_value_rest.go +++ b/pkg/registry/apis/secret/reststorage/secure_value_rest.go @@ -9,6 +9,8 @@ import ( "k8s.io/apimachinery/pkg/apis/meta/internalversion" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" + "k8s.io/apimachinery/pkg/fields" + "k8s.io/apimachinery/pkg/labels" "k8s.io/apimachinery/pkg/runtime" "k8s.io/apimachinery/pkg/util/validation/field" "k8s.io/apiserver/pkg/admission" @@ -79,12 +81,35 @@ func (s *SecureValueRest) List(ctx context.Context, options *internalversion.Lis return nil, fmt.Errorf("missing namespace") } - secureValueList, err := s.storage.List(ctx, xkube.Namespace(namespace), options) + secureValueList, err := s.storage.List(ctx, xkube.Namespace(namespace)) if err != nil { return nil, fmt.Errorf("failed to list secure values: %w", err) } - return secureValueList, nil + labelSelector := options.LabelSelector + + if labelSelector == nil { + labelSelector = labels.Everything() + } + + fieldSelector := options.FieldSelector + if fieldSelector == nil { + fieldSelector = fields.Everything() + } + + allowedSecureValues := make([]secretv0alpha1.SecureValue, 0, len(secureValueList.Items)) + + for _, secureValue := range secureValueList.Items { + // Filter by label + if labelSelector.Matches(labels.Set(secureValue.Labels)) { + // Filter by status.phase + if fieldSelector.Matches(fields.Set{"status.phase": string(secureValue.Status.Phase)}) { + allowedSecureValues = append(allowedSecureValues, secureValue) + } + } + } + + return &secretv0alpha1.SecureValueList{Items: allowedSecureValues}, nil } // Get calls the inner `store` (persistence) and returns a `securevalue` by `name`. It will NOT return the decrypted `value`. @@ -94,7 +119,7 @@ func (s *SecureValueRest) Get(ctx context.Context, name string, options *metav1. return nil, fmt.Errorf("missing namespace") } - sv, err := s.storage.Read(ctx, xkube.Namespace(namespace), name) + sv, err := s.storage.Read(ctx, xkube.Namespace(namespace), name, contracts.ReadOpts{}) if err != nil { if errors.Is(err, contracts.ErrSecureValueNotFound) { return nil, s.resource.NewNotFound(name) @@ -122,7 +147,7 @@ func (s *SecureValueRest) Create( return nil, err } - createdSecureValue, err := s.storage.Create(ctx, sv) + createdSecureValue, err := s.storage.Create(ctx, sv, "todo-user") if err != nil { return nil, fmt.Errorf("failed to create secure value: %w", err) } @@ -166,7 +191,7 @@ func (s *SecureValueRest) Update( newSecureValue.Annotations = xkube.CleanAnnotations(newSecureValue.Annotations) // Current implementation replaces everything passed in the spec, so it is not a PATCH. Do we want/need to support that? - updatedSecureValue, err := s.storage.Update(ctx, newSecureValue) + updatedSecureValue, err := s.storage.Update(ctx, newSecureValue, "todo-user") if err != nil { return nil, false, fmt.Errorf("failed to update secure value: %w", err) } @@ -176,17 +201,20 @@ func (s *SecureValueRest) Update( // Delete calls the inner `store` (persistence) in order to delete the `securevalue`. // The second return parameter `bool` indicates whether the delete was instant or not. It always is for `securevalues`. -func (s *SecureValueRest) Delete(ctx context.Context, name string, deleteValidation rest.ValidateObjectFunc, options *metav1.DeleteOptions) (runtime.Object, bool, error) { +func (s *SecureValueRest) Delete(ctx context.Context, name string, _ rest.ValidateObjectFunc, _ *metav1.DeleteOptions) (runtime.Object, bool, error) { namespace, ok := request.NamespaceFrom(ctx) if !ok { return nil, false, fmt.Errorf("missing namespace") } if err := s.storage.Delete(ctx, xkube.Namespace(namespace), name); err != nil { - return nil, false, fmt.Errorf("delete secure value: %w", err) + if errors.Is(err, contracts.ErrSecureValueNotFound) { + return nil, false, s.resource.NewNotFound(name) + } + return nil, false, fmt.Errorf("deleting secure value: %+w", err) } - return nil, true, nil + return nil, false, nil } // ValidateSecureValue does basic spec validation of a securevalue. diff --git a/pkg/registry/apis/secret/secretkeeper/secretkeeper.go b/pkg/registry/apis/secret/secretkeeper/secretkeeper.go index daf150d1543..45bf6633106 100644 --- a/pkg/registry/apis/secret/secretkeeper/secretkeeper.go +++ b/pkg/registry/apis/secret/secretkeeper/secretkeeper.go @@ -1,45 +1,32 @@ package secretkeeper import ( - "fmt" - + secretv0alpha1 "github.com/grafana/grafana/pkg/apis/secret/v0alpha1" "github.com/grafana/grafana/pkg/infra/tracing" "github.com/grafana/grafana/pkg/registry/apis/secret/contracts" "github.com/grafana/grafana/pkg/registry/apis/secret/secretkeeper/sqlkeeper" ) -// Service is the interface for secret keeper services. -// This exists because OSS and Enterprise have different amounts of keepers available. -type Service interface { - GetKeepers() (map[contracts.KeeperType]contracts.Keeper, error) -} - // OSSKeeperService is the OSS implementation of the Service interface. type OSSKeeperService struct { - tracer tracing.Tracer - encryptionManager contracts.EncryptionManager - store contracts.EncryptedValueStorage + systemKeeper *sqlkeeper.SQLKeeper } +var _ contracts.KeeperService = (*OSSKeeperService)(nil) + func ProvideService( tracer tracing.Tracer, store contracts.EncryptedValueStorage, encryptionManager contracts.EncryptionManager, -) (OSSKeeperService, error) { - return OSSKeeperService{ - tracer: tracer, - encryptionManager: encryptionManager, - store: store, +) (*OSSKeeperService, error) { + return &OSSKeeperService{ + // TODO: rename to system keeper or something like that + systemKeeper: sqlkeeper.NewSQLKeeper(tracer, encryptionManager, store), }, nil } -func (ks OSSKeeperService) GetKeepers() (map[contracts.KeeperType]contracts.Keeper, error) { - sqlKeeper, err := sqlkeeper.NewSQLKeeper(ks.tracer, ks.encryptionManager, ks.store) - if err != nil { - return nil, fmt.Errorf("failed to create sql keeper: %w", err) - } - - return map[contracts.KeeperType]contracts.Keeper{ - contracts.SQLKeeperType: sqlKeeper, - }, nil +// Ignore the config, but we could use it to get the keeper type and then return the correct keeper. +// Instantiation only happens on ProvideService ONCE. +func (k *OSSKeeperService) KeeperForConfig(secretv0alpha1.KeeperConfig) (contracts.Keeper, error) { + return k.systemKeeper, nil } diff --git a/pkg/registry/apis/secret/secretkeeper/secretkeeper_test.go b/pkg/registry/apis/secret/secretkeeper/secretkeeper_test.go index 8a89eefc226..aaa02e154e5 100644 --- a/pkg/registry/apis/secret/secretkeeper/secretkeeper_test.go +++ b/pkg/registry/apis/secret/secretkeeper/secretkeeper_test.go @@ -7,27 +7,30 @@ import ( "github.com/stretchr/testify/require" "github.com/grafana/grafana/pkg/infra/tracing" - "github.com/grafana/grafana/pkg/registry/apis/secret/contracts" "github.com/grafana/grafana/pkg/registry/apis/secret/secretkeeper/sqlkeeper" "github.com/grafana/grafana/pkg/setting" + "github.com/grafana/grafana/pkg/tests/testsuite" ) +func TestMain(m *testing.M) { + testsuite.Run(m) +} + func Test_OSSKeeperService_GetKeepers(t *testing.T) { cfg := setting.NewCfg() keeperService, err := setupTestService(t, cfg) require.NoError(t, err) - t.Run("GetKeepers should return a map with a sql keeper", func(t *testing.T) { - keeperMap, err := keeperService.GetKeepers() + t.Run("KeeperForConfig should return the system keeper", func(t *testing.T) { + keeper, err := keeperService.KeeperForConfig(nil) require.NoError(t, err) - assert.NotNil(t, keeperMap) - assert.Equal(t, 1, len(keeperMap)) - assert.IsType(t, &sqlkeeper.SQLKeeper{}, keeperMap[contracts.SQLKeeperType]) + assert.NotNil(t, keeper) + assert.IsType(t, &sqlkeeper.SQLKeeper{}, keeper) }) } -func setupTestService(t *testing.T, cfg *setting.Cfg) (OSSKeeperService, error) { +func setupTestService(t *testing.T, cfg *setting.Cfg) (*OSSKeeperService, error) { // Initialize the keeper service keeperService, err := ProvideService(tracing.InitializeTracerForTest(), nil, nil) diff --git a/pkg/registry/apis/secret/secretkeeper/sqlkeeper/keeper.go b/pkg/registry/apis/secret/secretkeeper/sqlkeeper/keeper.go index 7e35a2f6aa0..dce87821d2a 100644 --- a/pkg/registry/apis/secret/secretkeeper/sqlkeeper/keeper.go +++ b/pkg/registry/apis/secret/secretkeeper/sqlkeeper/keeper.go @@ -21,12 +21,12 @@ func NewSQLKeeper( tracer tracing.Tracer, encryptionManager contracts.EncryptionManager, store contracts.EncryptedValueStorage, -) (*SQLKeeper, error) { +) *SQLKeeper { return &SQLKeeper{ tracer: tracer, encryptionManager: encryptionManager, store: store, - }, nil + } } func (s *SQLKeeper) Store(ctx context.Context, cfg secretv0alpha1.KeeperConfig, namespace string, exposedValueOrRef string) (contracts.ExternalID, error) { diff --git a/pkg/registry/apis/secret/secretkeeper/sqlkeeper/keeper_test.go b/pkg/registry/apis/secret/secretkeeper/sqlkeeper/keeper_test.go index a304c6cdc4c..413a5fa7530 100644 --- a/pkg/registry/apis/secret/secretkeeper/sqlkeeper/keeper_test.go +++ b/pkg/registry/apis/secret/secretkeeper/sqlkeeper/keeper_test.go @@ -143,9 +143,9 @@ func setupTestService(t *testing.T, cfg *setting.Cfg) (*SQLKeeper, error) { encValueStore := newInMemoryEncryptedValueStorage() // Initialize the SQLKeeper - sqlKeeper, err := NewSQLKeeper(tracing.InitializeTracerForTest(), encMgr, encValueStore) + sqlKeeper := NewSQLKeeper(tracing.InitializeTracerForTest(), encMgr, encValueStore) - return sqlKeeper, err + return sqlKeeper, nil } // While we don't have the real implementation, use an in-memory one diff --git a/pkg/storage/secret/metadata/keeper_store.go b/pkg/storage/secret/metadata/keeper_store.go index ebc58801fd8..ed7f68c6fc8 100644 --- a/pkg/storage/secret/metadata/keeper_store.go +++ b/pkg/storage/secret/metadata/keeper_store.go @@ -9,7 +9,6 @@ import ( "github.com/grafana/grafana/pkg/registry/apis/secret/contracts" "github.com/grafana/grafana/pkg/registry/apis/secret/xkube" "github.com/grafana/grafana/pkg/services/featuremgmt" - "k8s.io/apimachinery/pkg/apis/meta/internalversion" ) func ProvideKeeperMetadataStorage(db db.DB, features featuremgmt.FeatureToggles, accessClient claims.AccessClient) (contracts.KeeperMetadataStorage, error) { @@ -27,15 +26,15 @@ type keeperMetadataStorage struct { accessClient claims.AccessClient } -func (s *keeperMetadataStorage) Create(ctx context.Context, keeper *secretv0alpha1.Keeper) (*secretv0alpha1.Keeper, error) { +func (s *keeperMetadataStorage) Create(ctx context.Context, keeper *secretv0alpha1.Keeper, actorUID string) (*secretv0alpha1.Keeper, error) { return nil, nil } -func (s *keeperMetadataStorage) Read(ctx context.Context, namespace xkube.Namespace, name string) (*secretv0alpha1.Keeper, error) { +func (s *keeperMetadataStorage) Read(ctx context.Context, namespace xkube.Namespace, name string, opts contracts.ReadOpts) (*secretv0alpha1.Keeper, error) { return nil, nil } -func (s *keeperMetadataStorage) Update(ctx context.Context, newKeeper *secretv0alpha1.Keeper) (*secretv0alpha1.Keeper, error) { +func (s *keeperMetadataStorage) Update(ctx context.Context, newKeeper *secretv0alpha1.Keeper, actorUID string) (*secretv0alpha1.Keeper, error) { return nil, nil } @@ -43,6 +42,10 @@ func (s *keeperMetadataStorage) Delete(ctx context.Context, namespace xkube.Name return nil } -func (s *keeperMetadataStorage) List(ctx context.Context, namespace xkube.Namespace, options *internalversion.ListOptions) (*secretv0alpha1.KeeperList, error) { +func (s *keeperMetadataStorage) List(ctx context.Context, namespace xkube.Namespace) ([]secretv0alpha1.Keeper, error) { + return nil, nil +} + +func (s *keeperMetadataStorage) GetKeeperConfig(ctx context.Context, namespace string, name *string, opts contracts.ReadOpts) (secretv0alpha1.KeeperConfig, error) { return nil, nil } diff --git a/pkg/storage/secret/metadata/secure_value_store.go b/pkg/storage/secret/metadata/secure_value_store.go index 1c55a430548..48afe0e11b8 100644 --- a/pkg/storage/secret/metadata/secure_value_store.go +++ b/pkg/storage/secret/metadata/secure_value_store.go @@ -10,7 +10,6 @@ import ( "github.com/grafana/grafana/pkg/registry/apis/secret/contracts" "github.com/grafana/grafana/pkg/registry/apis/secret/xkube" "github.com/grafana/grafana/pkg/services/featuremgmt" - "k8s.io/apimachinery/pkg/apis/meta/internalversion" ) func ProvideSecureValueMetadataStorage(db db.DB, features featuremgmt.FeatureToggles, accessClient claims.AccessClient) (contracts.SecureValueMetadataStorage, error) { @@ -28,15 +27,15 @@ type secureValueMetadataStorage struct { accessClient claims.AccessClient } -func (s *secureValueMetadataStorage) Create(ctx context.Context, sv *secretv0alpha1.SecureValue) (*secretv0alpha1.SecureValue, error) { +func (s *secureValueMetadataStorage) Create(ctx context.Context, sv *secretv0alpha1.SecureValue, actorUID string) (*secretv0alpha1.SecureValue, error) { return nil, nil } -func (s *secureValueMetadataStorage) Read(ctx context.Context, namespace xkube.Namespace, name string) (*secretv0alpha1.SecureValue, error) { +func (s *secureValueMetadataStorage) Read(ctx context.Context, namespace xkube.Namespace, name string, opts contracts.ReadOpts) (*secretv0alpha1.SecureValue, error) { return nil, nil } -func (s *secureValueMetadataStorage) Update(ctx context.Context, newSecureValue *secretv0alpha1.SecureValue) (*secretv0alpha1.SecureValue, error) { +func (s *secureValueMetadataStorage) Update(ctx context.Context, newSecureValue *secretv0alpha1.SecureValue, actorUID string) (*secretv0alpha1.SecureValue, error) { return nil, nil } @@ -44,6 +43,18 @@ func (s *secureValueMetadataStorage) Delete(ctx context.Context, namespace xkube return nil } -func (s *secureValueMetadataStorage) List(ctx context.Context, namespace xkube.Namespace, options *internalversion.ListOptions) (*secretv0alpha1.SecureValueList, error) { +func (s *secureValueMetadataStorage) List(ctx context.Context, namespace xkube.Namespace) (*secretv0alpha1.SecureValueList, error) { + return nil, nil +} + +func (s *secureValueMetadataStorage) SetStatus(ctx context.Context, namespace xkube.Namespace, name string, status secretv0alpha1.SecureValueStatus) error { + return nil +} + +func (s *secureValueMetadataStorage) SetExternalID(ctx context.Context, namespace xkube.Namespace, name string, externalID contracts.ExternalID) error { + return nil +} + +func (s *secureValueMetadataStorage) ReadForDecrypt(ctx context.Context, namespace xkube.Namespace, name string) (*contracts.DecryptSecureValue, error) { return nil, nil }