diff --git a/src/metrics/rules/rules_mock.go b/src/metrics/rules/rules_mock.go index b2a9396ca2..956eebe263 100644 --- a/src/metrics/rules/rules_mock.go +++ b/src/metrics/rules/rules_mock.go @@ -1,7 +1,7 @@ // Code generated by MockGen. DO NOT EDIT. // Source: github.com/m3db/m3/src/metrics/rules (interfaces: Store) -// Copyright (c) 2018 Uber Technologies, Inc. +// Copyright (c) 2020 Uber Technologies, Inc. // // Permission is hereby granted, free of charge, to any person obtaining a copy // of this software and associated documentation files (the "Software"), to deal @@ -109,6 +109,20 @@ func (mr *MockStoreMockRecorder) WriteAll(arg0, arg1 interface{}) *gomock.Call { return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "WriteAll", reflect.TypeOf((*MockStore)(nil).WriteAll), arg0, arg1) } +// WriteNamespaces mocks base method +func (m *MockStore) WriteNamespaces(arg0 *Namespaces) error { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "WriteNamespaces", arg0) + ret0, _ := ret[0].(error) + return ret0 +} + +// WriteNamespaces indicates an expected call of WriteNamespaces +func (mr *MockStoreMockRecorder) WriteNamespaces(arg0 interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "WriteNamespaces", reflect.TypeOf((*MockStore)(nil).WriteNamespaces), arg0) +} + // WriteRuleSet mocks base method func (m *MockStore) WriteRuleSet(arg0 MutableRuleSet) error { m.ctrl.T.Helper() diff --git a/src/metrics/rules/store.go b/src/metrics/rules/store.go index f691512cc0..878156fa17 100644 --- a/src/metrics/rules/store.go +++ b/src/metrics/rules/store.go @@ -31,6 +31,9 @@ type Store interface { // WriteRuleSet saves the given ruleset to the backing store. WriteRuleSet(rs MutableRuleSet) error + // WriteNamespaces saves the given namespaces to the backing store. + WriteNamespaces(nss *Namespaces) error + // WriteAll saves both the given ruleset and namespace to the backing store. WriteAll(nss *Namespaces, rs MutableRuleSet) error diff --git a/src/metrics/rules/store/kv/store.go b/src/metrics/rules/store/kv/store.go index 7381150d09..78132c347d 100644 --- a/src/metrics/rules/store/kv/store.go +++ b/src/metrics/rules/store/kv/store.go @@ -99,6 +99,16 @@ func (s *store) WriteRuleSet(rs rules.MutableRuleSet) error { return wrapWriteError(err) } +func (s *store) WriteNamespaces(nss *rules.Namespaces) error { + namespacesCond, namespacesOp, err := s.namespacesTransaction(nss) + if err != nil { + return err + } + conditions, ops := []kv.Condition{namespacesCond}, []kv.Op{namespacesOp} + _, err = s.kvStore.Commit(conditions, ops) + return wrapWriteError(err) +} + func (s *store) WriteAll(nss *rules.Namespaces, rs rules.MutableRuleSet) error { if s.opts.Validator != nil { if err := s.opts.Validator.Validate(rs); err != nil { diff --git a/src/metrics/rules/store/kv/store_test.go b/src/metrics/rules/store/kv/store_test.go index 0286840125..2621e62e4e 100644 --- a/src/metrics/rules/store/kv/store_test.go +++ b/src/metrics/rules/store/kv/store_test.go @@ -596,6 +596,56 @@ func TestWriteRuleSetStaleDataError(t *testing.T) { require.IsType(t, merrors.NewStaleDataError(""), err) } +func TestWriteNamespace(t *testing.T) { + s := testStore() + defer s.Close() + + nss, err := rules.NewNamespaces(0, testNamespaces) + require.NoError(t, err) + + err = s.WriteNamespaces(&nss) + require.NoError(t, err) + + existing, err := s.ReadNamespaces() + require.NoError(t, err) + + revived, err := existing.AddNamespace( + "new", + rules.NewRuleSetUpdateHelper(0).NewUpdateMetadata(time.Now().UnixNano(), "test"), + ) + require.NoError(t, err) + require.False(t, revived) + + // Update should succeed + err = s.WriteNamespaces(existing) + require.NoError(t, err) +} + +func TestWriteNamespaceError(t *testing.T) { + s := testStore() + defer s.Close() + + err := s.WriteNamespaces(nil) + require.Error(t, err) +} + +func TestWriteNamespacesStaleDataError(t *testing.T) { + s := testStore() + defer s.Close() + + nss, err := rules.NewNamespaces(0, testNamespaces) + require.NoError(t, err) + + // First write should succeed + err = s.WriteNamespaces(&nss) + require.NoError(t, err) + + // writing again will encounter stale version + err = s.WriteNamespaces(&nss) + require.Error(t, err) + require.IsType(t, merrors.NewStaleDataError(""), err) +} + func TestWriteAllNoNamespace(t *testing.T) { s := testStore() defer s.Close()