@@ -14,7 +14,7 @@ type ResourceData struct {
1414 schema map [string ]* Schema
1515 state * terraform.ResourceState
1616 diff * terraform.ResourceDiff
17- set map [string ]string
17+ setMap map [string ]string
1818}
1919
2020// Get returns the data for the given key, or nil if the key doesn't exist.
@@ -36,8 +36,8 @@ func (d *ResourceData) Get(key string) interface{} {
3636// If the key is invalid or the value is not a correct type, an error
3737// will be returned.
3838func (d * ResourceData ) Set (key string , value interface {}) error {
39- if d .set == nil {
40- d .set = make (map [string ]string )
39+ if d .setMap == nil {
40+ d .setMap = make (map [string ]string )
4141 }
4242
4343 parts := strings .Split (key , "." )
@@ -145,8 +145,8 @@ func (d *ResourceData) getPrimitive(
145145 }
146146 }
147147
148- if d .set != nil {
149- if v , ok := d .set [k ]; ok {
148+ if d .setMap != nil {
149+ if v , ok := d .setMap [k ]; ok {
150150 result = v
151151 resultSet = true
152152 }
@@ -176,6 +176,70 @@ func (d *ResourceData) getPrimitive(
176176 }
177177}
178178
179+ func (d * ResourceData ) set (
180+ k string ,
181+ parts []string ,
182+ schema * Schema ,
183+ value interface {}) error {
184+ switch schema .Type {
185+ case TypeList :
186+ return d .setList (k , parts , schema , value )
187+ default :
188+ return d .setPrimitive (k , schema , value )
189+ }
190+ }
191+
192+ func (d * ResourceData ) setList (
193+ k string ,
194+ parts []string ,
195+ schema * Schema ,
196+ value interface {}) error {
197+ if len (parts ) > 0 {
198+ // We're setting a specific element
199+ idx := parts [0 ]
200+ parts = parts [1 :]
201+
202+ // Special case if we're accessing the count of the list
203+ if idx == "#" {
204+ return fmt .Errorf ("%s: can't set count of list" , k )
205+ }
206+
207+ key := fmt .Sprintf ("%s.%s" , k , idx )
208+ switch t := schema .Elem .(type ) {
209+ case * Resource :
210+ return d .setObject (key , parts , t .Schema , value )
211+ case * Schema :
212+ return d .set (key , parts , t , value )
213+ }
214+ }
215+
216+ var vs []interface {}
217+ if err := mapstructure .Decode (value , & vs ); err != nil {
218+ return fmt .Errorf ("%s: %s" , k , err )
219+ }
220+
221+ // Set the entire list.
222+ var err error
223+ for i , elem := range vs {
224+ is := strconv .FormatInt (int64 (i ), 10 )
225+ err = d .setList (k , []string {is }, schema , elem )
226+ if err != nil {
227+ break
228+ }
229+ }
230+ if err != nil {
231+ for i , _ := range vs {
232+ is := strconv .FormatInt (int64 (i ), 10 )
233+ d .setList (k , []string {is }, schema , nil )
234+ }
235+
236+ return err
237+ }
238+
239+ d .setMap [k + ".#" ] = strconv .FormatInt (int64 (len (vs )), 10 )
240+ return nil
241+ }
242+
179243func (d * ResourceData ) setObject (
180244 k string ,
181245 parts []string ,
@@ -197,16 +261,41 @@ func (d *ResourceData) setObject(
197261 key = fmt .Sprintf ("%s.%s" , k , key )
198262 }
199263
200- return d .setPrimitive (key , s , value )
264+ return d .set (key , parts , s , value )
265+ }
266+
267+ // Set the entire object. First decode into a proper structure
268+ var v map [string ]interface {}
269+ if err := mapstructure .Decode (value , & v ); err != nil {
270+ return fmt .Errorf ("%s: %s" , k , err )
201271 }
202272
203- panic ("can't set full object yet" )
273+ // Set each element in turn
274+ var err error
275+ for k1 , v1 := range v {
276+ err = d .setObject (k , []string {k1 }, schema , v1 )
277+ if err != nil {
278+ break
279+ }
280+ }
281+ if err != nil {
282+ for k1 , _ := range v {
283+ d .setObject (k , []string {k1 }, schema , nil )
284+ }
285+ }
286+
287+ return err
204288}
205289
206290func (d * ResourceData ) setPrimitive (
207291 k string ,
208292 schema * Schema ,
209293 v interface {}) error {
294+ if v == nil {
295+ delete (d .setMap , k )
296+ return nil
297+ }
298+
210299 var set string
211300 switch schema .Type {
212301 case TypeString :
@@ -224,6 +313,6 @@ func (d *ResourceData) setPrimitive(
224313 return fmt .Errorf ("Unknown type: %s" , schema .Type )
225314 }
226315
227- d .set [k ] = set
316+ d .setMap [k ] = set
228317 return nil
229318}
0 commit comments