Skip to content

Commit cd9f942

Browse files
committed
Remove unused RequiredWriteOnlyNilsAttributePaths() function
1 parent e1e6866 commit cd9f942

File tree

2 files changed

+0
-362
lines changed

2 files changed

+0
-362
lines changed

internal/fwserver/server_planresourcechange.go

Lines changed: 0 additions & 62 deletions
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,6 @@ import (
1313

1414
"github.com/hashicorp/terraform-plugin-framework/attr"
1515
"github.com/hashicorp/terraform-plugin-framework/diag"
16-
"github.com/hashicorp/terraform-plugin-framework/internal/fromtftypes"
1716
"github.com/hashicorp/terraform-plugin-framework/internal/fwschema"
1817
"github.com/hashicorp/terraform-plugin-framework/internal/fwschemadata"
1918
"github.com/hashicorp/terraform-plugin-framework/internal/logging"
@@ -513,67 +512,6 @@ func NormaliseRequiresReplace(ctx context.Context, rs path.Paths) path.Paths {
513512
return ret[:j]
514513
}
515514

516-
// RequiredWriteOnlyNilsAttributePaths returns a tftypes.Walk() function
517-
// that populates reqWriteOnlyNilsPaths with the paths of Required and WriteOnly
518-
// attributes that have a null value.
519-
func RequiredWriteOnlyNilsAttributePaths(ctx context.Context, schema fwschema.Schema, reqWriteOnlyNilsPaths *path.Paths) func(path *tftypes.AttributePath, value tftypes.Value) (bool, error) {
520-
return func(attrPath *tftypes.AttributePath, value tftypes.Value) (bool, error) {
521-
// we are only modifying attributes, not the entire resource
522-
if len(attrPath.Steps()) < 1 {
523-
return true, nil
524-
}
525-
526-
ctx = logging.FrameworkWithAttributePath(ctx, attrPath.String())
527-
528-
attribute, err := schema.AttributeAtTerraformPath(ctx, attrPath)
529-
530-
if err != nil {
531-
if errors.Is(err, fwschema.ErrPathInsideAtomicAttribute) {
532-
// atomic attributes can be nested block objects that contain child writeOnly attributes
533-
return true, nil
534-
}
535-
536-
if errors.Is(err, fwschema.ErrPathIsBlock) {
537-
// blocks do not have the writeOnly field but can contain child writeOnly attributes
538-
return true, nil
539-
}
540-
541-
if errors.Is(err, fwschema.ErrPathInsideDynamicAttribute) {
542-
return false, nil
543-
}
544-
545-
logging.FrameworkError(ctx, "couldn't find attribute in resource schema")
546-
return false, fmt.Errorf("couldn't find attribute in resource schema: %w", err)
547-
}
548-
549-
if attribute.IsWriteOnly() {
550-
if attribute.IsRequired() && value.IsNull() {
551-
fwPath, diags := fromtftypes.AttributePath(ctx, attrPath, schema)
552-
if diags.HasError() {
553-
for _, diagErr := range diags.Errors() {
554-
logging.FrameworkError(ctx,
555-
"Error converting tftypes.AttributePath to path.Path",
556-
map[string]any{
557-
logging.KeyError: diagErr.Detail(),
558-
},
559-
)
560-
}
561-
562-
return false, fmt.Errorf("couldn't convert tftypes.AttributePath to path.Path")
563-
}
564-
reqWriteOnlyNilsPaths.Append(fwPath)
565-
566-
// if the value is nil, there is no need to continue walking
567-
return false, nil
568-
}
569-
// check for any writeOnly child attributes
570-
return true, nil
571-
}
572-
573-
return false, nil
574-
}
575-
}
576-
577515
// planToState returns a *tfsdk.State with a copied value from a tfsdk.Plan.
578516
func planToState(plan tfsdk.Plan) *tfsdk.State {
579517
return &tfsdk.State{

internal/fwserver/server_planresourcechange_test.go

Lines changed: 0 additions & 300 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,6 @@ import (
77
"context"
88
"fmt"
99
"math/big"
10-
"sort"
1110
"testing"
1211

1312
"github.com/google/go-cmp/cmp"
@@ -364,305 +363,6 @@ func TestMarkComputedNilsAsUnknown(t *testing.T) {
364363
}
365364
}
366365

367-
func TestRequiredWriteOnlyNilsAttributePath(t *testing.T) {
368-
t.Parallel()
369-
370-
s := schema.Schema{
371-
Attributes: map[string]schema.Attribute{
372-
"string-value": schema.StringAttribute{
373-
Required: true,
374-
},
375-
"string-nil-optional-writeonly": schema.StringAttribute{
376-
Optional: true,
377-
WriteOnly: true,
378-
},
379-
"string-value-optional-writeonly": schema.StringAttribute{
380-
Optional: true,
381-
WriteOnly: true,
382-
},
383-
"string-nil-required-writeonly": schema.StringAttribute{
384-
Required: true,
385-
WriteOnly: true,
386-
},
387-
"string-value-required-writeonly": schema.StringAttribute{
388-
Required: true,
389-
WriteOnly: true,
390-
},
391-
"list-value": schema.ListAttribute{
392-
ElementType: types.StringType,
393-
Required: true,
394-
},
395-
"list-nil-optional-writeonly": schema.ListAttribute{
396-
ElementType: types.StringType,
397-
Optional: true,
398-
WriteOnly: true,
399-
},
400-
"list-value-optional-writeonly": schema.ListAttribute{
401-
ElementType: types.StringType,
402-
Optional: true,
403-
WriteOnly: true,
404-
},
405-
"list-nil-required-writeonly": schema.ListAttribute{
406-
ElementType: types.StringType,
407-
Required: true,
408-
WriteOnly: true,
409-
},
410-
"list-value-required-writeonly": schema.ListAttribute{
411-
ElementType: types.StringType,
412-
Required: true,
413-
WriteOnly: true,
414-
},
415-
"dynamic-value": schema.DynamicAttribute{
416-
Required: true,
417-
},
418-
"dynamic-nil-optional-writeonly": schema.DynamicAttribute{
419-
Optional: true,
420-
WriteOnly: true,
421-
},
422-
"dynamic-value-optional-writeonly": schema.DynamicAttribute{
423-
Optional: true,
424-
WriteOnly: true,
425-
},
426-
"dynamic-nil-required-writeonly": schema.DynamicAttribute{
427-
Required: true,
428-
WriteOnly: true,
429-
},
430-
"dynamic-value-required-writeonly": schema.DynamicAttribute{
431-
Required: true,
432-
WriteOnly: true,
433-
},
434-
// underlying values of dynamic attributes should be left alone
435-
"dynamic-value-with-underlying-list-required-writeonly": schema.DynamicAttribute{
436-
Required: true,
437-
WriteOnly: true,
438-
},
439-
"object-nil-required-writeonly": schema.ObjectAttribute{
440-
AttributeTypes: map[string]attr.Type{
441-
"string-nil": types.StringType,
442-
"string-set": types.StringType,
443-
},
444-
Required: true,
445-
WriteOnly: true,
446-
},
447-
"object-value-required-writeonly": schema.ObjectAttribute{
448-
AttributeTypes: map[string]attr.Type{
449-
"string-nil": types.StringType,
450-
"string-set": types.StringType,
451-
},
452-
Required: true,
453-
WriteOnly: true,
454-
},
455-
"nested-nil-required-writeonly": schema.SingleNestedAttribute{
456-
Attributes: map[string]schema.Attribute{
457-
"string-nil": schema.StringAttribute{
458-
Required: true,
459-
WriteOnly: true,
460-
},
461-
"string-set": schema.StringAttribute{
462-
Required: true,
463-
WriteOnly: true,
464-
},
465-
},
466-
Required: true,
467-
WriteOnly: true,
468-
},
469-
"nested-value-required-writeonly": schema.SingleNestedAttribute{
470-
Attributes: map[string]schema.Attribute{
471-
"string-nil": schema.StringAttribute{
472-
Required: true,
473-
WriteOnly: true,
474-
},
475-
"string-set": schema.StringAttribute{
476-
Required: true,
477-
WriteOnly: true,
478-
},
479-
},
480-
Required: true,
481-
WriteOnly: true,
482-
},
483-
"optional-nested-value-required-writeonly-attributes": schema.SingleNestedAttribute{
484-
Attributes: map[string]schema.Attribute{
485-
"string-nil": schema.StringAttribute{
486-
Required: true,
487-
WriteOnly: true,
488-
},
489-
"string-set": schema.StringAttribute{
490-
Required: true,
491-
WriteOnly: true,
492-
},
493-
},
494-
Optional: true,
495-
WriteOnly: true,
496-
},
497-
},
498-
Blocks: map[string]schema.Block{
499-
"block-nil-required-writeonly-attributes": schema.SetNestedBlock{
500-
NestedObject: schema.NestedBlockObject{
501-
Attributes: map[string]schema.Attribute{
502-
"string-nil": schema.StringAttribute{
503-
Required: true,
504-
WriteOnly: true,
505-
},
506-
"string-set": schema.StringAttribute{
507-
Required: true,
508-
WriteOnly: true,
509-
},
510-
},
511-
},
512-
},
513-
"block-value-required-writeonly-attributes": schema.SetNestedBlock{
514-
NestedObject: schema.NestedBlockObject{
515-
Attributes: map[string]schema.Attribute{
516-
"string-nil": schema.StringAttribute{
517-
Required: true,
518-
WriteOnly: true,
519-
},
520-
"string-set": schema.StringAttribute{
521-
Required: true,
522-
WriteOnly: true,
523-
},
524-
},
525-
},
526-
},
527-
},
528-
}
529-
input := tftypes.NewValue(s.Type().TerraformType(context.Background()), map[string]tftypes.Value{
530-
"string-value": tftypes.NewValue(tftypes.String, "hello, world"),
531-
"string-nil-optional-writeonly": tftypes.NewValue(tftypes.String, nil),
532-
"string-value-optional-writeonly": tftypes.NewValue(tftypes.String, "hello, world"),
533-
"string-nil-required-writeonly": tftypes.NewValue(tftypes.String, nil),
534-
"string-value-required-writeonly": tftypes.NewValue(tftypes.String, "hello, world"),
535-
"list-value": tftypes.NewValue(tftypes.List{ElementType: tftypes.String}, []tftypes.Value{tftypes.NewValue(tftypes.String, "hello, world")}),
536-
"list-nil-optional-writeonly": tftypes.NewValue(tftypes.List{ElementType: tftypes.String}, nil),
537-
"list-value-optional-writeonly": tftypes.NewValue(tftypes.List{ElementType: tftypes.String}, []tftypes.Value{tftypes.NewValue(tftypes.String, "hello, world")}),
538-
"list-nil-required-writeonly": tftypes.NewValue(tftypes.List{ElementType: tftypes.String}, nil),
539-
"list-value-required-writeonly": tftypes.NewValue(tftypes.List{ElementType: tftypes.String}, []tftypes.Value{
540-
tftypes.NewValue(tftypes.String, "hello, world"),
541-
tftypes.NewValue(tftypes.String, nil),
542-
}),
543-
"dynamic-value": tftypes.NewValue(tftypes.String, "hello, world"),
544-
"dynamic-nil-optional-writeonly": tftypes.NewValue(tftypes.DynamicPseudoType, nil),
545-
"dynamic-value-optional-writeonly": tftypes.NewValue(tftypes.String, "hello, world"),
546-
"dynamic-nil-required-writeonly": tftypes.NewValue(tftypes.DynamicPseudoType, nil),
547-
"dynamic-value-required-writeonly": tftypes.NewValue(tftypes.String, "hello, world"),
548-
"dynamic-value-with-underlying-list-required-writeonly": tftypes.NewValue(
549-
tftypes.List{
550-
ElementType: tftypes.Bool,
551-
},
552-
[]tftypes.Value{
553-
tftypes.NewValue(tftypes.Bool, true),
554-
tftypes.NewValue(tftypes.Bool, nil),
555-
},
556-
),
557-
"object-nil-required-writeonly": tftypes.NewValue(tftypes.Object{
558-
AttributeTypes: map[string]tftypes.Type{
559-
"string-nil": tftypes.String,
560-
"string-set": tftypes.String,
561-
},
562-
}, nil),
563-
"object-value-required-writeonly": tftypes.NewValue(tftypes.Object{
564-
AttributeTypes: map[string]tftypes.Type{
565-
"string-nil": tftypes.String,
566-
"string-set": tftypes.String,
567-
},
568-
}, map[string]tftypes.Value{
569-
"string-nil": tftypes.NewValue(tftypes.String, nil),
570-
"string-set": tftypes.NewValue(tftypes.String, "foo"),
571-
}),
572-
"nested-nil-required-writeonly": tftypes.NewValue(tftypes.Object{
573-
AttributeTypes: map[string]tftypes.Type{
574-
"string-nil": tftypes.String,
575-
"string-set": tftypes.String,
576-
},
577-
}, nil),
578-
"nested-value-required-writeonly": tftypes.NewValue(tftypes.Object{
579-
AttributeTypes: map[string]tftypes.Type{
580-
"string-nil": tftypes.String,
581-
"string-set": tftypes.String,
582-
},
583-
}, map[string]tftypes.Value{
584-
"string-nil": tftypes.NewValue(tftypes.String, nil),
585-
"string-set": tftypes.NewValue(tftypes.String, "bar"),
586-
}),
587-
"optional-nested-value-required-writeonly-attributes": tftypes.NewValue(tftypes.Object{
588-
AttributeTypes: map[string]tftypes.Type{
589-
"string-nil": tftypes.String,
590-
"string-set": tftypes.String,
591-
},
592-
}, map[string]tftypes.Value{
593-
"string-nil": tftypes.NewValue(tftypes.String, nil),
594-
"string-set": tftypes.NewValue(tftypes.String, "bar"),
595-
}),
596-
"block-nil-required-writeonly-attributes": tftypes.NewValue(tftypes.Set{
597-
ElementType: tftypes.Object{
598-
AttributeTypes: map[string]tftypes.Type{
599-
"string-nil": tftypes.String,
600-
"string-set": tftypes.String,
601-
},
602-
},
603-
}, nil),
604-
"block-value-required-writeonly-attributes": tftypes.NewValue(tftypes.Set{
605-
ElementType: tftypes.Object{
606-
AttributeTypes: map[string]tftypes.Type{
607-
"string-nil": tftypes.String,
608-
"string-set": tftypes.String,
609-
},
610-
},
611-
}, []tftypes.Value{
612-
tftypes.NewValue(tftypes.Object{
613-
AttributeTypes: map[string]tftypes.Type{
614-
"string-nil": tftypes.String,
615-
"string-set": tftypes.String,
616-
},
617-
}, map[string]tftypes.Value{
618-
"string-nil": tftypes.NewValue(tftypes.String, nil),
619-
"string-set": tftypes.NewValue(tftypes.String, "bar"),
620-
}),
621-
}),
622-
})
623-
expected := path.Paths{
624-
path.Root("block-value-required-writeonly-attributes").
625-
AtSetValue(types.ObjectValueMust(
626-
map[string]attr.Type{
627-
"string-nil": types.StringType,
628-
"string-set": types.StringType,
629-
},
630-
map[string]attr.Value{
631-
"string-nil": types.StringNull(),
632-
"string-set": types.StringValue("bar"),
633-
},
634-
)).
635-
AtName("string-nil"),
636-
path.Root("dynamic-nil-required-writeonly"),
637-
path.Root("list-nil-required-writeonly"),
638-
path.Root("nested-value-required-writeonly").AtName("string-nil"),
639-
path.Root("object-nil-required-writeonly"),
640-
path.Root("optional-nested-value-required-writeonly-attributes").AtName("string-nil"),
641-
path.Root("string-nil-required-writeonly"),
642-
path.Root("nested-nil-required-writeonly"),
643-
}
644-
645-
var got path.Paths
646-
err := tftypes.Walk(input, fwserver.RequiredWriteOnlyNilsAttributePaths(context.Background(), s, &got))
647-
if err != nil {
648-
t.Errorf("Unexpected error: %s", err)
649-
return
650-
}
651-
652-
sort.Slice(got, func(i, j int) bool {
653-
return got[i].String() < got[j].String()
654-
})
655-
656-
sort.Slice(expected, func(i, j int) bool {
657-
return expected[i].String() < expected[j].String()
658-
})
659-
660-
if diff := cmp.Diff(got, expected, cmpopts.EquateEmpty()); diff != "" {
661-
t.Errorf("Unexpected diff (+wanted, -got): %s", diff)
662-
return
663-
}
664-
}
665-
666366
func TestNormaliseRequiresReplace(t *testing.T) {
667367
t.Parallel()
668368

0 commit comments

Comments
 (0)