func isResolved(node yaml.Node) bool { if node == nil { return true } switch node.Value().(type) { case Expression: return false case []yaml.Node: for _, n := range node.Value().([]yaml.Node) { if !isResolved(n) { return false } } return true case map[string]yaml.Node: for _, n := range node.Value().(map[string]yaml.Node) { if !isResolved(n) { return false } } return true case string: if yaml.EmbeddedDynaml(node) != nil { return false } return true default: return true } }
func FindUnresolvedNodes(root yaml.Node, context ...string) (nodes []UnresolvedNode) { if root == nil { return nodes } switch val := root.Value().(type) { case map[string]yaml.Node: for key, val := range val { nodes = append( nodes, FindUnresolvedNodes(val, addContext(context, key)...)..., ) } case []yaml.Node: for i, val := range val { context := addContext(context, fmt.Sprintf("[%d]", i)) nodes = append( nodes, FindUnresolvedNodes(val, context...)..., ) } case Expression: var path []string switch val := root.Value().(type) { case AutoExpr: path = val.Path case MergeExpr: path = val.Path } nodes = append(nodes, UnresolvedNode{ Node: root, Context: context, Path: path, }) case string: if yaml.EmbeddedDynaml(root) != nil { nodes = append(nodes, UnresolvedNode{ Node: yaml.IssueNode(root, "unparseable expression"), Context: context, Path: []string{}, }) } } return nodes }
func flowString(root yaml.Node, env Environment) yaml.Node { sub := yaml.EmbeddedDynaml(root) if sub == nil { return root } debug.Debug("dynaml: %v: %s\n", env.Path, *sub) expr, err := dynaml.Parse(*sub, env.Path, env.StubPath) if err != nil { return root } return yaml.SubstituteNode(expr, root) }