use an EvalOpFilter for module variables
Remove the Input flag threaded through the input graph creation process to prevent interpolation failures on module variables. Use an EvalOpFilter instead to inset the correct EvalNode during walkInput. Remove the EvalTryInterpolate type, and use the same ContinueOnErr flag as the output node for consistency and to try and keep the number possible eval node types down.
This commit is contained in:
parent
c4dd31e62b
commit
1ad97f6be8
|
@ -12,11 +12,16 @@ type EvalInterpolate struct {
|
||||||
Config *config.RawConfig
|
Config *config.RawConfig
|
||||||
Resource *Resource
|
Resource *Resource
|
||||||
Output **ResourceConfig
|
Output **ResourceConfig
|
||||||
|
ContinueOnErr bool
|
||||||
}
|
}
|
||||||
|
|
||||||
func (n *EvalInterpolate) Eval(ctx EvalContext) (interface{}, error) {
|
func (n *EvalInterpolate) Eval(ctx EvalContext) (interface{}, error) {
|
||||||
rc, err := ctx.Interpolate(n.Config, n.Resource)
|
rc, err := ctx.Interpolate(n.Config, n.Resource)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
if n.ContinueOnErr {
|
||||||
|
log.Printf("[WARN] Interpolation %q failed: %s", n.Config.Key, err)
|
||||||
|
return nil, EvalEarlyExitError{}
|
||||||
|
}
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -26,28 +31,3 @@ func (n *EvalInterpolate) Eval(ctx EvalContext) (interface{}, error) {
|
||||||
|
|
||||||
return nil, nil
|
return nil, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// EvalTryInterpolate is an EvalNode implementation that takes a raw
|
|
||||||
// configuration and interpolates it, but only logs a warning on an
|
|
||||||
// interpolation error, and stops further Eval steps.
|
|
||||||
// This is used during Input where a value may not be known before Refresh, but
|
|
||||||
// we don't want to block Input.
|
|
||||||
type EvalTryInterpolate struct {
|
|
||||||
Config *config.RawConfig
|
|
||||||
Resource *Resource
|
|
||||||
Output **ResourceConfig
|
|
||||||
}
|
|
||||||
|
|
||||||
func (n *EvalTryInterpolate) Eval(ctx EvalContext) (interface{}, error) {
|
|
||||||
rc, err := ctx.Interpolate(n.Config, n.Resource)
|
|
||||||
if err != nil {
|
|
||||||
log.Printf("[WARN] Interpolation %q failed: %s", n.Config.Key, err)
|
|
||||||
return nil, EvalEarlyExitError{}
|
|
||||||
}
|
|
||||||
|
|
||||||
if n.Output != nil {
|
|
||||||
*n.Output = rc
|
|
||||||
}
|
|
||||||
|
|
||||||
return nil, nil
|
|
||||||
}
|
|
||||||
|
|
|
@ -10,9 +10,6 @@ import (
|
||||||
// and is based on the PlanGraphBuilder. The PlanGraphBuilder passed in will be
|
// and is based on the PlanGraphBuilder. The PlanGraphBuilder passed in will be
|
||||||
// modified and should not be used for any other operations.
|
// modified and should not be used for any other operations.
|
||||||
func InputGraphBuilder(p *PlanGraphBuilder) GraphBuilder {
|
func InputGraphBuilder(p *PlanGraphBuilder) GraphBuilder {
|
||||||
// convert this to an InputPlan
|
|
||||||
p.Input = true
|
|
||||||
|
|
||||||
// We're going to customize the concrete functions
|
// We're going to customize the concrete functions
|
||||||
p.CustomConcrete = true
|
p.CustomConcrete = true
|
||||||
|
|
||||||
|
|
|
@ -40,9 +40,6 @@ type PlanGraphBuilder struct {
|
||||||
// Validate will do structural validation of the graph.
|
// Validate will do structural validation of the graph.
|
||||||
Validate bool
|
Validate bool
|
||||||
|
|
||||||
// Input represents that this builder is for an Input operation.
|
|
||||||
Input bool
|
|
||||||
|
|
||||||
// CustomConcrete can be set to customize the node types created
|
// CustomConcrete can be set to customize the node types created
|
||||||
// for various parts of the plan. This is useful in order to customize
|
// for various parts of the plan. This is useful in order to customize
|
||||||
// the plan behavior.
|
// the plan behavior.
|
||||||
|
@ -115,7 +112,6 @@ func (b *PlanGraphBuilder) Steps() []GraphTransformer {
|
||||||
// Add module variables
|
// Add module variables
|
||||||
&ModuleVariableTransformer{
|
&ModuleVariableTransformer{
|
||||||
Module: b.Module,
|
Module: b.Module,
|
||||||
Input: b.Input,
|
|
||||||
},
|
},
|
||||||
|
|
||||||
// Connect so that the references are ready for targeting. We'll
|
// Connect so that the references are ready for targeting. We'll
|
||||||
|
|
|
@ -15,9 +15,6 @@ type NodeApplyableModuleVariable struct {
|
||||||
Value *config.RawConfig // Value is the value that is set
|
Value *config.RawConfig // Value is the value that is set
|
||||||
|
|
||||||
Module *module.Tree // Antiquated, want to remove
|
Module *module.Tree // Antiquated, want to remove
|
||||||
|
|
||||||
// Input is set if this graph was created for the Input operation.
|
|
||||||
Input bool
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func (n *NodeApplyableModuleVariable) Name() string {
|
func (n *NodeApplyableModuleVariable) Name() string {
|
||||||
|
@ -96,23 +93,24 @@ func (n *NodeApplyableModuleVariable) EvalTree() EvalNode {
|
||||||
var config *ResourceConfig
|
var config *ResourceConfig
|
||||||
variables := make(map[string]interface{})
|
variables := make(map[string]interface{})
|
||||||
|
|
||||||
var interpolate EvalNode
|
|
||||||
|
|
||||||
if n.Input {
|
|
||||||
interpolate = &EvalTryInterpolate{
|
|
||||||
Config: n.Value,
|
|
||||||
Output: &config,
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
interpolate = &EvalInterpolate{
|
|
||||||
Config: n.Value,
|
|
||||||
Output: &config,
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return &EvalSequence{
|
return &EvalSequence{
|
||||||
Nodes: []EvalNode{
|
Nodes: []EvalNode{
|
||||||
interpolate,
|
&EvalOpFilter{
|
||||||
|
Ops: []walkOperation{walkInput},
|
||||||
|
Node: &EvalInterpolate{
|
||||||
|
Config: n.Value,
|
||||||
|
Output: &config,
|
||||||
|
ContinueOnErr: true,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
&EvalOpFilter{
|
||||||
|
Ops: []walkOperation{walkRefresh, walkPlan, walkApply,
|
||||||
|
walkDestroy, walkValidate},
|
||||||
|
Node: &EvalInterpolate{
|
||||||
|
Config: n.Value,
|
||||||
|
Output: &config,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
|
||||||
&EvalVariableBlock{
|
&EvalVariableBlock{
|
||||||
Config: &config,
|
Config: &config,
|
||||||
|
|
|
@ -17,7 +17,6 @@ type ModuleVariableTransformer struct {
|
||||||
Module *module.Tree
|
Module *module.Tree
|
||||||
|
|
||||||
DisablePrune bool // True if pruning unreferenced should be disabled
|
DisablePrune bool // True if pruning unreferenced should be disabled
|
||||||
Input bool // True if this is from an Input operation.
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func (t *ModuleVariableTransformer) Transform(g *Graph) error {
|
func (t *ModuleVariableTransformer) Transform(g *Graph) error {
|
||||||
|
@ -100,7 +99,6 @@ func (t *ModuleVariableTransformer) transformSingle(g *Graph, parent, m *module.
|
||||||
Config: v,
|
Config: v,
|
||||||
Value: value,
|
Value: value,
|
||||||
Module: t.Module,
|
Module: t.Module,
|
||||||
Input: t.Input,
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if !t.DisablePrune {
|
if !t.DisablePrune {
|
||||||
|
|
Loading…
Reference in New Issue