4
4
"bytes"
5
5
"context"
6
6
"fmt"
7
- "log"
8
7
"reflect"
9
8
"time"
10
9
@@ -18,6 +17,7 @@ import (
18
17
"github.com/hashicorp/terraform-plugin-sdk/v2/helper/validation"
19
18
"github.com/hashicorp/terraform-provider-aws/internal/conns"
20
19
"github.com/hashicorp/terraform-provider-aws/internal/create"
20
+ "github.com/hashicorp/terraform-provider-aws/internal/errs"
21
21
"github.com/hashicorp/terraform-provider-aws/internal/tfresource"
22
22
"github.com/hashicorp/terraform-provider-aws/internal/verify"
23
23
"github.com/hashicorp/terraform-provider-aws/names"
@@ -223,31 +223,27 @@ func ResourceResourceLFTags() *schema.Resource {
223
223
}
224
224
225
225
func resourceResourceLFTagsCreate (ctx context.Context , d * schema.ResourceData , meta interface {}) diag.Diagnostics {
226
+ var diags diag.Diagnostics
227
+
226
228
conn := meta .(* conns.AWSClient ).LakeFormationConn (ctx )
227
229
228
- input := & lakeformation.AddLFTagsToResourceInput {
229
- Resource : & lakeformation.Resource {},
230
- }
230
+ input := & lakeformation.AddLFTagsToResourceInput {}
231
231
232
232
if v , ok := d .GetOk ("catalog_id" ); ok {
233
233
input .CatalogId = aws .String (v .(string ))
234
234
}
235
235
236
- if v , ok := d .GetOk ("database" ); ok && len (v .([]interface {})) > 0 && v .([]interface {})[0 ] != nil {
237
- input .Resource .Database = ExpandDatabaseResource (v .([]interface {})[0 ].(map [string ]interface {}))
238
- }
239
-
240
236
if v , ok := d .GetOk ("lf_tag" ); ok && v .(* schema.Set ).Len () > 0 {
241
237
input .LFTags = expandLFTagPairs (v .(* schema.Set ).List ())
242
238
}
243
239
244
- if v , ok := d .GetOk ("table" ); ok && len (v .([]interface {})) > 0 && v .([]interface {})[0 ] != nil {
245
- input .Resource .Table = ExpandTableResource (v .([]interface {})[0 ].(map [string ]interface {}))
240
+ tagger , ds := lfTagsTagger (d )
241
+ diags = append (diags , ds ... )
242
+ if diags .HasError () {
243
+ return diags
246
244
}
247
245
248
- if v , ok := d .GetOk ("table_with_columns" ); ok && len (v .([]interface {})) > 0 && v .([]interface {})[0 ] != nil {
249
- input .Resource .TableWithColumns = expandTableColumnsResource (v .([]interface {})[0 ].(map [string ]interface {}))
250
- }
246
+ input .Resource = tagger .ExpandResource (d )
251
247
252
248
var output * lakeformation.AddLFTagsToResourceOutput
253
249
err := retry .RetryContext (ctx , IAMPropagationTimeout , func () * retry.RetryError {
@@ -271,130 +267,93 @@ func resourceResourceLFTagsCreate(ctx context.Context, d *schema.ResourceData, m
271
267
}
272
268
273
269
if err != nil {
274
- return create .DiagError ( names .LakeFormation , create .ErrActionCreating , ResNameLFTags , input .String (), err )
270
+ return create .AddError ( diags , names .LakeFormation , create .ErrActionCreating , ResNameLFTags , input .String (), err )
275
271
}
276
272
277
- diags := diag.Diagnostics {}
278
-
279
273
if output != nil && len (output .Failures ) > 0 {
280
274
for _ , v := range output .Failures {
281
275
if v .LFTag == nil || v .Error == nil {
282
276
continue
283
277
}
284
278
285
- diags = create .AddWarning (
286
- diags ,
279
+ diags = create .AddError (diags ,
287
280
names .LakeFormation ,
288
281
create .ErrActionCreating ,
289
282
ResNameLFTags ,
290
283
fmt .Sprintf ("catalog id:%s, tag key:%s, values:%+v" , aws .StringValue (v .LFTag .CatalogId ), aws .StringValue (v .LFTag .TagKey ), aws .StringValueSlice (v .LFTag .TagValues )),
291
284
awserr .New (aws .StringValue (v .Error .ErrorCode ), aws .StringValue (v .Error .ErrorMessage ), nil ),
292
285
)
293
286
}
294
-
295
- if len (diags ) == len (input .LFTags ) {
296
- return append (diags ,
297
- diag.Diagnostic {
298
- Severity : diag .Error ,
299
- Summary : create .ProblemStandardMessage (names .LakeFormation , create .ErrActionCreating , ResNameLFTags , "" , fmt .Errorf ("attempted to add %d tags, %d failures" , len (input .LFTags ), len (diags ))),
300
- },
301
- )
302
- }
287
+ }
288
+ if diags .HasError () {
289
+ return diags
303
290
}
304
291
305
292
d .SetId (fmt .Sprintf ("%d" , create .StringHashcode (input .String ())))
306
293
307
- return append (resourceResourceLFTagsRead (ctx , d , meta ), diags ... )
294
+ return append (diags , resourceResourceLFTagsRead (ctx , d , meta )... )
308
295
}
309
296
310
297
func resourceResourceLFTagsRead (ctx context.Context , d * schema.ResourceData , meta interface {}) diag.Diagnostics {
298
+ var diags diag.Diagnostics
299
+
311
300
conn := meta .(* conns.AWSClient ).LakeFormationConn (ctx )
312
301
313
302
input := & lakeformation.GetResourceLFTagsInput {
314
- Resource : & lakeformation.Resource {},
315
303
ShowAssignedLFTags : aws .Bool (true ),
316
304
}
317
305
318
306
if v , ok := d .GetOk ("catalog_id" ); ok {
319
307
input .CatalogId = aws .String (v .(string ))
320
308
}
321
309
322
- if v , ok := d .GetOk ("database" ); ok && len (v .([]interface {})) > 0 && v .([]interface {})[0 ] != nil {
323
- input .Resource .Database = ExpandDatabaseResource (v .([]interface {})[0 ].(map [string ]interface {}))
324
- }
325
-
326
- if v , ok := d .GetOk ("table" ); ok && len (v .([]interface {})) > 0 && v .([]interface {})[0 ] != nil {
327
- input .Resource .Table = ExpandTableResource (v .([]interface {})[0 ].(map [string ]interface {}))
310
+ tagger , ds := lfTagsTagger (d )
311
+ diags = append (diags , ds ... )
312
+ if diags .HasError () {
313
+ return diags
328
314
}
329
315
330
- if v , ok := d .GetOk ("table_with_columns" ); ok && len (v .([]interface {})) > 0 && v .([]interface {})[0 ] != nil {
331
- input .Resource .TableWithColumns = expandTableColumnsResource (v .([]interface {})[0 ].(map [string ]interface {}))
332
- }
316
+ input .Resource = tagger .ExpandResource (d )
333
317
334
318
output , err := conn .GetResourceLFTagsWithContext (ctx , input )
335
319
336
320
if err != nil {
337
- return create .DiagError (names .LakeFormation , create .ErrActionReading , ResNameLFTags , d .Id (), err )
338
- }
339
-
340
- if len (output .LFTagOnDatabase ) > 0 {
341
- if err := d .Set ("lf_tag" , flattenLFTagPairs (output .LFTagOnDatabase )); err != nil {
342
- return create .DiagError (names .LakeFormation , create .ErrActionSetting , ResNameLFTags , d .Id (), err )
343
- }
344
- }
345
-
346
- if len (output .LFTagsOnColumns ) > 0 {
347
- for _ , v := range output .LFTagsOnColumns {
348
- if aws .StringValue (v .Name ) != d .Get ("table_with_columns.0.name" ).(string ) {
349
- continue
350
- }
351
-
352
- if err := d .Set ("lf_tag" , flattenLFTagPairs (v .LFTags )); err != nil {
353
- return create .DiagError (names .LakeFormation , create .ErrActionSetting , ResNameLFTags , d .Id (), err )
354
- }
355
- }
321
+ return create .AddError (diags , names .LakeFormation , create .ErrActionReading , ResNameLFTags , d .Id (), err )
356
322
}
357
323
358
- if len (output .LFTagsOnTable ) > 0 {
359
- if err := d .Set ("lf_tag" , flattenLFTagPairs (output .LFTagsOnTable )); err != nil {
360
- return create .DiagError (names .LakeFormation , create .ErrActionSetting , ResNameLFTags , d .Id (), err )
361
- }
324
+ if err := d .Set ("lf_tag" , tagger .FlattenTags (output )); err != nil {
325
+ return create .AddError (diags , names .LakeFormation , create .ErrActionSetting , ResNameLFTags , d .Id (), err )
362
326
}
363
327
364
- return nil
328
+ return diags
365
329
}
366
330
367
331
func resourceResourceLFTagsDelete (ctx context.Context , d * schema.ResourceData , meta interface {}) diag.Diagnostics {
332
+ var diags diag.Diagnostics
333
+
368
334
conn := meta .(* conns.AWSClient ).LakeFormationConn (ctx )
369
335
370
- input := & lakeformation.RemoveLFTagsFromResourceInput {
371
- Resource : & lakeformation.Resource {},
372
- }
336
+ input := & lakeformation.RemoveLFTagsFromResourceInput {}
373
337
374
338
if v , ok := d .GetOk ("catalog_id" ); ok {
375
339
input .CatalogId = aws .String (v .(string ))
376
340
}
377
341
378
- if v , ok := d .GetOk ("database" ); ok && len (v .([]interface {})) > 0 && v .([]interface {})[0 ] != nil {
379
- input .Resource .Database = ExpandDatabaseResource (v .([]interface {})[0 ].(map [string ]interface {}))
380
- }
381
-
382
342
if v , ok := d .GetOk ("lf_tag" ); ok && v .(* schema.Set ).Len () > 0 {
383
343
input .LFTags = expandLFTagPairs (v .(* schema.Set ).List ())
384
344
}
385
345
386
- if v , ok := d .GetOk ("table" ); ok && len (v .([]interface {})) > 0 && v .([]interface {})[0 ] != nil {
387
- input .Resource .Table = ExpandTableResource (v .([]interface {})[0 ].(map [string ]interface {}))
346
+ tagger , ds := lfTagsTagger (d )
347
+ diags = append (diags , ds ... )
348
+ if diags .HasError () {
349
+ return diags
388
350
}
389
351
390
- if v , ok := d .GetOk ("table_with_columns" ); ok && len (v .([]interface {})) > 0 && v .([]interface {})[0 ] != nil {
391
- input .Resource .TableWithColumns = expandTableColumnsResource (v .([]interface {})[0 ].(map [string ]interface {}))
392
- }
352
+ input .Resource = tagger .ExpandResource (d )
393
353
394
- if input .Resource == nil || reflect .DeepEqual (input .Resource , & lakeformation.Resource {}) {
354
+ if input .Resource == nil || reflect .DeepEqual (input .Resource , & lakeformation.Resource {}) || len ( input . LFTags ) == 0 {
395
355
// if resource is empty, don't delete = it won't delete anything since this is the predicate
396
- log .Printf ("[WARN] No Lake Formation Resource LF Tags to remove" )
397
- return nil
356
+ return create .AddWarningMessage (diags , names .LakeFormation , create .ErrActionSetting , ResNameLFTags , d .Id (), "no LF-Tags to remove" )
398
357
}
399
358
400
359
err := retry .RetryContext (ctx , d .Timeout (schema .TimeoutDelete ), func () * retry.RetryError {
@@ -408,7 +367,7 @@ func resourceResourceLFTagsDelete(ctx context.Context, d *schema.ResourceData, m
408
367
return retry .RetryableError (err )
409
368
}
410
369
411
- return retry .NonRetryableError (fmt .Errorf ("unable to revoke Lake Formation Permissions : %w" , err ))
370
+ return retry .NonRetryableError (fmt .Errorf ("removing Lake Formation LF-Tags : %w" , err ))
412
371
}
413
372
return nil
414
373
})
@@ -418,10 +377,83 @@ func resourceResourceLFTagsDelete(ctx context.Context, d *schema.ResourceData, m
418
377
}
419
378
420
379
if err != nil {
421
- return create .DiagError (names .LakeFormation , create .ErrActionDeleting , ResNameLFTags , d .Id (), err )
380
+ return create .AddError (diags , names .LakeFormation , create .ErrActionDeleting , ResNameLFTags , d .Id (), err )
381
+ }
382
+
383
+ return diags
384
+ }
385
+
386
+ func lfTagsTagger (d * schema.ResourceData ) (tagger , diag.Diagnostics ) {
387
+ var diags diag.Diagnostics
388
+ if v , ok := d .GetOk ("database" ); ok && len (v .([]interface {})) > 0 && v .([]interface {})[0 ] != nil {
389
+ return & databaseTagger {}, diags
390
+ } else if v , ok := d .GetOk ("table" ); ok && len (v .([]interface {})) > 0 && v .([]interface {})[0 ] != nil {
391
+ return & tableTagger {}, diags
392
+ } else if v , ok := d .GetOk ("table_with_columns" ); ok && len (v .([]interface {})) > 0 && v .([]interface {})[0 ] != nil {
393
+ return & columnTagger {}, diags
394
+ } else {
395
+ diags = append (diags , errs .NewErrorDiagnostic (
396
+ "Invalid Lake Formation Resource Type" ,
397
+ "An unexpected error occurred while resolving the Lake Formation Resource type. " +
398
+ "This is always an error in the provider. " +
399
+ "Please report the following to the provider developer:\n \n " +
400
+ "No Lake Formation Resource defined." ,
401
+ ))
402
+ return nil , diags
403
+ }
404
+ }
405
+
406
+ type tagger interface {
407
+ ExpandResource (* schema.ResourceData ) * lakeformation.Resource
408
+ FlattenTags (* lakeformation.GetResourceLFTagsOutput ) []any
409
+ }
410
+
411
+ type databaseTagger struct {}
412
+
413
+ func (t * databaseTagger ) ExpandResource (d * schema.ResourceData ) * lakeformation.Resource {
414
+ v := d .Get ("database" ).([]any )[0 ].(map [string ]any )
415
+ return & lakeformation.Resource {
416
+ Database : ExpandDatabaseResource (v ),
417
+ }
418
+ }
419
+
420
+ func (t * databaseTagger ) FlattenTags (output * lakeformation.GetResourceLFTagsOutput ) []any {
421
+ return flattenLFTagPairs (output .LFTagOnDatabase )
422
+ }
423
+
424
+ type tableTagger struct {}
425
+
426
+ func (t * tableTagger ) ExpandResource (d * schema.ResourceData ) * lakeformation.Resource {
427
+ v := d .Get ("table" ).([]any )[0 ].(map [string ]any )
428
+ return & lakeformation.Resource {
429
+ Table : ExpandTableResource (v ),
430
+ }
431
+ }
432
+
433
+ func (t * tableTagger ) FlattenTags (output * lakeformation.GetResourceLFTagsOutput ) []any {
434
+ return flattenLFTagPairs (output .LFTagsOnTable )
435
+ }
436
+
437
+ type columnTagger struct {}
438
+
439
+ func (t * columnTagger ) ExpandResource (d * schema.ResourceData ) * lakeformation.Resource {
440
+ v := d .Get ("table_with_columns" ).([]any )[0 ].(map [string ]any )
441
+ return & lakeformation.Resource {
442
+ TableWithColumns : expandTableColumnsResource (v ),
443
+ }
444
+ }
445
+
446
+ func (t * columnTagger ) FlattenTags (output * lakeformation.GetResourceLFTagsOutput ) []any {
447
+ if len (output .LFTagsOnColumns ) == 0 {
448
+ return []any {}
449
+ }
450
+
451
+ tags := output .LFTagsOnColumns [0 ]
452
+ if tags == nil {
453
+ return []any {}
422
454
}
423
455
424
- return nil
456
+ return flattenLFTagPairs ( tags . LFTags )
425
457
}
426
458
427
459
func lfTagsHash (v interface {}) int {
0 commit comments