Skip to content

Commit

Permalink
hcl: When writting Module variables normalize the names
Browse files Browse the repository at this point in the history
As in some cases, like 'tags', they have keys that cannot be converted direclty into valirables names
so we have to normailze them.

For this we reused the 'tag' logic and abstracted it to the 'util' lib so it can be shared between the 2 packages
  • Loading branch information
xescugc committed Aug 30, 2021
1 parent 19ecf1c commit 09f8688
Show file tree
Hide file tree
Showing 6 changed files with 74 additions and 12 deletions.
5 changes: 5 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,11 @@
- Integration between Interpolation and Modules has been changed to not generate invalid HCL references
([Issue #219](https://github.com/cycloidio/terracognita/issues/219)

### Fixed

- Variables names will now be normalized to be valid HCL
([PUll #219](https://github.com/cycloidio/terracognita/pull/227)

## [0.7.2] _2021-08-13_

### Added
Expand Down
7 changes: 4 additions & 3 deletions hcl/writer.go
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ import (
"github.com/cycloidio/terracognita/errcode"
"github.com/cycloidio/terracognita/log"
"github.com/cycloidio/terracognita/provider"
"github.com/cycloidio/terracognita/util"
"github.com/cycloidio/terracognita/writer"
"github.com/hashicorp/hcl/v2/hclwrite"
"github.com/pkg/errors"
Expand Down Expand Up @@ -362,7 +363,7 @@ func walkVariables(cfg map[string]interface{}, validVariables map[string]struct{
case []interface{}:
if len(v) == 0 {
if hasKey(validVariables, currentKey) {
varName := strings.ReplaceAll(currentKey, ".", "_")
varName := util.NormalizeName(strings.ReplaceAll(currentKey, ".", "_"))
variables[varName] = map[string]interface{}{
"default": cfg[key],
}
Expand All @@ -378,7 +379,7 @@ func walkVariables(cfg map[string]interface{}, validVariables map[string]struct{
}
} else {
if hasKey(validVariables, currentKey) {
varName := strings.ReplaceAll(currentKey, ".", "_")
varName := util.NormalizeName(strings.ReplaceAll(currentKey, ".", "_"))
variables[varName] = map[string]interface{}{
"default": cfg[key],
}
Expand All @@ -389,7 +390,7 @@ func walkVariables(cfg map[string]interface{}, validVariables map[string]struct{
// This means is a "simple" value so we can
// directly replace it with the variable
if hasKey(validVariables, currentKey) {
varName := strings.ReplaceAll(currentKey, ".", "_")
varName := util.NormalizeName(strings.ReplaceAll(currentKey, ".", "_"))
variables[varName] = map[string]interface{}{
"default": cfg[key],
}
Expand Down
11 changes: 11 additions & 0 deletions hcl/writer_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -332,6 +332,9 @@ resource "type" "name" {
"key": "value",
"key2": "value",
"key3": []interface{}{},
"key4": map[string]interface{}{
"nested:key:4": "value4",
},
}
ehcl = `
resource "type" "name" {
Expand All @@ -342,12 +345,16 @@ resource "type" "name2" {
key = var.type_name2_key
key2 = var.type_name2_key2
key3 = var.type_name2_key3
key4 {
"nested:key:4" = var.type_name2_key4_nested_key_4
}
}
module "test" {
# type_name2_key = "value"
# type_name2_key2 = "value"
# type_name2_key3 = []
# type_name2_key4_nested_key_4 = "value4"
# type_name_key = "value"
source = "./module-test"
}
Expand Down Expand Up @@ -381,6 +388,10 @@ variable "type_name2_key3" {
default = []
}
variable "type_name2_key4_nested_key_4" {
default = "value4"
}
variable "type_name_key" {
default = "value"
}
Expand Down
12 changes: 3 additions & 9 deletions tag/tag.go
Original file line number Diff line number Diff line change
Expand Up @@ -11,14 +11,14 @@ import (
"github.com/aws/aws-sdk-go/service/rds"
"github.com/chr4/pwgen"
"github.com/cycloidio/terracognita/errcode"
"github.com/cycloidio/terracognita/util"
"github.com/hashicorp/hcl/v2/hclsyntax"
"github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema"
)

// nameRegexp is the new regexp used to validate the names
// of the resources on TF (defined on configs/configschema/internal_validate.go)
var nameRegexp = regexp.MustCompile(`^[a-z0-9_]+$`)
var invalidNameRegexp = regexp.MustCompile(`[^a-z0-9_]`)

// Tag it's an easy representation of
// a ec2.Filter for tags
Expand Down Expand Up @@ -75,8 +75,8 @@ func GetNameFromTag(key string, srd *schema.ResourceData, fallback string) strin
n = strings.ToLower(name.(string))
}

forcedN := forceResourceName(n)
forcedFallback := forceResourceName(fallback)
forcedN := util.NormalizeName(n)
forcedFallback := util.NormalizeName(fallback)

if isValidResourceName(n) && hclsyntax.ValidIdentifier(n) {
return n
Expand All @@ -97,12 +97,6 @@ func isValidResourceName(name string) bool {
return nameRegexp.MatchString(name)
}

// forceResourceName will try to replace all the
// invalid characters of the name for _
func forceResourceName(name string) string {
return invalidNameRegexp.ReplaceAllString(name, "_")
}

// GetOtherTags used to check other possible tag attributes on resources
func GetOtherTags(provider string, srd *schema.ResourceData, filterTag Tag) (string, bool) {
// keep the same logic as r.data.GetOk
Expand Down
14 changes: 14 additions & 0 deletions util/name.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
package util

import (
"regexp"
"strings"
)

var invalidNameRegexp = regexp.MustCompile(`[^a-z0-9_]`)

// NormalizeName will convert the n into an low case alphanumeric value
// and the invalid characters will be replaced by '_'
func NormalizeName(n string) string {
return invalidNameRegexp.ReplaceAllString(strings.ToLower(n), "_")
}
37 changes: 37 additions & 0 deletions util/name_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
package util_test

import (
"testing"

"github.com/cycloidio/terracognita/util"
"github.com/stretchr/testify/assert"
)

func TestNormalizeName(t *testing.T) {
tests := []struct {
Name string
In string
Expected string
}{
{
Name: "NoChange",
In: "in",
Expected: "in",
},
{
Name: "UpperCase",
In: "IN",
Expected: "in",
},
{
Name: "Invalid",
In: ":a",
Expected: "_a",
},
}
for _, tt := range tests {
t.Run(tt.Name, func(t *testing.T) {
assert.Equal(t, tt.Expected, util.NormalizeName(tt.In))
})
}
}

0 comments on commit 09f8688

Please sign in to comment.