diff --git a/command/013_config_upgrade.go b/command/013_config_upgrade.go index 81494e8f5..06ef7d2d6 100644 --- a/command/013_config_upgrade.go +++ b/command/013_config_upgrade.go @@ -404,7 +404,18 @@ command and dealing with them before running this command again. } else { attributesObject = cty.EmptyObjectVal } - body.SetAttributeValue(localName, attributesObject) + // If this block already has an entry for this local name, we only + // want to replace it if it's semantically different + if existing := body.GetAttribute(localName); existing != nil { + bytes := existing.Expr().BuildTokens(nil).Bytes() + expr, _ := hclsyntax.ParseExpression(bytes, "", hcl.InitialPos) + value, _ := expr.Value(nil) + if !attributesObject.RawEquals(value) { + body.SetAttributeValue(localName, attributesObject) + } + } else { + body.SetAttributeValue(localName, attributesObject) + } // If we don't have a source attribute, manually construct a commented // block explaining what to do diff --git a/command/testdata/013upgrade-preserves-comments/expected/main.tf b/command/testdata/013upgrade-preserves-comments/expected/main.tf index 13bbe0b95..7ddfeb0ff 100644 --- a/command/testdata/013upgrade-preserves-comments/expected/main.tf +++ b/command/testdata/013upgrade-preserves-comments/expected/main.tf @@ -9,8 +9,15 @@ terraform { source = "hashicorp/bar" version = "0.5.0" } + # An explicit requirement + baz = { + # Comment inside the block should stay + source = "foo/baz" + } + # Foo is required foo = { - source = "hashicorp/foo" + source = "hashicorp/foo" + version = "1.0.0" } } } diff --git a/command/testdata/013upgrade-preserves-comments/input/main.tf b/command/testdata/013upgrade-preserves-comments/input/main.tf index c384d2819..7d12b4337 100644 --- a/command/testdata/013upgrade-preserves-comments/input/main.tf +++ b/command/testdata/013upgrade-preserves-comments/input/main.tf @@ -6,5 +6,15 @@ terraform { required_providers { # Pin bar to this version bar = "0.5.0" + # An explicit requirement + baz = { + # Comment inside the block should stay + source = "foo/baz" + } + # Foo is required + foo = { + # This comment sadly won't make it + version = "1.0.0" + } } }