From c54c18680eb15c4d7a4e6f6d04a542823813e21a Mon Sep 17 00:00:00 2001 From: Alisdair McDiarmid Date: Tue, 30 Mar 2021 15:50:47 -0400 Subject: [PATCH] core: Fix sensitive value/attribute conflict When applying sensitivity marks to resources, we previously would first mark any provider-denoted sensitive attributes, then apply the set of planned-change sensitive value marks. This would cause a panic if a provider marked an iterable value as sensitive, because it is invalid to call `MarkWithPaths` against a marked iterable value. Instead, we now merge the marks from the provider schema and the planned change into a single set, and apply them with one call. The included test panics without this change. --- terraform/evaluate.go | 5 +++-- terraform/evaluate_test.go | 13 ++++++++++++- 2 files changed, 15 insertions(+), 3 deletions(-) diff --git a/terraform/evaluate.go b/terraform/evaluate.go index 6dde197003..0e5da5e005 100644 --- a/terraform/evaluate.go +++ b/terraform/evaluate.go @@ -758,11 +758,12 @@ func (d *evaluationStateData) GetResource(addr addrs.Resource, rng tfdiags.Sourc } // If our provider schema contains sensitive values, mark those as sensitive + afterMarks := change.AfterValMarks if schema.ContainsSensitive() { - val = markProviderSensitiveAttributes(schema, val) + afterMarks = append(afterMarks, getValMarks(schema, val, nil)...) } - instances[key] = val.MarkWithPaths(change.AfterValMarks) + instances[key] = val.MarkWithPaths(afterMarks) continue } diff --git a/terraform/evaluate_test.go b/terraform/evaluate_test.go index 427b2291a7..3061df5f7e 100644 --- a/terraform/evaluate_test.go +++ b/terraform/evaluate_test.go @@ -357,6 +357,9 @@ func TestEvaluatorGetResource_changes(t *testing.T) { "id": cty.StringVal("foo"), "to_mark_val": cty.StringVal("pizza").Mark("sensitive"), "sensitive_value": cty.StringVal("abc"), + "sensitive_collection": cty.MapVal(map[string]cty.Value{ + "boop": cty.StringVal("beep"), + }), }), }, } @@ -382,6 +385,11 @@ func TestEvaluatorGetResource_changes(t *testing.T) { Computed: true, Sensitive: true, }, + "sensitive_collection": { + Type: cty.Map(cty.String), + Computed: true, + Sensitive: true, + }, }, }, }, @@ -408,7 +416,7 @@ func TestEvaluatorGetResource_changes(t *testing.T) { Config: &configs.Config{ Module: &configs.Module{ ManagedResources: map[string]*configs.Resource{ - "test_resource.foo": &configs.Resource{ + "test_resource.foo": { Mode: addrs.ManagedResourceMode, Type: "test_resource", Name: "foo", @@ -434,6 +442,9 @@ func TestEvaluatorGetResource_changes(t *testing.T) { "id": cty.StringVal("foo"), "to_mark_val": cty.StringVal("pizza").Mark("sensitive"), "sensitive_value": cty.StringVal("abc").Mark("sensitive"), + "sensitive_collection": cty.MapVal(map[string]cty.Value{ + "boop": cty.StringVal("beep"), + }).Mark("sensitive"), }) got, diags := scope.Data.GetResource(addr, tfdiags.SourceRange{})