Skip to content

Commit

Permalink
Merge pull request #404 from hashicorp/td-use-attr.ValueAs
Browse files Browse the repository at this point in the history
Use `plugin-framework` `attr.ValueAs`
  • Loading branch information
ewbankkit authored Feb 24, 2022
2 parents b76a47d + d4411ce commit d736861
Show file tree
Hide file tree
Showing 10 changed files with 128 additions and 144 deletions.
8 changes: 4 additions & 4 deletions internal/validate/arn.go
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ func (validator arnValidator) MarkdownDescription(ctx context.Context) string {

// Validate performs the validation.
func (validator arnValidator) Validate(ctx context.Context, request tfsdk.ValidateAttributeRequest, response *tfsdk.ValidateAttributeResponse) {
s, ok := validateString(request, response)
s, ok := validateString(ctx, request, response)
if !ok {
return
}
Expand Down Expand Up @@ -67,7 +67,7 @@ func (validator iamPolicyARNValidator) Validate(ctx context.Context, request tfs
"expected an IAM policy ARN",
)

arn, ok := validateARN(request, response, errDiag)
arn, ok := validateARN(ctx, request, response, errDiag)
if !ok {
return
}
Expand All @@ -82,8 +82,8 @@ func IAMPolicyARN() tfsdk.AttributeValidator {
return iamPolicyARNValidator{}
}

func validateARN(request tfsdk.ValidateAttributeRequest, response *tfsdk.ValidateAttributeResponse, errDiag diag.Diagnostic) (arn.ARN, bool) {
s, ok := validateString(request, response)
func validateARN(ctx context.Context, request tfsdk.ValidateAttributeRequest, response *tfsdk.ValidateAttributeResponse, errDiag diag.Diagnostic) (arn.ARN, bool) {
s, ok := validateString(ctx, request, response)
if !ok {
return arn.ARN{}, false
}
Expand Down
47 changes: 26 additions & 21 deletions internal/validate/array.go
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,7 @@ func (validator arrayLenBetweenValidator) MarkdownDescription(ctx context.Contex

// Validate performs the validation.
func (validator arrayLenBetweenValidator) Validate(ctx context.Context, request tfsdk.ValidateAttributeRequest, response *tfsdk.ValidateAttributeResponse) {
elems, _, ok := validateArray(request, response)
elems, _, ok := validateArray(ctx, request, response)
if !ok {
return
}
Expand Down Expand Up @@ -76,7 +76,7 @@ func (validator arrayLenAtLeastValidator) MarkdownDescription(ctx context.Contex

// Validate performs the validation.
func (validator arrayLenAtLeastValidator) Validate(ctx context.Context, request tfsdk.ValidateAttributeRequest, response *tfsdk.ValidateAttributeResponse) {
elems, _, ok := validateArray(request, response)
elems, _, ok := validateArray(ctx, request, response)
if !ok {
return
}
Expand Down Expand Up @@ -120,7 +120,7 @@ func (validator arrayLenAtMostValidator) MarkdownDescription(ctx context.Context

// Validate performs the validation.
func (validator arrayLenAtMostValidator) Validate(ctx context.Context, request tfsdk.ValidateAttributeRequest, response *tfsdk.ValidateAttributeResponse) {
elems, _, ok := validateArray(request, response)
elems, _, ok := validateArray(ctx, request, response)
if !ok {
return
}
Expand Down Expand Up @@ -162,33 +162,38 @@ func setKeyer(ctx context.Context, path *tftypes.AttributePath, i int, v attr.Va
return path.WithElementKeyValue(val), nil
}

func validateArray(request tfsdk.ValidateAttributeRequest, response *tfsdk.ValidateAttributeResponse) ([]attr.Value, arrayKeyer, bool) {
func validateArray(ctx context.Context, request tfsdk.ValidateAttributeRequest, response *tfsdk.ValidateAttributeResponse) ([]attr.Value, arrayKeyer, bool) {
var elemKeyer arrayKeyer
var elems []attr.Value
switch v := request.AttributeConfig.(type) {
case types.List:
if v.Null || v.Unknown {
return elems, elemKeyer, false
}

elemKeyer = listKeyer
elems = v.Elems
var v types.List

diags := tfsdk.ValueAs(ctx, request.AttributeConfig, &v)

if diags.HasError() {
var v types.Set

diags := tfsdk.ValueAs(ctx, request.AttributeConfig, &v)

if diags.HasError() {
response.Diagnostics = append(response.Diagnostics, diags...)

case types.Set:
return elems, elemKeyer, false
} else {
if v.Null || v.Unknown {
return elems, elemKeyer, false
}

elemKeyer = setKeyer
elems = v.Elems
}
} else {
if v.Null || v.Unknown {
return elems, elemKeyer, false
}

elemKeyer = setKeyer
elemKeyer = listKeyer
elems = v.Elems

default:
response.Diagnostics.Append(ccdiag.NewIncorrectValueTypeAttributeError(
request.AttributePath,
v,
))

return elems, elemKeyer, false
}

return elems, elemKeyer, true
Expand Down
46 changes: 25 additions & 21 deletions internal/validate/float.go
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ func (validator floatBetweenValidator) MarkdownDescription(ctx context.Context)

// Validate performs the validation.
func (validator floatBetweenValidator) Validate(ctx context.Context, request tfsdk.ValidateAttributeRequest, response *tfsdk.ValidateAttributeResponse) {
f, ok := validateFloat(request, response)
f, ok := validateFloat(ctx, request, response)
if !ok {
return
}
Expand Down Expand Up @@ -74,7 +74,7 @@ func (validator floatAtLeastValidator) MarkdownDescription(ctx context.Context)

// Validate performs the validation.
func (validator floatAtLeastValidator) Validate(ctx context.Context, request tfsdk.ValidateAttributeRequest, response *tfsdk.ValidateAttributeResponse) {
f, ok := validateFloat(request, response)
f, ok := validateFloat(ctx, request, response)
if !ok {
return
}
Expand Down Expand Up @@ -115,7 +115,7 @@ func (validator floatAtMostValidator) MarkdownDescription(ctx context.Context) s

// Validate performs the validation.
func (validator floatAtMostValidator) Validate(ctx context.Context, request tfsdk.ValidateAttributeRequest, response *tfsdk.ValidateAttributeResponse) {
f, ok := validateFloat(request, response)
f, ok := validateFloat(ctx, request, response)
if !ok {
return
}
Expand All @@ -137,30 +137,34 @@ func FloatAtMost(max float64) tfsdk.AttributeValidator {
}
}

func validateFloat(request tfsdk.ValidateAttributeRequest, response *tfsdk.ValidateAttributeResponse) (float64, bool) {
switch n := request.AttributeConfig.(type) {
case types.Float64:
if n.Unknown || n.Null {
func validateFloat(ctx context.Context, request tfsdk.ValidateAttributeRequest, response *tfsdk.ValidateAttributeResponse) (float64, bool) {
var n types.Float64

diags := tfsdk.ValueAs(ctx, request.AttributeConfig, &n)

if diags.HasError() {
var n types.Number

diags := tfsdk.ValueAs(ctx, request.AttributeConfig, &n)

if diags.HasError() {
response.Diagnostics = append(response.Diagnostics, diags...)

return 0, false
}
} else {
if n.Unknown || n.Null {
return 0, false
}

return n.Value, true
f, _ := n.Value.Float64()

case types.Number:
return f, true
}
} else {
if n.Unknown || n.Null {
return 0, false
}

f, _ := n.Value.Float64()

return f, true

default:
response.Diagnostics.Append(diag.NewIncorrectValueTypeAttributeError(
request.AttributePath,
request.AttributeConfig,
))

return 0, false
return n.Value, true
}
}
2 changes: 1 addition & 1 deletion internal/validate/for_each.go
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@ func (validator arrayForEachValidator) MarkdownDescription(ctx context.Context)

// Validate performs the validation.
func (validator arrayForEachValidator) Validate(ctx context.Context, request tfsdk.ValidateAttributeRequest, response *tfsdk.ValidateAttributeResponse) {
elems, elemKeyer, ok := validateArray(request, response)
elems, elemKeyer, ok := validateArray(ctx, request, response)
if !ok {
return
}
Expand Down
53 changes: 19 additions & 34 deletions internal/validate/for_each_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ import (
"github.com/hashicorp/terraform-plugin-framework/tfsdk"
"github.com/hashicorp/terraform-plugin-framework/types"
"github.com/hashicorp/terraform-plugin-go/tftypes"
ccdiag "github.com/hashicorp/terraform-provider-awscc/internal/diag"
"github.com/hashicorp/terraform-provider-awscc/internal/tfresource"
)

func TestArrayForEachValidator(t *testing.T) {
Expand All @@ -20,20 +20,17 @@ func TestArrayForEachValidator(t *testing.T) {
rootPath := tftypes.NewAttributePath().WithAttributeName("test")

type testCase struct {
val tftypes.Value
f func(context.Context, tftypes.Value) (attr.Value, error)
validator tfsdk.AttributeValidator
expectedDiag diag.Diagnostic
val tftypes.Value
f func(context.Context, tftypes.Value) (attr.Value, error)
validator tfsdk.AttributeValidator
expectError bool
}
tests := map[string]testCase{
"not a list": {
val: tftypes.NewValue(tftypes.Bool, true),
f: types.BoolType.ValueFromTerraform,
validator: StringInSlice([]string{"alpha", "beta", "gamma"}),
expectedDiag: ccdiag.NewIncorrectValueTypeAttributeError(
rootPath,
types.Bool{},
),
val: tftypes.NewValue(tftypes.Bool, true),
f: types.BoolType.ValueFromTerraform,
validator: StringInSlice([]string{"alpha", "beta", "gamma"}),
expectError: true,
},

"unknown list": {
Expand Down Expand Up @@ -67,13 +64,9 @@ func TestArrayForEachValidator(t *testing.T) {
tftypes.NewValue(tftypes.String, "gamma"),
tftypes.NewValue(tftypes.String, "delta"),
}),
f: types.ListType{ElemType: types.StringType}.ValueFromTerraform,
validator: StringInSlice([]string{"alpha", "beta", "gamma"}),
expectedDiag: newStringNotInSliceError(
rootPath.WithElementKeyInt(3),
[]string{"alpha", "beta", "gamma"},
"delta",
),
f: types.ListType{ElemType: types.StringType}.ValueFromTerraform,
validator: StringInSlice([]string{"alpha", "beta", "gamma"}),
expectError: true,
},
"list of string with unknown element": {
val: tftypes.NewValue(tftypes.List{ElementType: tftypes.String}, []tftypes.Value{
Expand Down Expand Up @@ -116,13 +109,9 @@ func TestArrayForEachValidator(t *testing.T) {
tftypes.NewValue(tftypes.String, "gamma"),
tftypes.NewValue(tftypes.String, "delta"),
}),
f: types.SetType{ElemType: types.StringType}.ValueFromTerraform,
validator: StringInSlice([]string{"alpha", "beta", "gamma"}),
expectedDiag: newStringNotInSliceError(
rootPath.WithElementKeyValue(tftypes.NewValue(tftypes.String, "delta")),
[]string{"alpha", "beta", "gamma"},
"delta",
),
f: types.SetType{ElemType: types.StringType}.ValueFromTerraform,
validator: StringInSlice([]string{"alpha", "beta", "gamma"}),
expectError: true,
},
"set of string with unknown element": {
val: tftypes.NewValue(tftypes.Set{ElementType: tftypes.String}, []tftypes.Value{
Expand Down Expand Up @@ -152,16 +141,12 @@ func TestArrayForEachValidator(t *testing.T) {
response := tfsdk.ValidateAttributeResponse{}
ArrayForEach(test.validator).Validate(ctx, request, &response)

if !response.Diagnostics.HasError() && test.expectedDiag != nil {
t.Fatal("expected error diagnostics, got no error")
}

if response.Diagnostics.HasError() && !response.Diagnostics.Contains(test.expectedDiag) {
t.Fatalf(`expected diagnostics to contain "%s", got %s`, printDiagnostic(test.expectedDiag), printDiagnostics(response.Diagnostics))
if !response.Diagnostics.HasError() && test.expectError {
t.Fatal("expected error, got no error")
}

if response.Diagnostics.HasError() && test.expectedDiag == nil {
t.Fatalf(`got unexpected error diagnostics: %s`, printDiagnostics(response.Diagnostics))
if response.Diagnostics.HasError() && !test.expectError {
t.Fatalf("got unexpected error: %s", tfresource.DiagsError(response.Diagnostics))
}
})
}
Expand Down
Loading

0 comments on commit d736861

Please sign in to comment.