diff --git a/CHANGELOG.md b/CHANGELOG.md index f6b22e0e4d..8fa5364414 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -65,6 +65,7 @@ BUG FIXES: * Type validation for mocks and overrides are now less strict in `tofu test`. ([#2144](https://github.com/opentofu/opentofu/pull/2144)) * Skip imports blocks logic on `tofu destroy` ([#2214](https://github.com/opentofu/opentofu/pull/2214)) * Updated github.com/golang-jwt/jwt/v4 from 4.4.2 to 4.5.1 to make security scanners happy (no vulnerability, see [#2179](https://github.com/opentofu/opentofu/pull/2179)) +* `tofu test` is now setting `null`s for dynamic type when generating mock values. ([#2245](https://github.com/opentofu/opentofu/pull/2245)) INTERNAL CHANGES: diff --git a/internal/configs/hcl2shim/mock_value_composer.go b/internal/configs/hcl2shim/mock_value_composer.go index 7ad6eabcf7..6a8c424556 100644 --- a/internal/configs/hcl2shim/mock_value_composer.go +++ b/internal/configs/hcl2shim/mock_value_composer.go @@ -129,18 +129,7 @@ func (mvc MockValueComposer) composeMockValueForAttributes(schema *configschema. continue } - // If there's no value in defaults, we generate our own. - v, ok := mvc.getMockValueByType(impliedTypes[k]) - if !ok { - diags = diags.Append(tfdiags.WholeContainingBody( - tfdiags.Error, - "Failed to generate mock value", - fmt.Sprintf("Mock value cannot be generated for dynamic type. Please specify the `%v` field explicitly in the configuration.", k), - )) - continue - } - - mockAttrs[k] = v + mockAttrs[k] = mvc.getMockValueByType(impliedTypes[k]) } return mockAttrs, diags @@ -289,16 +278,10 @@ func (mvc MockValueComposer) getMockValueForBlock(targetType cty.Type, configVal } } -// getMockValueByType tries to generate mock cty.Value based on provided cty.Type. -// It will return non-ok response if it encounters dynamic type. -func (mvc MockValueComposer) getMockValueByType(t cty.Type) (cty.Value, bool) { +// getMockValueByType generates mock cty.Value based on provided cty.Type. +func (mvc MockValueComposer) getMockValueByType(t cty.Type) cty.Value { var v cty.Value - // just to be sure for cases when the logic below misses something - if t.HasDynamicTypes() { - return cty.Value{}, false - } - switch { // primitives case t.Equals(cty.Number): @@ -329,24 +312,19 @@ func (mvc MockValueComposer) getMockValueByType(t cty.Type) (cty.Value, bool) { continue } - objV, ok := mvc.getMockValueByType(at) - if !ok { - return cty.Value{}, false - } - - objVals[k] = objV + objVals[k] = mvc.getMockValueByType(at) } v = cty.ObjectVal(objVals) case t.IsTupleType(): v = cty.EmptyTupleVal - // dynamically typed values are not supported + // dynamically typed values default: - return cty.Value{}, false + v = cty.NullVal(cty.DynamicPseudoType) } - return v, true + return v } func (mvc MockValueComposer) getMockString() string { diff --git a/internal/configs/hcl2shim/mock_value_composer_test.go b/internal/configs/hcl2shim/mock_value_composer_test.go index 00db0a66b7..a403dcdcfa 100644 --- a/internal/configs/hcl2shim/mock_value_composer_test.go +++ b/internal/configs/hcl2shim/mock_value_composer_test.go @@ -528,6 +528,19 @@ func TestComposeMockValueBySchema(t *testing.T) { }, wantError: true, }, + "dynamically-typed-values": { + schema: &configschema.Block{ + Attributes: map[string]*configschema.Attribute{ + "dynamic-field": { + Type: cty.DynamicPseudoType, + Optional: true, + }, + }, + }, + wantVal: cty.ObjectVal(map[string]cty.Value{ + "dynamic-field": cty.NullVal(cty.DynamicPseudoType), + }), + }, } for name, test := range tests {