Skip to content

Commit

Permalink
Update reused 'element from id' logic to use errors instead of diagno…
Browse files Browse the repository at this point in the history
…stics. Remove use of warnings as a result, opt for debug log instead.
  • Loading branch information
SarahFrench committed Mar 12, 2024
1 parent 7f0dc96 commit b56708e
Show file tree
Hide file tree
Showing 2 changed files with 17 additions and 35 deletions.
25 changes: 9 additions & 16 deletions mmv1/third_party/terraform/functions/element_from_id.go
Original file line number Diff line number Diff line change
@@ -1,36 +1,29 @@
package functions

import (
"context"
"fmt"
"regexp"

"github.com/hashicorp/terraform-plugin-framework/function"
"github.com/hashicorp/terraform-plugin-log/tflog"
)

const noMatchesErrorSummary string = "No matches present in the input string"
const ambiguousMatchesWarningSummary string = "Ambiguous input string could contain more than one match"

// ValidateElementFromIdArguments is reusable validation logic used in provider-defined functions that use the getElementFromId function
func ValidateElementFromIdArguments(input string, regex *regexp.Regexp, pattern string, resp *function.RunResponse) {
// ValidateElementFromIdArguments is reusable validation logic used in provider-defined functions that use the GetElementFromId function
func ValidateElementFromIdArguments(ctx context.Context, input string, regex *regexp.Regexp, pattern string) *function.FuncError {
submatches := regex.FindAllStringSubmatchIndex(input, -1)

// Zero matches means unusable input; error returned
if len(submatches) == 0 {
resp.Diagnostics.AddArgumentError(
0,
noMatchesErrorSummary,
fmt.Sprintf("The input string \"%s\" doesn't contain the expected pattern \"%s\".", input, pattern),
)
return function.NewArgumentFuncError(0, fmt.Sprintf("The input string \"%s\" doesn't contain the expected pattern \"%s\".", input, pattern))
}

// >1 matches means input usable but not ideal; issue warning
// >1 matches means input usable but not ideal; debug log
if len(submatches) > 1 {
resp.Diagnostics.AddArgumentWarning(
0,
ambiguousMatchesWarningSummary,
fmt.Sprintf("The input string \"%s\" contains more than one match for the pattern \"%s\". Terraform will use the first found match.", input, pattern),
)
tflog.Debug(ctx, fmt.Sprintf("The input string \"%s\" contains more than one match for the pattern \"%s\" expected by the provider function. Terraform will use the first found match.", input, pattern))
}

return nil
}

// GetElementFromId is reusable logic that is used in multiple provider-defined functions for pulling elements out of self links and ids of resources and data sources
Expand Down
Original file line number Diff line number Diff line change
@@ -1,11 +1,10 @@
package functions_test

import (
"context"
"regexp"
"testing"

"github.com/hashicorp/terraform-plugin-framework/function"
"github.com/hashicorp/terraform-plugin-framework/types/basetypes"
tpg_functions "github.com/hashicorp/terraform-provider-google/google/functions"
)

Expand All @@ -19,43 +18,33 @@ func TestFunctionInternals_ValidateElementFromIdArguments(t *testing.T) {
Input string
ExpectedElement string
ExpectError bool
ExpectWarning bool
}{
"it sets an error in diags if no match is found": {
"it sets an error if no match is found": {
Input: "one/element-1/three/element-3",
ExpectError: true,
},
"it sets a warning in diags if more than one match is found": {
"it doesn't set an error if more than one match is found": {
Input: "two/element-2/two/element-2/two/element-2",
ExpectedElement: "element-2",
ExpectWarning: true,
},
}

for tn, tc := range cases {
t.Run(tn, func(t *testing.T) {

// Arrange
resp := function.RunResponse{
Result: function.NewResultData(basetypes.StringValue{}),
}
ctx := context.Background()

// Act
tpg_functions.ValidateElementFromIdArguments(tc.Input, regex, pattern, &resp)
err := tpg_functions.ValidateElementFromIdArguments(ctx, tc.Input, regex, pattern)

// Assert
if resp.Diagnostics.HasError() && !tc.ExpectError {
t.Fatalf("Unexpected error(s) were set in response diags: %s", resp.Diagnostics.Errors())
if err != nil && !tc.ExpectError {
t.Fatalf("Unexpected error(s) were set in response diags: %s", err.Text)
}
if !resp.Diagnostics.HasError() && tc.ExpectError {
if err == nil && tc.ExpectError {
t.Fatal("Expected error(s) to be set in response diags, but there were none.")
}
if (resp.Diagnostics.WarningsCount() > 0) && !tc.ExpectWarning {
t.Fatalf("Unexpected warning(s) were set in response diags: %s", resp.Diagnostics.Warnings())
}
if (resp.Diagnostics.WarningsCount() == 0) && tc.ExpectWarning {
t.Fatal("Expected warning(s) to be set in response diags, but there were none.")
}
})
}
}
Expand Down

0 comments on commit b56708e

Please sign in to comment.