github.com/Yunsang-Jeong/terraforge@v0.0.0-20231003081416-fe4fad2c57e3/internal/configs/generate.go (about) 1 package configs 2 3 import ( 4 "errors" 5 6 "github.com/hashicorp/hcl/v2" 7 "github.com/hashicorp/hcl/v2/hclsyntax" 8 "github.com/zclconf/go-cty/cty" 9 ) 10 11 type Generate struct { 12 Labels []string 13 When bool 14 ForEach map[string]cty.Value 15 Config *hclsyntax.Body 16 } 17 18 func decodeGenerateBlock(block *hclsyntax.Block, ctx *hcl.EvalContext) (*Generate, error) { 19 g := &Generate{ 20 Labels: block.Labels, 21 When: true, 22 } 23 24 if attr, ok := block.Body.Attributes["when"]; ok { 25 value, diags := attr.Expr.Value(ctx) 26 if diags.HasErrors() { 27 g.When = true 28 } else if !value.IsNull() && value.False() { 29 g.When = false 30 } 31 } 32 33 if attr, ok := block.Body.Attributes["for_each"]; ok { 34 forEach, diags := attr.Expr.Value(ctx) 35 if diags.HasErrors() { 36 return nil, errors.Join(diags.Errs()...) 37 } 38 39 g.ForEach = map[string]cty.Value{} 40 41 switch t := forEach.Type(); { 42 case t.IsObjectType(): 43 for key, value := range forEach.AsValueMap() { 44 g.ForEach[key] = value 45 } 46 case t.IsListType() || t.IsSetType(): 47 for _, value := range forEach.AsValueSlice() { 48 g.ForEach[value.AsString()] = value 49 } 50 default: 51 return nil, errors.New("for_each type must be object or set(string)") 52 } 53 } 54 55 for _, blockInBlock := range block.Body.Blocks { 56 if blockInBlock.Type == "config" { 57 g.Config = blockInBlock.Body 58 break 59 } 60 } 61 62 return g, nil 63 }