github.com/hashicorp/terraform-plugin-sdk@v1.17.2/internal/plans/changes_src.go (about) 1 package plans 2 3 import ( 4 "fmt" 5 6 "github.com/hashicorp/terraform-plugin-sdk/internal/addrs" 7 "github.com/hashicorp/terraform-plugin-sdk/internal/states" 8 "github.com/zclconf/go-cty/cty" 9 ) 10 11 // ResourceInstanceChangeSrc is a not-yet-decoded ResourceInstanceChange. 12 // Pass the associated resource type's schema type to method Decode to 13 // obtain a ResourceInstancChange. 14 type ResourceInstanceChangeSrc struct { 15 // Addr is the absolute address of the resource instance that the change 16 // will apply to. 17 Addr addrs.AbsResourceInstance 18 19 // DeposedKey is the identifier for a deposed object associated with the 20 // given instance, or states.NotDeposed if this change applies to the 21 // current object. 22 // 23 // A Replace change for a resource with create_before_destroy set will 24 // create a new DeposedKey temporarily during replacement. In that case, 25 // DeposedKey in the plan is always states.NotDeposed, representing that 26 // the current object is being replaced with the deposed. 27 DeposedKey states.DeposedKey 28 29 // Provider is the address of the provider configuration that was used 30 // to plan this change, and thus the configuration that must also be 31 // used to apply it. 32 ProviderAddr addrs.AbsProviderConfig 33 34 // ChangeSrc is an embedded description of the not-yet-decoded change. 35 ChangeSrc 36 37 // RequiredReplace is a set of paths that caused the change action to be 38 // Replace rather than Update. Always nil if the change action is not 39 // Replace. 40 // 41 // This is retained only for UI-plan-rendering purposes and so it does not 42 // currently survive a round-trip through a saved plan file. 43 RequiredReplace cty.PathSet 44 45 // Private allows a provider to stash any extra data that is opaque to 46 // Terraform that relates to this change. Terraform will save this 47 // byte-for-byte and return it to the provider in the apply call. 48 Private []byte 49 } 50 51 // Decode unmarshals the raw representation of the instance object being 52 // changed. Pass the implied type of the corresponding resource type schema 53 // for correct operation. 54 func (rcs *ResourceInstanceChangeSrc) Decode(ty cty.Type) (*ResourceInstanceChange, error) { 55 change, err := rcs.ChangeSrc.Decode(ty) 56 if err != nil { 57 return nil, err 58 } 59 return &ResourceInstanceChange{ 60 Addr: rcs.Addr, 61 DeposedKey: rcs.DeposedKey, 62 ProviderAddr: rcs.ProviderAddr, 63 Change: *change, 64 RequiredReplace: rcs.RequiredReplace, 65 Private: rcs.Private, 66 }, nil 67 } 68 69 // DeepCopy creates a copy of the receiver where any pointers to nested mutable 70 // values are also copied, thus ensuring that future mutations of the receiver 71 // will not affect the copy. 72 // 73 // Some types used within a resource change are immutable by convention even 74 // though the Go language allows them to be mutated, such as the types from 75 // the addrs package. These are _not_ copied by this method, under the 76 // assumption that callers will behave themselves. 77 func (rcs *ResourceInstanceChangeSrc) DeepCopy() *ResourceInstanceChangeSrc { 78 if rcs == nil { 79 return nil 80 } 81 ret := *rcs 82 83 ret.RequiredReplace = cty.NewPathSet(ret.RequiredReplace.List()...) 84 85 if len(ret.Private) != 0 { 86 private := make([]byte, len(ret.Private)) 87 copy(private, ret.Private) 88 ret.Private = private 89 } 90 91 ret.ChangeSrc.Before = ret.ChangeSrc.Before.Copy() 92 ret.ChangeSrc.After = ret.ChangeSrc.After.Copy() 93 94 return &ret 95 } 96 97 // OutputChangeSrc describes a change to an output value. 98 type OutputChangeSrc struct { 99 // Addr is the absolute address of the output value that the change 100 // will apply to. 101 Addr addrs.AbsOutputValue 102 103 // ChangeSrc is an embedded description of the not-yet-decoded change. 104 // 105 // For output value changes, the type constraint for the DynamicValue 106 // instances is always cty.DynamicPseudoType. 107 ChangeSrc 108 109 // Sensitive, if true, indicates that either the old or new value in the 110 // change is sensitive and so a rendered version of the plan in the UI 111 // should elide the actual values while still indicating the action of the 112 // change. 113 Sensitive bool 114 } 115 116 // Decode unmarshals the raw representation of the output value being 117 // changed. 118 func (ocs *OutputChangeSrc) Decode() (*OutputChange, error) { 119 change, err := ocs.ChangeSrc.Decode(cty.DynamicPseudoType) 120 if err != nil { 121 return nil, err 122 } 123 return &OutputChange{ 124 Addr: ocs.Addr, 125 Change: *change, 126 Sensitive: ocs.Sensitive, 127 }, nil 128 } 129 130 // DeepCopy creates a copy of the receiver where any pointers to nested mutable 131 // values are also copied, thus ensuring that future mutations of the receiver 132 // will not affect the copy. 133 // 134 // Some types used within a resource change are immutable by convention even 135 // though the Go language allows them to be mutated, such as the types from 136 // the addrs package. These are _not_ copied by this method, under the 137 // assumption that callers will behave themselves. 138 func (ocs *OutputChangeSrc) DeepCopy() *OutputChangeSrc { 139 if ocs == nil { 140 return nil 141 } 142 ret := *ocs 143 144 ret.ChangeSrc.Before = ret.ChangeSrc.Before.Copy() 145 ret.ChangeSrc.After = ret.ChangeSrc.After.Copy() 146 147 return &ret 148 } 149 150 // ChangeSrc is a not-yet-decoded Change. 151 type ChangeSrc struct { 152 // Action defines what kind of change is being made. 153 Action Action 154 155 // Before and After correspond to the fields of the same name in Change, 156 // but have not yet been decoded from the serialized value used for 157 // storage. 158 Before, After DynamicValue 159 } 160 161 // Decode unmarshals the raw representations of the before and after values 162 // to produce a Change object. Pass the type constraint that the result must 163 // conform to. 164 // 165 // Where a ChangeSrc is embedded in some other struct, it's generally better 166 // to call the corresponding Decode method of that struct rather than working 167 // directly with its embedded Change. 168 func (cs *ChangeSrc) Decode(ty cty.Type) (*Change, error) { 169 var err error 170 before := cty.NullVal(ty) 171 after := cty.NullVal(ty) 172 173 if len(cs.Before) > 0 { 174 before, err = cs.Before.Decode(ty) 175 if err != nil { 176 return nil, fmt.Errorf("error decoding 'before' value: %s", err) 177 } 178 } 179 if len(cs.After) > 0 { 180 after, err = cs.After.Decode(ty) 181 if err != nil { 182 return nil, fmt.Errorf("error decoding 'after' value: %s", err) 183 } 184 } 185 return &Change{ 186 Action: cs.Action, 187 Before: before, 188 After: after, 189 }, nil 190 }