remove GraphNodeModuleInstance from Resource types

Remove the requirement for most *Resource types to be a
GraphNodeModuleInstance, ensuring that they never call ctx.Path while
being evaluated. This gets rid of most of the direct need for the Path
method currently implemented by NodeResourceAbstract, leaving the
provider and schema related calls for a subsequent PR.
This commit is contained in:
James Bardin 2020-03-09 15:43:56 -04:00
parent 68b500c5c7
commit fae5f9958d
8 changed files with 43 additions and 46 deletions

View File

@ -453,6 +453,7 @@ func (n *EvalMaybeRestoreDeposedObject) Eval(ctx EvalContext) (interface{}, erro
// list rather than as not set at all.
type EvalWriteResourceState struct {
Addr addrs.Resource
Module addrs.Module
Config *configs.Resource
ProviderAddr addrs.AbsProviderConfig
}
@ -460,7 +461,6 @@ type EvalWriteResourceState struct {
// TODO: test
func (n *EvalWriteResourceState) Eval(ctx EvalContext) (interface{}, error) {
var diags tfdiags.Diagnostics
absAddr := n.Addr.Absolute(ctx.Path())
state := ctx.State()
count, countDiags := evaluateResourceCountExpression(n.Config.Count, ctx)
@ -484,16 +484,16 @@ func (n *EvalWriteResourceState) Eval(ctx EvalContext) (interface{}, error) {
eachMode = states.EachMap
}
// This method takes care of all of the business logic of updating this
// while ensuring that any existing instances are preserved, etc.
state.SetResourceMeta(absAddr, eachMode, n.ProviderAddr)
// We'll record our expansion decision in the shared "expander" object
// so that later operations (i.e. DynamicExpand and expression evaluation)
// can refer to it. Since this node represents the abstract module, we need
// to expand the module here to create all resources.
expander := ctx.InstanceExpander()
for _, module := range expander.ExpandModule(ctx.Path().Module()) {
for _, module := range expander.ExpandModule(n.Module) {
// This method takes care of all of the business logic of updating this
// while ensuring that any existing instances are preserved, etc.
state.SetResourceMeta(n.Addr.Absolute(module), eachMode, n.ProviderAddr)
switch eachMode {
case states.EachList:
expander.SetResourceCount(module, n.Addr, count)

View File

@ -1,6 +1,7 @@
package terraform
import (
"github.com/hashicorp/terraform/addrs"
"github.com/hashicorp/terraform/dag"
"github.com/hashicorp/terraform/plans"
"github.com/hashicorp/terraform/providers"
@ -15,7 +16,6 @@ type NodeRefreshableDataResource struct {
}
var (
_ GraphNodeModuleInstance = (*NodeRefreshableDataResource)(nil)
_ GraphNodeDynamicExpandable = (*NodeRefreshableDataResource)(nil)
_ GraphNodeReferenceable = (*NodeRefreshableDataResource)(nil)
_ GraphNodeReferencer = (*NodeRefreshableDataResource)(nil)
@ -54,18 +54,22 @@ func (n *NodeRefreshableDataResource) DynamicExpand(ctx EvalContext) (*Graph, er
// if we're transitioning whether "count" is set at all.
fixResourceCountSetTransition(ctx, n.ResourceAddr(), count != -1)
var instanceAddrs []addrs.AbsResourceInstance
// Inform our instance expander about our expansion results above,
// and then use it to calculate the instance addresses we'll expand for.
expander := ctx.InstanceExpander()
switch {
case count >= 0:
expander.SetResourceCount(ctx.Path(), n.ResourceAddr().Resource, count)
case forEachMap != nil:
expander.SetResourceForEach(ctx.Path(), n.ResourceAddr().Resource, forEachMap)
default:
expander.SetResourceSingle(ctx.Path(), n.ResourceAddr().Resource)
for _, path := range expander.ExpandModule(n.Module) {
switch {
case count >= 0:
expander.SetResourceCount(path, n.ResourceAddr().Resource, count)
case forEachMap != nil:
expander.SetResourceForEach(path, n.ResourceAddr().Resource, forEachMap)
default:
expander.SetResourceSingle(path, n.ResourceAddr().Resource)
}
instanceAddrs = append(instanceAddrs, expander.ExpandResource(path.Module(), n.ResourceAddr().Resource)...)
}
instanceAddrs := expander.ExpandResource(ctx.Path().Module(), n.ResourceAddr().Resource)
// Our graph transformers require access to the full state, so we'll
// temporarily lock it while we work on this.
@ -135,7 +139,7 @@ func (n *NodeRefreshableDataResource) DynamicExpand(ctx EvalContext) (*Graph, er
Name: "NodeRefreshableDataResource",
}
graph, diags := b.Build(ctx.Path())
graph, diags := b.Build(nil)
return graph, diags.ErrWithWarnings()
}

View File

@ -99,7 +99,8 @@ func NewNodeAbstractResource(addr addrs.AbsResource) *NodeAbstractResource {
// the "count" or "for_each" arguments.
type NodeAbstractResourceInstance struct {
NodeAbstractResource
InstanceKey addrs.InstanceKey
ModuleInstance addrs.ModuleInstance
InstanceKey addrs.InstanceKey
// The fields below will be automatically set using the Attach
// interfaces if you're running those transforms, but also be explicitly
@ -138,7 +139,8 @@ func NewNodeAbstractResourceInstance(addr addrs.AbsResourceInstance) *NodeAbstra
Addr: addr.Resource.Resource,
Module: addr.Module.Module(),
},
InstanceKey: addr.Resource.Key,
ModuleInstance: addr.Module,
InstanceKey: addr.Resource.Key,
}
}
@ -155,6 +157,10 @@ func (n *NodeAbstractResource) Path() addrs.ModuleInstance {
return n.Module.UnkeyedInstanceShim()
}
func (n *NodeAbstractResourceInstance) Path() addrs.ModuleInstance {
return n.ModuleInstance
}
// GraphNodeModulePath
func (n *NodeAbstractResource) ModulePath() addrs.Module {
return n.Module

View File

@ -53,19 +53,16 @@ func (n *NodeApplyableResource) References() []*addrs.Reference {
// GraphNodeEvalable
func (n *NodeApplyableResource) EvalTree() EvalNode {
addr := n.ResourceAddr()
config := n.Config
providerAddr := n.ResolvedProvider
if config == nil {
if n.Config == nil {
// Nothing to do, then.
log.Printf("[TRACE] NodeApplyableResource: no configuration present for %s", addr)
log.Printf("[TRACE] NodeApplyableResource: no configuration present for %s", n.Name())
return &EvalNoop{}
}
return &EvalWriteResourceState{
Addr: addr.Resource,
Config: config,
ProviderAddr: providerAddr,
Addr: n.Addr,
Module: n.Module,
Config: n.Config,
ProviderAddr: n.ResolvedProvider,
}
}

View File

@ -288,6 +288,7 @@ func (n *NodeDestroyResourceInstance) EvalTree() EvalNode {
// all been destroyed.
type NodeDestroyResource struct {
*NodeAbstractResource
Addr addrs.AbsResource
}
var (
@ -342,11 +343,6 @@ func (n *NodeDestroyResource) ResourceAddr() addrs.AbsResource {
return n.NodeAbstractResource.ResourceAddr()
}
// GraphNodeSubpath
func (n *NodeDestroyResource) Path() addrs.ModuleInstance {
return n.NodeAbstractResource.Path()
}
// GraphNodeNoProvider
// FIXME: this should be removed once the node can be separated from the
// Internal NodeAbstractResource behavior.

View File

@ -19,7 +19,6 @@ type NodePlannableResource struct {
}
var (
_ GraphNodeModuleInstance = (*NodePlannableResource)(nil)
_ GraphNodeDestroyerCBD = (*NodePlannableResource)(nil)
_ GraphNodeDynamicExpandable = (*NodePlannableResource)(nil)
_ GraphNodeReferenceable = (*NodePlannableResource)(nil)
@ -30,19 +29,17 @@ var (
// GraphNodeEvalable
func (n *NodePlannableResource) EvalTree() EvalNode {
addr := n.ResourceAddr()
config := n.Config
if config == nil {
if n.Config == nil {
// Nothing to do, then.
log.Printf("[TRACE] NodeApplyableResource: no configuration present for %s", addr)
log.Printf("[TRACE] NodeApplyableResource: no configuration present for %s", n.Name())
return &EvalNoop{}
}
// this ensures we can reference the resource even if the count is 0
return &EvalWriteResourceState{
Addr: addr.Resource,
Config: config,
Addr: n.Addr,
Module: n.Module,
Config: n.Config,
ProviderAddr: n.ResolvedProvider,
}
}

View File

@ -25,7 +25,6 @@ type NodeRefreshableManagedResource struct {
}
var (
_ GraphNodeModuleInstance = (*NodeRefreshableManagedResource)(nil)
_ GraphNodeDynamicExpandable = (*NodeRefreshableManagedResource)(nil)
_ GraphNodeReferenceable = (*NodeRefreshableManagedResource)(nil)
_ GraphNodeReferencer = (*NodeRefreshableManagedResource)(nil)
@ -61,8 +60,7 @@ func (n *NodeRefreshableManagedResource) DynamicExpand(ctx EvalContext) (*Graph,
// Inform our instance expander about our expansion results above,
// and then use it to calculate the instance addresses we'll expand for.
expander := ctx.InstanceExpander()
for _, module := range expander.ExpandModule(ctx.Path().Module()) {
for _, module := range expander.ExpandModule(n.Module) {
switch {
case count >= 0:
expander.SetResourceCount(module, n.ResourceAddr().Resource, count)
@ -72,7 +70,7 @@ func (n *NodeRefreshableManagedResource) DynamicExpand(ctx EvalContext) (*Graph,
expander.SetResourceSingle(module, n.ResourceAddr().Resource)
}
}
instanceAddrs := expander.ExpandResource(ctx.Path().Module(), n.ResourceAddr().Resource)
instanceAddrs := expander.ExpandResource(n.Module, n.ResourceAddr().Resource)
// Our graph transformers require access to the full state, so we'll
// temporarily lock it while we work on this.
@ -131,7 +129,7 @@ func (n *NodeRefreshableManagedResource) DynamicExpand(ctx EvalContext) (*Graph,
Name: "NodeRefreshableManagedResource",
}
graph, diags := b.Build(ctx.Path())
graph, diags := b.Build(nil)
return graph, diags.ErrWithWarnings()
}

View File

@ -15,7 +15,6 @@ type NodeValidatableResource struct {
}
var (
_ GraphNodeModuleInstance = (*NodeValidatableResource)(nil)
_ GraphNodeEvalable = (*NodeValidatableResource)(nil)
_ GraphNodeReferenceable = (*NodeValidatableResource)(nil)
_ GraphNodeReferencer = (*NodeValidatableResource)(nil)