terraform: prepare Plan for shadowing
This commit is contained in:
parent
f9fee4106f
commit
ce4ff06d25
|
@ -487,28 +487,75 @@ func (c *Context) Plan() (*Plan, error) {
|
||||||
c.diffLock.Unlock()
|
c.diffLock.Unlock()
|
||||||
|
|
||||||
// Used throughout below
|
// Used throughout below
|
||||||
|
X_newApply := experiment.Enabled(experiment.X_newDestroy)
|
||||||
X_newDestroy := experiment.Enabled(experiment.X_newDestroy)
|
X_newDestroy := experiment.Enabled(experiment.X_newDestroy)
|
||||||
|
newGraphEnabled := (c.destroy && X_newDestroy) || (!c.destroy && X_newApply)
|
||||||
|
|
||||||
// Build the graph. We have a branch here since for the pure-destroy
|
// Build the original graph. This is before the new graph builders
|
||||||
// plan (c.destroy) we use a much simpler graph builder that simply
|
// coming in 0.8. We do this for shadow graphing.
|
||||||
// walks the state and reverses edges.
|
oldGraph, err := c.Graph(&ContextGraphOpts{Validate: true})
|
||||||
var graph *Graph
|
if err != nil && newGraphEnabled {
|
||||||
var err error
|
// If we had an error graphing but we're using the new graph,
|
||||||
if c.destroy && X_newDestroy {
|
// just set it to nil and let it go. There are some features that
|
||||||
graph, err = (&DestroyPlanGraphBuilder{
|
// may work with the new graph that don't with the old.
|
||||||
Module: c.module,
|
oldGraph = nil
|
||||||
State: c.state,
|
err = nil
|
||||||
Targets: c.targets,
|
|
||||||
}).Build(RootModulePath)
|
|
||||||
} else {
|
|
||||||
graph, err = c.Graph(&ContextGraphOpts{Validate: true})
|
|
||||||
}
|
}
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Build the new graph. We do this no matter wht so we can shadow it.
|
||||||
|
var newGraph *Graph
|
||||||
|
err = nil
|
||||||
|
if c.destroy {
|
||||||
|
newGraph, err = (&DestroyPlanGraphBuilder{
|
||||||
|
Module: c.module,
|
||||||
|
State: c.state,
|
||||||
|
Targets: c.targets,
|
||||||
|
}).Build(RootModulePath)
|
||||||
|
} else {
|
||||||
|
// TODO: new plan graph when its ready
|
||||||
|
newGraph = nil
|
||||||
|
}
|
||||||
|
if err != nil && !newGraphEnabled {
|
||||||
|
// If we had an error graphing but we're not using this graph, just
|
||||||
|
// set it to nil and record it as a shadow error.
|
||||||
|
c.shadowErr = multierror.Append(c.shadowErr, fmt.Errorf(
|
||||||
|
"Error building new graph: %s", err))
|
||||||
|
|
||||||
|
newGraph = nil
|
||||||
|
err = nil
|
||||||
|
}
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
|
||||||
|
// Determine what is the real and what is the shadow. The logic here
|
||||||
|
// is straightforward though the if statements are not:
|
||||||
|
//
|
||||||
|
// * If the new graph, shadow with experiment in both because the
|
||||||
|
// experiment has less nodes so the original can't shadow.
|
||||||
|
// * If not the new graph, shadow with the experiment
|
||||||
|
//
|
||||||
|
real := oldGraph
|
||||||
|
shadow := newGraph
|
||||||
|
if newGraphEnabled {
|
||||||
|
log.Printf("[WARN] terraform: real graph is experiment, shadow is experiment")
|
||||||
|
real = shadow
|
||||||
|
} else {
|
||||||
|
log.Printf("[WARN] terraform: real graph is original, shadow is experiment")
|
||||||
|
}
|
||||||
|
|
||||||
|
// Special case here: if we're using destroy don't shadow it because
|
||||||
|
// the new destroy graph behaves a bit differently on purpose by not
|
||||||
|
// setting the module destroy flag.
|
||||||
|
if c.destroy && !newGraphEnabled {
|
||||||
|
shadow = nil
|
||||||
|
}
|
||||||
|
|
||||||
// Do the walk
|
// Do the walk
|
||||||
walker, err := c.walk(graph, graph, operation)
|
walker, err := c.walk(real, shadow, operation)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue