Skip to content

Commit 5082348

Browse files
authored
Update remote.Client interface's methods to return diagnostics instead of primitive errors (#37502)
* Update remote package's Client interface to use diagnostics instead of errors * Update all implementations of Client interface to match changes, update calling code (incl. tests) to use diags.
1 parent 8503c45 commit 5082348

24 files changed

+328
-260
lines changed

internal/backend/remote-state/azure/client.go

Lines changed: 18 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@ import (
1818

1919
"github.com/hashicorp/terraform/internal/states/remote"
2020
"github.com/hashicorp/terraform/internal/states/statemgr"
21+
"github.com/hashicorp/terraform/internal/tfdiags"
2122
)
2223

2324
const (
@@ -44,7 +45,8 @@ type RemoteClient struct {
4445
snapshot bool
4546
}
4647

47-
func (c *RemoteClient) Get() (*remote.Payload, error) {
48+
func (c *RemoteClient) Get() (*remote.Payload, tfdiags.Diagnostics) {
49+
var diags tfdiags.Diagnostics
4850
options := blobs.GetInput{}
4951
if c.leaseID != "" {
5052
options.LeaseID = &c.leaseID
@@ -56,11 +58,11 @@ func (c *RemoteClient) Get() (*remote.Payload, error) {
5658
if response.WasNotFound(blob.HttpResponse) {
5759
return nil, nil
5860
}
59-
return nil, err
61+
return nil, diags.Append(err)
6062
}
6163

6264
if blob.Contents == nil {
63-
return nil, nil
65+
return nil, diags
6466
}
6567

6668
payload := &remote.Payload{
@@ -69,13 +71,15 @@ func (c *RemoteClient) Get() (*remote.Payload, error) {
6971

7072
// If there was no data, then return nil
7173
if len(payload.Data) == 0 {
72-
return nil, nil
74+
return nil, diags
7375
}
7476

75-
return payload, nil
77+
return payload, diags
7678
}
7779

78-
func (c *RemoteClient) Put(data []byte) error {
80+
func (c *RemoteClient) Put(data []byte) tfdiags.Diagnostics {
81+
var diags tfdiags.Diagnostics
82+
7983
getOptions := blobs.GetPropertiesInput{}
8084
setOptions := blobs.SetPropertiesInput{}
8185
putOptions := blobs.PutBlockBlobInput{}
@@ -95,7 +99,7 @@ func (c *RemoteClient) Put(data []byte) error {
9599

96100
log.Printf("[DEBUG] Snapshotting existing Blob %q (Container %q / Account %q)", c.keyName, c.containerName, c.accountName)
97101
if _, err := c.giovanniBlobClient.Snapshot(ctx, c.containerName, c.keyName, snapshotInput); err != nil {
98-
return fmt.Errorf("error snapshotting Blob %q (Container %q / Account %q): %+v", c.keyName, c.containerName, c.accountName, err)
102+
return diags.Append(fmt.Errorf("error snapshotting Blob %q (Container %q / Account %q): %+v", c.keyName, c.containerName, c.accountName, err))
99103
}
100104

101105
log.Print("[DEBUG] Created blob snapshot")
@@ -104,7 +108,7 @@ func (c *RemoteClient) Put(data []byte) error {
104108
blob, err := c.giovanniBlobClient.GetProperties(ctx, c.containerName, c.keyName, getOptions)
105109
if err != nil {
106110
if !response.WasNotFound(blob.HttpResponse) {
107-
return err
111+
return diags.Append(err)
108112
}
109113
}
110114

@@ -114,10 +118,12 @@ func (c *RemoteClient) Put(data []byte) error {
114118
putOptions.MetaData = blob.MetaData
115119
_, err = c.giovanniBlobClient.PutBlockBlob(ctx, c.containerName, c.keyName, putOptions)
116120

117-
return err
121+
return diags.Append(err)
118122
}
119123

120-
func (c *RemoteClient) Delete() error {
124+
func (c *RemoteClient) Delete() tfdiags.Diagnostics {
125+
var diags tfdiags.Diagnostics
126+
121127
options := blobs.DeleteInput{}
122128

123129
if c.leaseID != "" {
@@ -128,10 +134,10 @@ func (c *RemoteClient) Delete() error {
128134
resp, err := c.giovanniBlobClient.Delete(ctx, c.containerName, c.keyName, options)
129135
if err != nil {
130136
if !response.WasNotFound(resp.HttpResponse) {
131-
return err
137+
return diags.Append(err)
132138
}
133139
}
134-
return nil
140+
return diags
135141
}
136142

137143
func (c *RemoteClient) Lock(info *statemgr.LockInfo) (string, error) {

internal/backend/remote-state/azure/client_test.go

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -306,9 +306,9 @@ func TestPutMaintainsMetaData(t *testing.T) {
306306
}
307307

308308
bytes := []byte(randString(20))
309-
err = remoteClient.Put(bytes)
310-
if err != nil {
311-
t.Fatalf("Error putting data: %+v", err)
309+
diags := remoteClient.Put(bytes)
310+
if diags.HasErrors() {
311+
t.Fatalf("Error putting data: %+v", diags.Err())
312312
}
313313

314314
// Verify it still exists

internal/backend/remote-state/consul/client.go

Lines changed: 25 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@ import (
2020

2121
"github.com/hashicorp/terraform/internal/states/remote"
2222
"github.com/hashicorp/terraform/internal/states/statemgr"
23+
"github.com/hashicorp/terraform/internal/tfdiags"
2324
)
2425

2526
const (
@@ -71,18 +72,20 @@ type RemoteClient struct {
7172
sessionCancel context.CancelFunc
7273
}
7374

74-
func (c *RemoteClient) Get() (*remote.Payload, error) {
75+
func (c *RemoteClient) Get() (*remote.Payload, tfdiags.Diagnostics) {
76+
var diags tfdiags.Diagnostics
77+
7578
c.mu.Lock()
7679
defer c.mu.Unlock()
7780

7881
kv := c.Client.KV()
7982

8083
chunked, hash, chunks, pair, err := c.chunkedMode()
8184
if err != nil {
82-
return nil, err
85+
return nil, diags.Append(err)
8386
}
8487
if pair == nil {
85-
return nil, nil
88+
return nil, diags
8689
}
8790

8891
c.modifyIndex = pair.ModifyIndex
@@ -92,10 +95,10 @@ func (c *RemoteClient) Get() (*remote.Payload, error) {
9295
for _, c := range chunks {
9396
pair, _, err := kv.Get(c, nil)
9497
if err != nil {
95-
return nil, err
98+
return nil, diags.Append(err)
9699
}
97100
if pair == nil {
98-
return nil, fmt.Errorf("Key %q could not be found", c)
101+
return nil, diags.Append(fmt.Errorf("Key %q could not be found", c))
99102
}
100103
payload = append(payload, pair.Value[:]...)
101104
}
@@ -107,23 +110,23 @@ func (c *RemoteClient) Get() (*remote.Payload, error) {
107110
if len(payload) >= 1 && payload[0] == '\x1f' {
108111
payload, err = uncompressState(payload)
109112
if err != nil {
110-
return nil, err
113+
return nil, diags.Append(err)
111114
}
112115
}
113116

114117
md5 := md5.Sum(payload)
115118

116119
if hash != "" && fmt.Sprintf("%x", md5) != hash {
117-
return nil, fmt.Errorf("The remote state does not match the expected hash")
120+
return nil, diags.Append(fmt.Errorf("The remote state does not match the expected hash"))
118121
}
119122

120123
return &remote.Payload{
121124
Data: payload,
122125
MD5: md5[:],
123-
}, nil
126+
}, diags
124127
}
125128

126-
func (c *RemoteClient) Put(data []byte) error {
129+
func (c *RemoteClient) Put(data []byte) tfdiags.Diagnostics {
127130
// The state can be stored in 4 different ways, based on the payload size
128131
// and whether the user enabled gzip:
129132
// - single entry mode with plain JSON: a single JSON is stored at
@@ -161,6 +164,8 @@ func (c *RemoteClient) Put(data []byte) error {
161164
// in chunked mode and we will need to remove the old chunks (whether or
162165
// not we were using gzip does not matter in that case).
163166

167+
var diags tfdiags.Diagnostics
168+
164169
c.mu.Lock()
165170
defer c.mu.Unlock()
166171

@@ -169,7 +174,7 @@ func (c *RemoteClient) Put(data []byte) error {
169174
// First we determine what mode we were using and to prepare the cleanup
170175
chunked, hash, _, _, err := c.chunkedMode()
171176
if err != nil {
172-
return err
177+
return diags.Append(err)
173178
}
174179
cleanupOldChunks := func() {}
175180
if chunked {
@@ -188,7 +193,7 @@ func (c *RemoteClient) Put(data []byte) error {
188193
if compressedState, err := compressState(data); err == nil {
189194
payload = compressedState
190195
} else {
191-
return err
196+
return diags.Append(err)
192197
}
193198
}
194199

@@ -256,10 +261,10 @@ func (c *RemoteClient) Put(data []byte) error {
256261

257262
if err = store(payload); err == nil {
258263
// The payload was small enough to be stored
259-
return nil
264+
return diags
260265
} else if !strings.Contains(err.Error(), "too large") {
261266
// We failed for some other reason, report this to the user
262-
return err
267+
return diags.Append(err)
263268
}
264269

265270
// The payload was too large so we split it in multiple chunks
@@ -278,7 +283,7 @@ func (c *RemoteClient) Put(data []byte) error {
278283
}, nil)
279284

280285
if err != nil {
281-
return err
286+
return diags.Append(err)
282287
}
283288
}
284289

@@ -288,20 +293,21 @@ func (c *RemoteClient) Put(data []byte) error {
288293
"chunks": chunkPaths,
289294
})
290295
if err != nil {
291-
return err
296+
return diags.Append(err)
292297
}
293-
return store(payload)
298+
return diags.Append(store(payload))
294299
}
295300

296-
func (c *RemoteClient) Delete() error {
301+
func (c *RemoteClient) Delete() tfdiags.Diagnostics {
302+
var diags tfdiags.Diagnostics
297303
c.mu.Lock()
298304
defer c.mu.Unlock()
299305

300306
kv := c.Client.KV()
301307

302308
chunked, hash, _, _, err := c.chunkedMode()
303309
if err != nil {
304-
return err
310+
return diags.Append(err)
305311
}
306312

307313
_, err = kv.Delete(c.Path, nil)
@@ -312,7 +318,7 @@ func (c *RemoteClient) Delete() error {
312318
kv.DeleteTree(path, nil)
313319
}
314320

315-
return err
321+
return diags.Append(err)
316322
}
317323

318324
func (c *RemoteClient) lockPath() string {

internal/backend/remote-state/consul/client_test.go

Lines changed: 9 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -135,14 +135,14 @@ func TestConsul_largeState(t *testing.T) {
135135
if err != nil {
136136
t.Fatal(err)
137137
}
138-
err = c.Put(payload)
139-
if err != nil {
140-
t.Fatal("could not put payload", err)
138+
diags := c.Put(payload)
139+
if diags.HasErrors() {
140+
t.Fatal("could not put payload", diags.Err())
141141
}
142142

143-
remote, err := c.Get()
144-
if err != nil {
145-
t.Fatal(err)
143+
remote, diags := c.Get()
144+
if diags.HasErrors() {
145+
t.Fatal(diags.Err())
146146
}
147147

148148
if !bytes.Equal(payload, remote.Data) {
@@ -229,9 +229,9 @@ func TestConsul_largeState(t *testing.T) {
229229
)
230230

231231
// Deleting the state should remove all chunks
232-
err := c.Delete()
233-
if err != nil {
234-
t.Fatal(err)
232+
dDiags := c.Delete()
233+
if dDiags.HasErrors() {
234+
t.Fatal(dDiags.Err())
235235
}
236236
testPaths(t, []string{})
237237
}

internal/backend/remote-state/cos/client.go

Lines changed: 12 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@ import (
2121

2222
"github.com/hashicorp/terraform/internal/states/remote"
2323
"github.com/hashicorp/terraform/internal/states/statemgr"
24+
"github.com/hashicorp/terraform/internal/tfdiags"
2425
)
2526

2627
const (
@@ -41,38 +42,41 @@ type remoteClient struct {
4142
}
4243

4344
// Get returns remote state file
44-
func (c *remoteClient) Get() (*remote.Payload, error) {
45+
func (c *remoteClient) Get() (*remote.Payload, tfdiags.Diagnostics) {
4546
log.Printf("[DEBUG] get remote state file %s", c.stateFile)
47+
var diags tfdiags.Diagnostics
4648

4749
exists, data, checksum, err := c.getObject(c.stateFile)
4850
if err != nil {
49-
return nil, err
51+
return nil, diags.Append(err)
5052
}
5153

5254
if !exists {
53-
return nil, nil
55+
return nil, diags
5456
}
5557

5658
payload := &remote.Payload{
5759
Data: data,
5860
MD5: []byte(checksum),
5961
}
6062

61-
return payload, nil
63+
return payload, diags
6264
}
6365

6466
// Put put state file to remote
65-
func (c *remoteClient) Put(data []byte) error {
67+
func (c *remoteClient) Put(data []byte) tfdiags.Diagnostics {
6668
log.Printf("[DEBUG] put remote state file %s", c.stateFile)
69+
var diags tfdiags.Diagnostics
6770

68-
return c.putObject(c.stateFile, data)
71+
return diags.Append(c.putObject(c.stateFile, data))
6972
}
7073

7174
// Delete delete remote state file
72-
func (c *remoteClient) Delete() error {
75+
func (c *remoteClient) Delete() tfdiags.Diagnostics {
7376
log.Printf("[DEBUG] delete remote state file %s", c.stateFile)
77+
var diags tfdiags.Diagnostics
7478

75-
return c.deleteObject(c.stateFile)
79+
return diags.Append(c.deleteObject(c.stateFile))
7680
}
7781

7882
// Lock lock remote state file for writing

0 commit comments

Comments
 (0)