forked from awslabs/goformation
-
Notifications
You must be signed in to change notification settings - Fork 0
/
fnsub.go
66 lines (54 loc) · 1.96 KB
/
fnsub.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
package intrinsics
import (
"regexp"
"strings"
)
// FnSub resolves the 'Fn::Sub' AWS CloudFormation intrinsic function.
// See: http://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/intrinsic-function-reference-sub.html
func FnSub(name string, input interface{}, template interface{}) interface{} {
// Input can either be a string for this type of Fn::Sub call:
// { "Fn::Sub": "some-string-with-a-${variable}" }
// or it will be an array of length two for named replacements
// { "Fn::Sub": [ "some ${replaced}", { "replaced": "value" } ] }
switch val := input.(type) {
case []interface{}:
// Replace each of the variables in element 0 with the items in element 1
if src, ok := val[0].(string); ok {
// The seconds element is a map of variables to replace
if replacements, ok := val[1].(map[string]interface{}); ok {
// Loop through the replacements
for key, replacement := range replacements {
// Check the replacement is a string
if value, ok := replacement.(string); ok {
src = strings.Replace(src, "${"+key+"}", value, -1)
}
}
return src
}
}
case string:
// Look up references for each of the variables
regex := regexp.MustCompile(`\$\{([\.0-9A-Za-z]+)\}`)
variables := regex.FindAllStringSubmatch(val, -1)
for _, variable := range variables {
var resolved interface{}
if strings.Contains(variable[1], ".") {
// If the variable name has a . in it, use Fn::GetAtt to resolve it
resolved = FnGetAtt("Fn::GetAtt", strings.Split(variable[1], "."), template)
} else {
// The variable name doesn't have a . in it, so use Ref
resolved = Ref("Ref", variable[1], template)
}
if resolved != nil {
if replacement, ok := resolved.(string); ok {
val = strings.Replace(val, variable[0], replacement, -1)
}
} else {
// The reference couldn't be resolved, so just strip the variable
val = strings.Replace(val, variable[0], "", -1)
}
}
return val
}
return nil
}