From d78bd61620c85e1eac9505254b862f646f217d82 Mon Sep 17 00:00:00 2001 From: Ian Wahbe Date: Thu, 11 Apr 2024 18:45:10 +0200 Subject: [PATCH 1/4] Refactor TestTerraformOutputsWithSecretsSupported into table driven tests This is only a refactor of test code for clarity. --- pkg/tfbridge/schema_test.go | 429 ++++++++++++++++++++++++------------ 1 file changed, 283 insertions(+), 146 deletions(-) diff --git a/pkg/tfbridge/schema_test.go b/pkg/tfbridge/schema_test.go index f479ee643..16bfbe8b6 100644 --- a/pkg/tfbridge/schema_test.go +++ b/pkg/tfbridge/schema_test.go @@ -330,170 +330,307 @@ type MyString string // TestTerraformOutputsWithSecretsSupported verifies that we translate Terraform outputs into Pulumi outputs and // treating sensitive outputs as secrets func TestTerraformOutputsWithSecretsSupported(t *testing.T) { - ctx := context.Background() - for _, f := range factories { - t.Run(f.SDKVersion(), func(t *testing.T) { - result := MakeTerraformOutputs( - ctx, - f.NewTestProvider(), - map[string]interface{}{ - "nil_property_value": nil, - "bool_property_value": false, - "number_property_value": 42, - "float_property_value": 99.6767932, - "string_property_value": "ognirts", - "my_string_property_value": MyString("ognirts"), - "array_property_value": []interface{}{"an array"}, - "object_property_value": map[string]interface{}{ - "property_a": "a", - "property_b": true, - }, - "map_property_value": map[string]interface{}{ - "propertyA": "a", - "propertyB": true, - "propertyC": map[string]interface{}{ - "nestedPropertyA": true, - }, - }, - "nested_resource": []interface{}{ - map[string]interface{}{ - "configuration": map[string]interface{}{ - "configurationValue": true, - }, - }, + t.Parallel() + + tests := []struct { + name string + tfValue map[string]any + tfType map[string]*schema.Schema + schemaInfo map[string]*SchemaInfo + expect autogold.Value + }{ + { + name: "nil_property_value", + tfValue: map[string]any{ + "nil_property_value": nil, + }, + expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("nilPropertyValue"): resource.PropertyValue{}}), + }, + { + name: "bool_property_value", + tfValue: map[string]any{ + "bool_property_value": false, + }, + expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("boolPropertyValue"): resource.PropertyValue{ + V: false, + }}), + }, + { + name: "number_property_value", + tfValue: map[string]any{ + "number_property_value": 42, + }, + expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("numberPropertyValue"): resource.PropertyValue{ + V: 42, + }}), + }, + { + name: "float_property_value", + tfValue: map[string]any{ + "float_property_value": 99.6767932, + }, + tfType: map[string]*schema.Schema{ + "float_property_value": {Type: shim.TypeFloat}, + }, + expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("floatPropertyValue"): resource.PropertyValue{ + V: 99.6767932, + }}), + }, + { + name: "string_property_value", + tfValue: map[string]any{ + "string_property_value": "ognirts", + }, + schemaInfo: map[string]*SchemaInfo{ + // Reverse map string_property_value to the stringo property. + "string_property_value": { + Name: "stringo", + }, + }, + expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("stringo"): resource.PropertyValue{ + V: "ognirts", + }}), + }, + { + name: "my_string_property_value", + tfValue: map[string]any{ + "my_string_property_value": MyString("ognirts"), + }, + tfType: map[string]*schema.Schema{"my_string_property_value": {Type: shim.TypeString}}, + expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("myStringPropertyValue"): resource.PropertyValue{ + V: "ognirts", + }}), + }, + { + name: "array_property_value", + tfValue: map[string]any{ + "array_property_value": []interface{}{"an array"}, + }, + expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("arrayPropertyValue"): resource.PropertyValue{ + V: []resource.PropertyValue{{ + V: "an array", + }}, + }}), + }, + { + name: "object_property_value", + tfValue: map[string]any{ + "object_property_value": map[string]interface{}{ + "property_a": "a", + "property_b": true, + }, + }, + expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("objectPropertyValue"): resource.PropertyValue{ + V: resource.PropertyMap{ + resource.PropertyKey("propertyA"): resource.PropertyValue{ + V: "a", }, - "optional_config": []interface{}{ - map[string]interface{}{ - "some_value": true, - "some_other_value": "a value", - }, + resource.PropertyKey("propertyB"): resource.PropertyValue{V: true}, + }, + }}), + }, + { + name: "map_property_value", + tfValue: map[string]any{ + "map_property_value": map[string]interface{}{ + "propertyA": "a", + "propertyB": true, + "propertyC": map[string]interface{}{ + "nestedPropertyA": true, }, - "optional_config_other": []interface{}{ - map[string]interface{}{ - "some_value": true, - "some_other_value": "a value", - }, + }, + }, + tfType: map[string]*schema.Schema{ + // Type mapPropertyValue as a map so that keys aren't mangled in the usual way. + "map_property_value": {Type: shim.TypeMap}, + }, + expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("mapPropertyValue"): resource.PropertyValue{ + V: resource.PropertyMap{ + resource.PropertyKey("propertyA"): resource.PropertyValue{ + V: "a", }, - "secret_value": "MyPassword", - "nested_secret_value": []interface{}{ - map[string]interface{}{ - "secret_value": "MyPassword", + resource.PropertyKey("propertyB"): resource.PropertyValue{V: true}, + resource.PropertyKey("propertyC"): resource.PropertyValue{V: resource.PropertyMap{resource.PropertyKey("nestedPropertyA"): resource.PropertyValue{ + V: true, + }}}, + }, + }}), + }, + { + name: "nested_resource", + tfValue: map[string]any{ + "nested_resource": []interface{}{ + map[string]interface{}{ + "configuration": map[string]interface{}{ + "configurationValue": true, }, }, }, - f.NewSchemaMap(map[string]*schema.Schema{ - // Type mapPropertyValue as a map so that keys aren't mangled in the usual way. - "float_property_value": {Type: shim.TypeFloat}, - "my_string_property_value": {Type: shim.TypeString}, - "map_property_value": {Type: shim.TypeMap}, - "nested_resource": { - Type: shim.TypeList, - MaxItems: 2, - // Embed a `*schema.Resource` to validate that type directed - // walk of the schema successfully walks inside Resources as well - // as Schemas. - Elem: (&schema.Resource{ - Schema: schemaMap(map[string]*schema.Schema{ - "configuration": {Type: shim.TypeMap}, - }), - }).Shim(), - }, - "optional_config": { - Type: shim.TypeList, - MaxItems: 1, - Elem: (&schema.Resource{ - Schema: schemaMap(map[string]*schema.Schema{ - "some_value": {Type: shim.TypeBool}, - "some_other_value": {Type: shim.TypeString}, - }), - }).Shim(), - }, - "optional_config_other": { - Type: shim.TypeList, - Elem: (&schema.Resource{ - Schema: schemaMap(map[string]*schema.Schema{ - "some_value": {Type: shim.TypeBool}, - "some_other_value": {Type: shim.TypeString}, - }), - }).Shim(), - }, - "secret_value": { - Type: shim.TypeString, - Optional: true, - Sensitive: true, - }, - "nested_secret_value": { - Type: shim.TypeList, - MaxItems: 1, - Elem: (&schema.Resource{ - Schema: schemaMap(map[string]*schema.Schema{ - "secret_value": { - Type: shim.TypeString, - Sensitive: true, - }, - }), - }).Shim(), - }, - }), - map[string]*SchemaInfo{ - // Reverse map string_property_value to the stringo property. - "string_property_value": { - Name: "stringo", - }, - "optional_config_other": { - Name: "optionalConfigOther", - MaxItemsOne: boolPointer(true), + }, + tfType: map[string]*schema.Schema{ + "nested_resource": { + Type: shim.TypeList, + MaxItems: 2, + // Embed a `*schema.Resource` to validate that type directed + // walk of the schema successfully walks inside Resources as well + // as Schemas. + Elem: (&schema.Resource{ + Schema: schemaMap(map[string]*schema.Schema{ + "configuration": {Type: shim.TypeMap}, + }), + }).Shim(), + }, + }, + expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("nestedResources"): resource.PropertyValue{ + V: []resource.PropertyValue{{ + V: resource.PropertyMap{resource.PropertyKey("configuration"): resource.PropertyValue{ + V: resource.PropertyMap{resource.PropertyKey("configurationValue"): resource.PropertyValue{ + V: true, + }}, + }}, + }}, + }}), + }, + { + name: "optional_config", + tfValue: map[string]any{ + "optional_config": []interface{}{ + map[string]interface{}{ + "some_value": true, + "some_other_value": "a value", }, }, - nil, /* assets */ - false, /* useRawNames */ - true, /* supportsSecrets */ - ) - assert.Equal(t, resource.NewPropertyMapFromMap(map[string]interface{}{ - "nilPropertyValue": nil, - "boolPropertyValue": false, - "numberPropertyValue": 42, - "floatPropertyValue": 99.6767932, - "stringo": "ognirts", - "myStringPropertyValue": "ognirts", - "arrayPropertyValue": []interface{}{"an array"}, - "objectPropertyValue": map[string]interface{}{ - "propertyA": "a", - "propertyB": true, + }, + tfType: map[string]*schema.Schema{ + "optional_config": { + Type: shim.TypeList, + MaxItems: 1, + Elem: (&schema.Resource{ + Schema: schemaMap(map[string]*schema.Schema{ + "some_value": {Type: shim.TypeBool}, + "some_other_value": {Type: shim.TypeString}, + }), + }).Shim(), }, - "mapPropertyValue": map[string]interface{}{ - "propertyA": "a", - "propertyB": true, - "propertyC": map[string]interface{}{ - "nestedPropertyA": true, + }, + expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("optionalConfig"): resource.PropertyValue{ + V: resource.PropertyMap{ + resource.PropertyKey("someOtherValue"): resource.PropertyValue{ + V: "a value", }, + resource.PropertyKey("someValue"): resource.PropertyValue{V: true}, }, - "nestedResources": []map[string]interface{}{{ - "configuration": map[string]interface{}{ - "configurationValue": true, + }}), + }, + { + name: "optional_config_other", + tfValue: map[string]any{ + "optional_config_other": []interface{}{ + map[string]interface{}{ + "some_value": true, + "some_other_value": "a value", }, - }}, - "optionalConfig": map[string]interface{}{ - "someValue": true, - "someOtherValue": "a value", }, - "optionalConfigOther": map[string]interface{}{ - "someValue": true, - "someOtherValue": "a value", + }, + tfType: map[string]*schema.Schema{ + "optional_config_other": { + Type: shim.TypeList, + Elem: (&schema.Resource{ + Schema: schemaMap(map[string]*schema.Schema{ + "some_value": {Type: shim.TypeBool}, + "some_other_value": {Type: shim.TypeString}, + }), + }).Shim(), }, - "secretValue": &resource.Secret{ - Element: resource.PropertyValue{ - V: "MyPassword", + }, + schemaInfo: map[string]*SchemaInfo{ + "optional_config_other": { + Name: "optionalConfigOther", + MaxItemsOne: boolPointer(true), + }, + }, + expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("optionalConfigOther"): resource.PropertyValue{ + V: resource.PropertyMap{ + resource.PropertyKey("someOtherValue"): resource.PropertyValue{ + V: "a value", }, + resource.PropertyKey("someValue"): resource.PropertyValue{V: true}, }, - "nestedSecretValue": map[string]interface{}{ - "secretValue": &resource.Secret{ - Element: resource.PropertyValue{ - V: "MyPassword", - }, + }}), + }, + { + name: "secret_value", + tfValue: map[string]any{ + "secret_value": "MyPassword", + }, + tfType: map[string]*schema.Schema{ + "secret_value": { + Type: shim.TypeString, + Optional: true, + Sensitive: true, + }, + }, + expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("secretValue"): resource.PropertyValue{ + V: &resource.Secret{Element: resource.PropertyValue{ + V: "MyPassword", + }}, + }}), + }, + { + name: "nested_secret_value", + tfValue: map[string]any{ + "nested_secret_value": []interface{}{ + map[string]interface{}{ + "secret_value": "MyPassword", }, }, - }), result) + }, + tfType: map[string]*schema.Schema{ + "nested_secret_value": { + Type: shim.TypeList, + MaxItems: 1, + Elem: (&schema.Resource{ + Schema: schemaMap(map[string]*schema.Schema{ + "secret_value": { + Type: shim.TypeString, + Sensitive: true, + }, + }), + }).Shim(), + }, + }, + expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("nestedSecretValue"): resource.PropertyValue{ + V: resource.PropertyMap{resource.PropertyKey("secretValue"): resource.PropertyValue{ + V: &resource.Secret{Element: resource.PropertyValue{ + V: "MyPassword", + }}, + }}, + }}), + }, + } + + for _, tt := range tests { + tt := tt + t.Run("name", func(t *testing.T) { + t.Parallel() + for _, f := range factories { + f := f + t.Run(f.SDKVersion(), func(t *testing.T) { + t.Parallel() + ctx := context.Background() + result := MakeTerraformOutputs( + ctx, + f.NewTestProvider(), + tt.tfValue, + f.NewSchemaMap(tt.tfType), + tt.schemaInfo, + nil, /* assets */ + false, /* useRawNames */ + true, /* supportsSecrets */ + ) + tt.expect.Equal(t, result) + }) + } }) } } From 0bd4c6977c1d0c24b45678f63acac816c5d3bc96 Mon Sep 17 00:00:00 2001 From: Ian Wahbe Date: Thu, 11 Apr 2024 19:15:06 +0200 Subject: [PATCH 2/4] Refactor: reduce verbosity --- pkg/tfbridge/schema_test.go | 259 ++++++++++++++++-------------------- 1 file changed, 116 insertions(+), 143 deletions(-) diff --git a/pkg/tfbridge/schema_test.go b/pkg/tfbridge/schema_test.go index 16bfbe8b6..aaf106097 100644 --- a/pkg/tfbridge/schema_test.go +++ b/pkg/tfbridge/schema_test.go @@ -334,78 +334,60 @@ func TestTerraformOutputsWithSecretsSupported(t *testing.T) { tests := []struct { name string - tfValue map[string]any - tfType map[string]*schema.Schema - schemaInfo map[string]*SchemaInfo + tfValue any + tfType *schema.Schema + schemaInfo *SchemaInfo expect autogold.Value }{ { - name: "nil_property_value", - tfValue: map[string]any{ - "nil_property_value": nil, - }, - expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("nilPropertyValue"): resource.PropertyValue{}}), + name: "nil_property_value", + tfValue: nil, + expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("nilPropertyValue"): resource.PropertyValue{}}), }, { - name: "bool_property_value", - tfValue: map[string]any{ - "bool_property_value": false, - }, + name: "bool_property_value", + tfValue: false, expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("boolPropertyValue"): resource.PropertyValue{ V: false, }}), }, { - name: "number_property_value", - tfValue: map[string]any{ - "number_property_value": 42, - }, + name: "number_property_value", + tfValue: 42, expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("numberPropertyValue"): resource.PropertyValue{ V: 42, }}), }, { - name: "float_property_value", - tfValue: map[string]any{ - "float_property_value": 99.6767932, - }, - tfType: map[string]*schema.Schema{ - "float_property_value": {Type: shim.TypeFloat}, - }, + name: "float_property_value", + tfValue: 99.6767932, + tfType: &schema.Schema{Type: shim.TypeFloat}, expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("floatPropertyValue"): resource.PropertyValue{ V: 99.6767932, }}), }, { - name: "string_property_value", - tfValue: map[string]any{ - "string_property_value": "ognirts", - }, - schemaInfo: map[string]*SchemaInfo{ + name: "string_property_value", + tfValue: "ognirts", + schemaInfo: &SchemaInfo{ // Reverse map string_property_value to the stringo property. - "string_property_value": { - Name: "stringo", - }, + Name: "stringo", }, expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("stringo"): resource.PropertyValue{ V: "ognirts", }}), }, { - name: "my_string_property_value", - tfValue: map[string]any{ - "my_string_property_value": MyString("ognirts"), - }, - tfType: map[string]*schema.Schema{"my_string_property_value": {Type: shim.TypeString}}, + name: "my_string_property_value", + tfValue: MyString("ognirts"), + tfType: &schema.Schema{Type: shim.TypeString}, expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("myStringPropertyValue"): resource.PropertyValue{ V: "ognirts", }}), }, { - name: "array_property_value", - tfValue: map[string]any{ - "array_property_value": []interface{}{"an array"}, - }, + name: "array_property_value", + tfValue: []interface{}{"an array"}, expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("arrayPropertyValue"): resource.PropertyValue{ V: []resource.PropertyValue{{ V: "an array", @@ -414,11 +396,9 @@ func TestTerraformOutputsWithSecretsSupported(t *testing.T) { }, { name: "object_property_value", - tfValue: map[string]any{ - "object_property_value": map[string]interface{}{ - "property_a": "a", - "property_b": true, - }, + tfValue: map[string]interface{}{ + "property_a": "a", + "property_b": true, }, expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("objectPropertyValue"): resource.PropertyValue{ V: resource.PropertyMap{ @@ -431,18 +411,16 @@ func TestTerraformOutputsWithSecretsSupported(t *testing.T) { }, { name: "map_property_value", - tfValue: map[string]any{ - "map_property_value": map[string]interface{}{ - "propertyA": "a", - "propertyB": true, - "propertyC": map[string]interface{}{ - "nestedPropertyA": true, - }, + tfValue: map[string]interface{}{ + "propertyA": "a", + "propertyB": true, + "propertyC": map[string]interface{}{ + "nestedPropertyA": true, }, }, - tfType: map[string]*schema.Schema{ + tfType: &schema.Schema{ // Type mapPropertyValue as a map so that keys aren't mangled in the usual way. - "map_property_value": {Type: shim.TypeMap}, + Type: shim.TypeMap, }, expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("mapPropertyValue"): resource.PropertyValue{ V: resource.PropertyMap{ @@ -458,28 +436,24 @@ func TestTerraformOutputsWithSecretsSupported(t *testing.T) { }, { name: "nested_resource", - tfValue: map[string]any{ - "nested_resource": []interface{}{ - map[string]interface{}{ - "configuration": map[string]interface{}{ - "configurationValue": true, - }, + tfValue: []interface{}{ + map[string]interface{}{ + "configuration": map[string]interface{}{ + "configurationValue": true, }, }, }, - tfType: map[string]*schema.Schema{ - "nested_resource": { - Type: shim.TypeList, - MaxItems: 2, - // Embed a `*schema.Resource` to validate that type directed - // walk of the schema successfully walks inside Resources as well - // as Schemas. - Elem: (&schema.Resource{ - Schema: schemaMap(map[string]*schema.Schema{ - "configuration": {Type: shim.TypeMap}, - }), - }).Shim(), - }, + tfType: &schema.Schema{ + Type: shim.TypeList, + MaxItems: 2, + // Embed a `*schema.Resource` to validate that type directed + // walk of the schema successfully walks inside Resources as well + // as Schemas. + Elem: (&schema.Resource{ + Schema: schemaMap(map[string]*schema.Schema{ + "configuration": {Type: shim.TypeMap}, + }), + }).Shim(), }, expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("nestedResources"): resource.PropertyValue{ V: []resource.PropertyValue{{ @@ -493,25 +467,21 @@ func TestTerraformOutputsWithSecretsSupported(t *testing.T) { }, { name: "optional_config", - tfValue: map[string]any{ - "optional_config": []interface{}{ - map[string]interface{}{ - "some_value": true, - "some_other_value": "a value", - }, + tfValue: []interface{}{ + map[string]interface{}{ + "some_value": true, + "some_other_value": "a value", }, }, - tfType: map[string]*schema.Schema{ - "optional_config": { - Type: shim.TypeList, - MaxItems: 1, - Elem: (&schema.Resource{ - Schema: schemaMap(map[string]*schema.Schema{ - "some_value": {Type: shim.TypeBool}, - "some_other_value": {Type: shim.TypeString}, - }), - }).Shim(), - }, + tfType: &schema.Schema{ + Type: shim.TypeList, + MaxItems: 1, + Elem: (&schema.Resource{ + Schema: schemaMap(map[string]*schema.Schema{ + "some_value": {Type: shim.TypeBool}, + "some_other_value": {Type: shim.TypeString}, + }), + }).Shim(), }, expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("optionalConfig"): resource.PropertyValue{ V: resource.PropertyMap{ @@ -524,30 +494,24 @@ func TestTerraformOutputsWithSecretsSupported(t *testing.T) { }, { name: "optional_config_other", - tfValue: map[string]any{ - "optional_config_other": []interface{}{ - map[string]interface{}{ - "some_value": true, - "some_other_value": "a value", - }, + tfValue: []interface{}{ + map[string]interface{}{ + "some_value": true, + "some_other_value": "a value", }, }, - tfType: map[string]*schema.Schema{ - "optional_config_other": { - Type: shim.TypeList, - Elem: (&schema.Resource{ - Schema: schemaMap(map[string]*schema.Schema{ - "some_value": {Type: shim.TypeBool}, - "some_other_value": {Type: shim.TypeString}, - }), - }).Shim(), - }, + tfType: &schema.Schema{ + Type: shim.TypeList, + Elem: (&schema.Resource{ + Schema: schemaMap(map[string]*schema.Schema{ + "some_value": {Type: shim.TypeBool}, + "some_other_value": {Type: shim.TypeString}, + }), + }).Shim(), }, - schemaInfo: map[string]*SchemaInfo{ - "optional_config_other": { - Name: "optionalConfigOther", - MaxItemsOne: boolPointer(true), - }, + schemaInfo: &SchemaInfo{ + Name: "optionalConfigOther", + MaxItemsOne: boolPointer(true), }, expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("optionalConfigOther"): resource.PropertyValue{ V: resource.PropertyMap{ @@ -559,16 +523,12 @@ func TestTerraformOutputsWithSecretsSupported(t *testing.T) { }}), }, { - name: "secret_value", - tfValue: map[string]any{ - "secret_value": "MyPassword", - }, - tfType: map[string]*schema.Schema{ - "secret_value": { - Type: shim.TypeString, - Optional: true, - Sensitive: true, - }, + name: "secret_value", + tfValue: "MyPassword", + tfType: &schema.Schema{ + Type: shim.TypeString, + Optional: true, + Sensitive: true, }, expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("secretValue"): resource.PropertyValue{ V: &resource.Secret{Element: resource.PropertyValue{ @@ -578,26 +538,22 @@ func TestTerraformOutputsWithSecretsSupported(t *testing.T) { }, { name: "nested_secret_value", - tfValue: map[string]any{ - "nested_secret_value": []interface{}{ - map[string]interface{}{ - "secret_value": "MyPassword", - }, + tfValue: []interface{}{ + map[string]interface{}{ + "secret_value": "MyPassword", }, }, - tfType: map[string]*schema.Schema{ - "nested_secret_value": { - Type: shim.TypeList, - MaxItems: 1, - Elem: (&schema.Resource{ - Schema: schemaMap(map[string]*schema.Schema{ - "secret_value": { - Type: shim.TypeString, - Sensitive: true, - }, - }), - }).Shim(), - }, + tfType: &schema.Schema{ + Type: shim.TypeList, + MaxItems: 1, + Elem: (&schema.Resource{ + Schema: schemaMap(map[string]*schema.Schema{ + "secret_value": { + Type: shim.TypeString, + Sensitive: true, + }, + }), + }).Shim(), }, expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("nestedSecretValue"): resource.PropertyValue{ V: resource.PropertyMap{resource.PropertyKey("secretValue"): resource.PropertyValue{ @@ -611,19 +567,36 @@ func TestTerraformOutputsWithSecretsSupported(t *testing.T) { for _, tt := range tests { tt := tt - t.Run("name", func(t *testing.T) { + t.Run(tt.name, func(t *testing.T) { t.Parallel() for _, f := range factories { f := f t.Run(f.SDKVersion(), func(t *testing.T) { t.Parallel() ctx := context.Background() + + var tfType map[string]*schema.Schema + if tt.tfType != nil { + tfType = map[string]*schema.Schema{ + tt.name: tt.tfType, + } + } + + var schemaInfo map[string]*SchemaInfo + if tt.schemaInfo != nil { + schemaInfo = map[string]*SchemaInfo{ + tt.name: tt.schemaInfo, + } + } + result := MakeTerraformOutputs( ctx, f.NewTestProvider(), - tt.tfValue, - f.NewSchemaMap(tt.tfType), - tt.schemaInfo, + map[string]any{ + tt.name: tt.tfValue, + }, + f.NewSchemaMap(tfType), + schemaInfo, nil, /* assets */ false, /* useRawNames */ true, /* supportsSecrets */ From ad03c90d5d5e815a532b951f3901c79cdf681428 Mon Sep 17 00:00:00 2001 From: Ian Wahbe Date: Thu, 11 Apr 2024 19:27:40 +0200 Subject: [PATCH 3/4] Fix types so they validate --- pkg/tfbridge/schema_test.go | 29 +++++++++++++++++++---------- 1 file changed, 19 insertions(+), 10 deletions(-) diff --git a/pkg/tfbridge/schema_test.go b/pkg/tfbridge/schema_test.go index aaf106097..244e3322f 100644 --- a/pkg/tfbridge/schema_test.go +++ b/pkg/tfbridge/schema_test.go @@ -361,7 +361,7 @@ func TestTerraformOutputsWithSecretsSupported(t *testing.T) { { name: "float_property_value", tfValue: 99.6767932, - tfType: &schema.Schema{Type: shim.TypeFloat}, + tfType: &schema.Schema{Type: shim.TypeFloat, Required: true}, expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("floatPropertyValue"): resource.PropertyValue{ V: 99.6767932, }}), @@ -380,7 +380,7 @@ func TestTerraformOutputsWithSecretsSupported(t *testing.T) { { name: "my_string_property_value", tfValue: MyString("ognirts"), - tfType: &schema.Schema{Type: shim.TypeString}, + tfType: &schema.Schema{Type: shim.TypeString, Optional: true}, expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("myStringPropertyValue"): resource.PropertyValue{ V: "ognirts", }}), @@ -420,7 +420,8 @@ func TestTerraformOutputsWithSecretsSupported(t *testing.T) { }, tfType: &schema.Schema{ // Type mapPropertyValue as a map so that keys aren't mangled in the usual way. - Type: shim.TypeMap, + Type: shim.TypeMap, + Optional: true, }, expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("mapPropertyValue"): resource.PropertyValue{ V: resource.PropertyMap{ @@ -449,9 +450,10 @@ func TestTerraformOutputsWithSecretsSupported(t *testing.T) { // Embed a `*schema.Resource` to validate that type directed // walk of the schema successfully walks inside Resources as well // as Schemas. + Optional: true, Elem: (&schema.Resource{ Schema: schemaMap(map[string]*schema.Schema{ - "configuration": {Type: shim.TypeMap}, + "configuration": {Type: shim.TypeMap, Optional: true}, }), }).Shim(), }, @@ -476,10 +478,11 @@ func TestTerraformOutputsWithSecretsSupported(t *testing.T) { tfType: &schema.Schema{ Type: shim.TypeList, MaxItems: 1, + Optional: true, Elem: (&schema.Resource{ Schema: schemaMap(map[string]*schema.Schema{ - "some_value": {Type: shim.TypeBool}, - "some_other_value": {Type: shim.TypeString}, + "some_value": {Type: shim.TypeBool, Optional: true}, + "some_other_value": {Type: shim.TypeString, Optional: true}, }), }).Shim(), }, @@ -501,11 +504,12 @@ func TestTerraformOutputsWithSecretsSupported(t *testing.T) { }, }, tfType: &schema.Schema{ - Type: shim.TypeList, + Type: shim.TypeList, + Required: true, Elem: (&schema.Resource{ Schema: schemaMap(map[string]*schema.Schema{ - "some_value": {Type: shim.TypeBool}, - "some_other_value": {Type: shim.TypeString}, + "some_value": {Type: shim.TypeBool, Optional: true}, + "some_other_value": {Type: shim.TypeString, Optional: true}, }), }).Shim(), }, @@ -546,11 +550,13 @@ func TestTerraformOutputsWithSecretsSupported(t *testing.T) { tfType: &schema.Schema{ Type: shim.TypeList, MaxItems: 1, + Optional: true, Elem: (&schema.Resource{ Schema: schemaMap(map[string]*schema.Schema{ "secret_value": { Type: shim.TypeString, Sensitive: true, + Required: true, }, }), }).Shim(), @@ -582,6 +588,9 @@ func TestTerraformOutputsWithSecretsSupported(t *testing.T) { } } + schemaMap := f.NewSchemaMap(tfType) + require.NoError(t, schemaMap.Validate()) + var schemaInfo map[string]*SchemaInfo if tt.schemaInfo != nil { schemaInfo = map[string]*SchemaInfo{ @@ -595,7 +604,7 @@ func TestTerraformOutputsWithSecretsSupported(t *testing.T) { map[string]any{ tt.name: tt.tfValue, }, - f.NewSchemaMap(tfType), + schemaMap, schemaInfo, nil, /* assets */ false, /* useRawNames */ From 36c17661a3cfd8f5a5a1ba7aabf1233cd5a37326 Mon Sep 17 00:00:00 2001 From: Ian Wahbe Date: Fri, 12 Apr 2024 12:16:31 +0200 Subject: [PATCH 4/4] Fix lint --- .github/workflows/ci.yml | 2 +- .github/workflows/master.yml | 2 +- .github/workflows/weekly-pulumi-update.yml | 2 +- .golangci.yml | 8 ++++---- pkg/tfbridge/schema_test.go | 1 + 5 files changed, 8 insertions(+), 7 deletions(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index de906191a..00d4e4ea4 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -41,7 +41,7 @@ jobs: skip-cache: true skip-pkg-cache: true skip-build-cache: true - version: v1.55 + version: v1.57 - name: Lint run: make lint - name: Test diff --git a/.github/workflows/master.yml b/.github/workflows/master.yml index d2c95ae7f..bfd43b5cd 100644 --- a/.github/workflows/master.yml +++ b/.github/workflows/master.yml @@ -44,7 +44,7 @@ jobs: skip-cache: true skip-pkg-cache: true skip-build-cache: true - version: v1.55 + version: v1.57 - name: Lint run: make lint - name: Test diff --git a/.github/workflows/weekly-pulumi-update.yml b/.github/workflows/weekly-pulumi-update.yml index f794b3326..e171b8e88 100644 --- a/.github/workflows/weekly-pulumi-update.yml +++ b/.github/workflows/weekly-pulumi-update.yml @@ -32,7 +32,7 @@ jobs: skip-cache: true skip-pkg-cache: true skip-build-cache: true - version: v1.55 + version: v1.57 - name: Update Pulumi/Pulumi id: gomod run: >- diff --git a/.golangci.yml b/.golangci.yml index 3ed0a23f9..95305d3d6 100644 --- a/.golangci.yml +++ b/.golangci.yml @@ -1,8 +1,4 @@ run: - skip-dirs: - - pkg/tf2pulumi/internal/addrs - - pkg/tf2pulumi/internal/config - - pkg/tf2pulumi/internal/configs timeout: 10m linters: @@ -25,3 +21,7 @@ issues: exclude: - "unused-parameter: parameter" - "redefines-builtin-id:" + exclude-dirs: + - pkg/tf2pulumi/internal/addrs + - pkg/tf2pulumi/internal/config + - pkg/tf2pulumi/internal/configs diff --git a/pkg/tfbridge/schema_test.go b/pkg/tfbridge/schema_test.go index 244e3322f..0ca185d90 100644 --- a/pkg/tfbridge/schema_test.go +++ b/pkg/tfbridge/schema_test.go @@ -423,6 +423,7 @@ func TestTerraformOutputsWithSecretsSupported(t *testing.T) { Type: shim.TypeMap, Optional: true, }, + //nolint:lll expect: autogold.Expect(resource.PropertyMap{resource.PropertyKey("mapPropertyValue"): resource.PropertyValue{ V: resource.PropertyMap{ resource.PropertyKey("propertyA"): resource.PropertyValue{