diff --git a/backend/remote-state/etcdv3/backend.go b/backend/remote-state/etcdv3/backend.go index e10fffa0d..dfd63131d 100644 --- a/backend/remote-state/etcdv3/backend.go +++ b/backend/remote-state/etcdv3/backend.go @@ -37,8 +37,9 @@ func New() backend.Backend { "prefix": &schema.Schema{ Type: schema.TypeString, - Required: true, - Description: "The prefix to use when storing state in etcd.", + Optional: true, + Description: "An optional prefix to be added to keys when to storing state in etcd.", + Default: "", }, "lock": &schema.Schema{ diff --git a/backend/remote-state/etcdv3/backend_state.go b/backend/remote-state/etcdv3/backend_state.go index 358a95295..1df89008a 100644 --- a/backend/remote-state/etcdv3/backend_state.go +++ b/backend/remote-state/etcdv3/backend_state.go @@ -13,18 +13,13 @@ import ( "github.com/hashicorp/terraform/terraform" ) -const ( - keyEnvPrefix = "-env:" -) - func (b *Backend) States() ([]string, error) { client, err := b.rawClient() if err != nil { return nil, err } - prefix := b.determineKey("") - res, err := client.Get(context.TODO(), prefix, etcdv3.WithPrefix(), etcdv3.WithKeysOnly()) + res, err := client.Get(context.TODO(), b.prefix, etcdv3.WithPrefix(), etcdv3.WithKeysOnly()) if err != nil { return nil, err } @@ -32,7 +27,7 @@ func (b *Backend) States() ([]string, error) { result := make([]string, 1, len(res.Kvs)+1) result[0] = backend.DefaultStateName for _, kv := range res.Kvs { - result = append(result, strings.TrimPrefix(string(kv.Key), prefix)) + result = append(result, strings.TrimPrefix(string(kv.Key), b.prefix)) } sort.Strings(result[1:]) @@ -49,9 +44,9 @@ func (b *Backend) DeleteState(name string) error { return err } - path := b.determineKey(name) + key := b.determineKey(name) - _, err = client.Delete(context.TODO(), path) + _, err = client.Delete(context.TODO(), key) return err } @@ -111,11 +106,7 @@ func (b *Backend) State(name string) (state.State, error) { } func (b *Backend) determineKey(name string) string { - prefix := b.prefix - if name != backend.DefaultStateName { - prefix += fmt.Sprintf("%s%s", keyEnvPrefix, name) - } - return prefix + return b.prefix + name } const errStateUnlock = ` diff --git a/backend/remote-state/etcdv3/backend_test.go b/backend/remote-state/etcdv3/backend_test.go index 619f46c05..ded8f4ae3 100644 --- a/backend/remote-state/etcdv3/backend_test.go +++ b/backend/remote-state/etcdv3/backend_test.go @@ -49,17 +49,17 @@ func prepareEtcdv3(t *testing.T) { func TestBackend(t *testing.T) { prepareEtcdv3(t) - path := fmt.Sprintf("tf-unit/%s", time.Now().String()) + prefix := fmt.Sprintf("%s/%s/", keyPrefix, time.Now().Format(time.RFC3339)) // Get the backend. We need two to test locking. b1 := backend.TestBackendConfig(t, New(), map[string]interface{}{ "endpoints": etcdv3Endpoints, - "prefix": path, + "prefix": prefix, }) b2 := backend.TestBackendConfig(t, New(), map[string]interface{}{ "endpoints": etcdv3Endpoints, - "prefix": path, + "prefix": prefix, }) // Test @@ -69,19 +69,19 @@ func TestBackend(t *testing.T) { func TestBackend_lockDisabled(t *testing.T) { prepareEtcdv3(t) - key := fmt.Sprintf("%s/%s", keyPrefix, time.Now().String()) + prefix := fmt.Sprintf("%s/%s/", keyPrefix, time.Now().Format(time.RFC3339)) // Get the backend. We need two to test locking. b1 := backend.TestBackendConfig(t, New(), map[string]interface{}{ "endpoints": etcdv3Endpoints, + "prefix": prefix, "lock": false, - "prefix": key, }) b2 := backend.TestBackendConfig(t, New(), map[string]interface{}{ "endpoints": etcdv3Endpoints, + "prefix": prefix + "/" + "different", // Diff so locking test would fail if it was locking "lock": false, - "prefix": key + "/" + "different", // Diff so locking test would fail if it was locking }) // Test diff --git a/backend/remote-state/etcdv3/client_test.go b/backend/remote-state/etcdv3/client_test.go index 0551afb76..0bd39a663 100644 --- a/backend/remote-state/etcdv3/client_test.go +++ b/backend/remote-state/etcdv3/client_test.go @@ -18,10 +18,12 @@ func TestRemoteClient_impl(t *testing.T) { func TestRemoteClient(t *testing.T) { prepareEtcdv3(t) + prefix := fmt.Sprintf("%s/%s/", keyPrefix, time.Now().Format(time.RFC3339)) + // Get the backend b := backend.TestBackendConfig(t, New(), map[string]interface{}{ "endpoints": etcdv3Endpoints, - "prefix": fmt.Sprintf("%s/%s", keyPrefix, time.Now().String()), + "prefix": prefix, }) // Grab the client @@ -37,12 +39,12 @@ func TestRemoteClient(t *testing.T) { func TestEtcdv3_stateLock(t *testing.T) { prepareEtcdv3(t) - key := fmt.Sprintf("tf-unit/%s", time.Now().String()) + prefix := fmt.Sprintf("%s/%s/", keyPrefix, time.Now().Format(time.RFC3339)) // Get the backend s1, err := backend.TestBackendConfig(t, New(), map[string]interface{}{ "endpoints": etcdv3Endpoints, - "prefix": key, + "prefix": prefix, }).State(backend.DefaultStateName) if err != nil { t.Fatal(err) @@ -50,7 +52,7 @@ func TestEtcdv3_stateLock(t *testing.T) { s2, err := backend.TestBackendConfig(t, New(), map[string]interface{}{ "endpoints": etcdv3Endpoints, - "prefix": key, + "prefix": prefix, }).State(backend.DefaultStateName) if err != nil { t.Fatal(err) @@ -62,10 +64,12 @@ func TestEtcdv3_stateLock(t *testing.T) { func TestEtcdv3_destroyLock(t *testing.T) { prepareEtcdv3(t) + prefix := fmt.Sprintf("%s/%s/", keyPrefix, time.Now().Format(time.RFC3339)) + // Get the backend b := backend.TestBackendConfig(t, New(), map[string]interface{}{ "endpoints": etcdv3Endpoints, - "prefix": fmt.Sprintf("tf-unit/%s", time.Now().String()), + "prefix": prefix, }) // Grab the client