github.com/terramate-io/tf@v0.0.0-20230830114523-fce866b4dfcd/command/jsonformat/computed/renderers/set.go (about) 1 // Copyright (c) HashiCorp, Inc. 2 // SPDX-License-Identifier: MPL-2.0 3 4 package renderers 5 6 import ( 7 "bytes" 8 "fmt" 9 10 "github.com/terramate-io/tf/command/jsonformat/computed" 11 "github.com/terramate-io/tf/plans" 12 ) 13 14 var _ computed.DiffRenderer = (*setRenderer)(nil) 15 16 func Set(elements []computed.Diff) computed.DiffRenderer { 17 return &setRenderer{ 18 elements: elements, 19 } 20 } 21 22 func NestedSet(elements []computed.Diff) computed.DiffRenderer { 23 return &setRenderer{ 24 elements: elements, 25 overrideForcesReplacement: true, 26 } 27 } 28 29 type setRenderer struct { 30 NoWarningsRenderer 31 32 elements []computed.Diff 33 34 overrideForcesReplacement bool 35 } 36 37 func (renderer setRenderer) RenderHuman(diff computed.Diff, indent int, opts computed.RenderHumanOpts) string { 38 // Sets are a bit finicky, nested sets don't render the forces replacement 39 // suffix themselves, but push it onto their children. So if we are 40 // overriding the forces replacement setting, we set it to true for children 41 // and false for ourselves. 42 displayForcesReplacementInSelf := diff.Replace && !renderer.overrideForcesReplacement 43 displayForcesReplacementInChildren := diff.Replace && renderer.overrideForcesReplacement 44 45 if len(renderer.elements) == 0 { 46 return fmt.Sprintf("[]%s%s", nullSuffix(diff.Action, opts), forcesReplacement(displayForcesReplacementInSelf, opts)) 47 } 48 49 elementOpts := opts.Clone() 50 elementOpts.OverrideNullSuffix = true 51 elementOpts.OverrideForcesReplacement = displayForcesReplacementInChildren 52 53 unchangedElements := 0 54 55 var buf bytes.Buffer 56 buf.WriteString(fmt.Sprintf("[%s\n", forcesReplacement(displayForcesReplacementInSelf, opts))) 57 for _, element := range renderer.elements { 58 if element.Action == plans.NoOp && !opts.ShowUnchangedChildren { 59 unchangedElements++ 60 continue 61 } 62 63 for _, warning := range element.WarningsHuman(indent+1, opts) { 64 buf.WriteString(fmt.Sprintf("%s%s\n", formatIndent(indent+1), warning)) 65 } 66 buf.WriteString(fmt.Sprintf("%s%s%s,\n", formatIndent(indent+1), writeDiffActionSymbol(element.Action, elementOpts), element.RenderHuman(indent+1, elementOpts))) 67 } 68 69 if unchangedElements > 0 { 70 buf.WriteString(fmt.Sprintf("%s%s%s\n", formatIndent(indent+1), writeDiffActionSymbol(plans.NoOp, opts), unchanged("element", unchangedElements, opts))) 71 } 72 73 buf.WriteString(fmt.Sprintf("%s%s]%s", formatIndent(indent), writeDiffActionSymbol(plans.NoOp, opts), nullSuffix(diff.Action, opts))) 74 return buf.String() 75 }