diff --git a/terraform/eval_read_data.go b/terraform/eval_read_data.go index 4630841b7..9235130bd 100644 --- a/terraform/eval_read_data.go +++ b/terraform/eval_read_data.go @@ -58,6 +58,9 @@ type evalReadData struct { // determine if there are any changes that will force this data sources to // be deferred to apply. dependsOn []addrs.ConfigResource + // forceDependsOn indicates that resources may be missing from dependsOn, + // but the parent module may have depends_on configured. + forceDependsOn bool } // readDataSource handles everything needed to call ReadDataSource on the provider. @@ -302,5 +305,5 @@ func (n *evalReadDataRefresh) Eval(ctx EvalContext) (interface{}, error) { // immediately reading from the data source where possible, instead forcing us // to generate a plan. func (n *evalReadDataRefresh) forcePlanRead() bool { - return len(n.Config.DependsOn) > 0 || len(n.dependsOn) > 0 + return len(n.Config.DependsOn) > 0 || len(n.dependsOn) > 0 || n.forceDependsOn } diff --git a/terraform/node_data_refresh.go b/terraform/node_data_refresh.go index 0c191d272..135bcb2a2 100644 --- a/terraform/node_data_refresh.go +++ b/terraform/node_data_refresh.go @@ -122,6 +122,7 @@ func (n *NodeRefreshableDataResource) DynamicExpand(ctx EvalContext) (*Graph, er a.ResolvedProvider = n.ResolvedProvider a.ProviderMetas = n.ProviderMetas a.dependsOn = n.dependsOn + a.forceDependsOn = n.forceDependsOn return &NodeRefreshableDataResourceInstance{ NodeAbstractResourceInstance: a, @@ -229,6 +230,7 @@ func (n *NodeRefreshableDataResourceInstance) EvalTree() EvalNode { OutputChange: &change, State: &state, dependsOn: n.dependsOn, + forceDependsOn: n.forceDependsOn, }, }, diff --git a/terraform/node_resource_abstract.go b/terraform/node_resource_abstract.go index 11eca0d96..aada8d09c 100644 --- a/terraform/node_resource_abstract.go +++ b/terraform/node_resource_abstract.go @@ -61,8 +61,9 @@ type NodeAbstractResource struct { // Set from GraphNodeTargetable Targets []addrs.Targetable - // Set from GraphNodeDependsOn - dependsOn []addrs.ConfigResource + // Set from AttachResourceDependencies + dependsOn []addrs.ConfigResource + forceDependsOn bool // The address of the provider this resource will use ResolvedProvider addrs.AbsProviderConfig @@ -402,8 +403,9 @@ func (n *NodeAbstractResource) SetTargets(targets []addrs.Targetable) { } // graphNodeAttachResourceDependencies -func (n *NodeAbstractResource) AttachResourceDependencies(deps []addrs.ConfigResource) { +func (n *NodeAbstractResource) AttachResourceDependencies(deps []addrs.ConfigResource, force bool) { n.dependsOn = deps + n.forceDependsOn = force } // GraphNodeAttachResourceState diff --git a/terraform/transform_reference.go b/terraform/transform_reference.go index ba5fc2b51..34f214319 100644 --- a/terraform/transform_reference.go +++ b/terraform/transform_reference.go @@ -62,7 +62,15 @@ type graphNodeDependsOn interface { type graphNodeAttachResourceDependencies interface { GraphNodeConfigResource graphNodeDependsOn - AttachResourceDependencies([]addrs.ConfigResource) + + // AttachResourceDependencies stored the discovered dependencies in the + // resource node for evaluation later. + // + // The force parameter indicates that even if there are no dependencies, + // force the data source to act as though there are for refresh purposes. + // This is needed because yet-to-be-created resources won't be in the + // initial refresh graph, but may still be referenced through depends_on. + AttachResourceDependencies(deps []addrs.ConfigResource, force bool) } // GraphNodeReferenceOutside is an interface that can optionally be implemented. @@ -186,7 +194,7 @@ func (t attachDataResourceDependenciesTransformer) Transform(g *Graph) error { } log.Printf("[TRACE] attachDataDependenciesTransformer: %s depends on %s", depender.ResourceAddr(), res) - depender.AttachResourceDependencies(res) + depender.AttachResourceDependencies(res, false) } return nil