remove invalid destroy provisioner tests

Remove all the destroy provisioner tests that are testing what is no
longer allowed.

Add missing state dependencies to remaining tests that require it.
This commit is contained in:
James Bardin 2019-12-03 22:54:30 -05:00
parent 9edb719aaa
commit a4bc91abeb
11 changed files with 79 additions and 767 deletions

View File

@ -290,35 +290,26 @@ func TestContext2Apply_resourceDependsOnModuleStateOnly(t *testing.T) {
p := testProvider("aws")
p.DiffFn = testDiffFn
state := MustShimLegacyState(&State{
Modules: []*ModuleState{
&ModuleState{
Path: rootModulePath,
Resources: map[string]*ResourceState{
"aws_instance.a": &ResourceState{
Type: "aws_instance",
Primary: &InstanceState{
ID: "parent",
},
Dependencies: []string{"module.child"},
Provider: "provider.aws",
},
},
},
&ModuleState{
Path: []string{"root", "child"},
Resources: map[string]*ResourceState{
"aws_instance.child": &ResourceState{
Type: "aws_instance",
Primary: &InstanceState{
ID: "child",
},
Provider: "provider.aws",
},
},
},
state := states.NewState()
root := state.EnsureModule(addrs.RootModuleInstance)
root.SetResourceInstanceCurrent(
mustResourceInstanceAddr("aws_instance.a").Resource,
&states.ResourceInstanceObjectSrc{
Status: states.ObjectReady,
AttrsJSON: []byte(`{"id":"parent"}`),
Dependencies: []addrs.AbsResource{mustResourceAddr("module.child.aws_instance.child")},
},
})
mustProviderConfig("provider.aws"),
)
child := state.EnsureModule(addrs.RootModuleInstance.Child("child", addrs.NoKey))
child.SetResourceInstanceCurrent(
mustResourceInstanceAddr("aws_instance.child").Resource,
&states.ResourceInstanceObjectSrc{
Status: states.ObjectReady,
AttrsJSON: []byte(`{"id":"child"}`),
},
mustProviderConfig("provider.aws"),
)
{
// verify the apply happens in the correct order
@ -1264,30 +1255,26 @@ func testContext2Apply_destroyDependsOn(t *testing.T) {
p := testProvider("aws")
p.ApplyFn = testApplyFn
p.DiffFn = testDiffFn
state := MustShimLegacyState(&State{
Modules: []*ModuleState{
&ModuleState{
Path: rootModulePath,
Resources: map[string]*ResourceState{
"aws_instance.foo": &ResourceState{
Type: "aws_instance",
Primary: &InstanceState{
ID: "foo",
Attributes: map[string]string{},
},
},
"aws_instance.bar": &ResourceState{
Type: "aws_instance",
Primary: &InstanceState{
ID: "bar",
Attributes: map[string]string{},
},
},
},
},
state := states.NewState()
root := state.EnsureModule(addrs.RootModuleInstance)
root.SetResourceInstanceCurrent(
mustResourceInstanceAddr("aws_instance.bar").Resource,
&states.ResourceInstanceObjectSrc{
Status: states.ObjectReady,
AttrsJSON: []byte(`{"id":"bar"}`),
},
})
mustProviderConfig("provider.aws"),
)
root.SetResourceInstanceCurrent(
mustResourceInstanceAddr("aws_instance.foo").Resource,
&states.ResourceInstanceObjectSrc{
Status: states.ObjectReady,
AttrsJSON: []byte(`{"id":"foo"}`),
Dependencies: []addrs.AbsResource{mustResourceAddr("aws_instance.bar")},
},
mustProviderConfig("provider.aws"),
)
// Record the order we see Apply
var actual []string
@ -1329,34 +1316,6 @@ func testContext2Apply_destroyDependsOn(t *testing.T) {
// Test that destroy ordering is correct with dependencies only
// in the state.
func TestContext2Apply_destroyDependsOnStateOnly(t *testing.T) {
legacyState := MustShimLegacyState(&State{
Modules: []*ModuleState{
&ModuleState{
Path: rootModulePath,
Resources: map[string]*ResourceState{
"aws_instance.foo": &ResourceState{
Type: "aws_instance",
Primary: &InstanceState{
ID: "foo",
Attributes: map[string]string{},
},
Provider: "provider.aws",
},
"aws_instance.bar": &ResourceState{
Type: "aws_instance",
Primary: &InstanceState{
ID: "bar",
Attributes: map[string]string{},
},
Dependencies: []string{"aws_instance.foo"},
Provider: "provider.aws",
},
},
},
},
})
newState := states.NewState()
root := newState.EnsureModule(addrs.RootModuleInstance)
root.SetResourceInstanceCurrent(
@ -1404,9 +1363,6 @@ func TestContext2Apply_destroyDependsOnStateOnly(t *testing.T) {
// It is possible for this to be racy, so we loop a number of times
// just to check.
for i := 0; i < 10; i++ {
t.Run("legacy", func(t *testing.T) {
testContext2Apply_destroyDependsOnStateOnly(t, legacyState)
})
t.Run("new", func(t *testing.T) {
testContext2Apply_destroyDependsOnStateOnly(t, newState)
})
@ -1458,34 +1414,6 @@ func testContext2Apply_destroyDependsOnStateOnly(t *testing.T, state *states.Sta
// Test that destroy ordering is correct with dependencies only
// in the state within a module (GH-11749)
func TestContext2Apply_destroyDependsOnStateOnlyModule(t *testing.T) {
legacyState := MustShimLegacyState(&State{
Modules: []*ModuleState{
&ModuleState{
Path: []string{"root", "child"},
Resources: map[string]*ResourceState{
"aws_instance.foo": &ResourceState{
Type: "aws_instance",
Primary: &InstanceState{
ID: "foo",
Attributes: map[string]string{},
},
Provider: "provider.aws",
},
"aws_instance.bar": &ResourceState{
Type: "aws_instance",
Primary: &InstanceState{
ID: "bar",
Attributes: map[string]string{},
},
Dependencies: []string{"aws_instance.foo"},
Provider: "provider.aws",
},
},
},
},
})
newState := states.NewState()
child := newState.EnsureModule(addrs.RootModuleInstance.Child("child", addrs.NoKey))
child.SetResourceInstanceCurrent(
@ -1533,9 +1461,6 @@ func TestContext2Apply_destroyDependsOnStateOnlyModule(t *testing.T) {
// It is possible for this to be racy, so we loop a number of times
// just to check.
for i := 0; i < 10; i++ {
t.Run("legacy", func(t *testing.T) {
testContext2Apply_destroyDependsOnStateOnlyModule(t, legacyState)
})
t.Run("new", func(t *testing.T) {
testContext2Apply_destroyDependsOnStateOnlyModule(t, newState)
})
@ -2118,72 +2043,6 @@ aws_instance.foo:
`)
}
// for_each values cannot be used in the provisioner during destroy.
// There may be a way to handle this, but for now make sure we print an error
// rather than crashing with an invalid config.
func TestContext2Apply_provisionerDestroyForEach(t *testing.T) {
m := testModule(t, "apply-provisioner-each")
p := testProvider("aws")
pr := testProvisioner()
p.DiffFn = testDiffFn
p.ApplyFn = testApplyFn
s := &states.State{
Modules: map[string]*states.Module{
"": &states.Module{
Resources: map[string]*states.Resource{
"aws_instance.bar": &states.Resource{
Addr: addrs.Resource{Mode: 77, Type: "aws_instance", Name: "bar"},
EachMode: states.EachMap,
Instances: map[addrs.InstanceKey]*states.ResourceInstance{
addrs.StringKey("a"): &states.ResourceInstance{
Current: &states.ResourceInstanceObjectSrc{
AttrsJSON: []byte(`{"foo":"bar","id":"foo"}`),
},
},
addrs.StringKey("b"): &states.ResourceInstance{
Current: &states.ResourceInstanceObjectSrc{
AttrsJSON: []byte(`{"foo":"bar","id":"foo"}`),
},
},
},
ProviderConfig: addrs.AbsProviderConfig{
Module: addrs.ModuleInstance(nil),
Provider: addrs.NewLegacyProvider("aws"),
},
},
},
},
},
}
ctx := testContext2(t, &ContextOpts{
Config: m,
ProviderResolver: providers.ResolverFixed(
map[addrs.Provider]providers.Factory{
addrs.NewLegacyProvider("aws"): testProviderFuncFixed(p),
},
),
Provisioners: map[string]ProvisionerFactory{
"shell": testProvisionerFuncFixed(pr),
},
State: s,
Destroy: true,
})
if _, diags := ctx.Plan(); diags.HasErrors() {
t.Fatalf("plan errors: %s", diags.Err())
}
_, diags := ctx.Apply()
if diags == nil {
t.Fatal("should error")
}
if !strings.Contains(diags.Err().Error(), "each.value cannot be used in this context") {
t.Fatal("unexpected error:", diags.Err())
}
}
func TestContext2Apply_cancelProvisioner(t *testing.T) {
m := testModule(t, "apply-cancel-provisioner")
p := testProvider("aws")
@ -2831,30 +2690,26 @@ func TestContext2Apply_moduleDestroyOrder(t *testing.T) {
},
}
state := MustShimLegacyState(&State{
Modules: []*ModuleState{
&ModuleState{
Path: rootModulePath,
Resources: map[string]*ResourceState{
"aws_instance.b": resourceState("aws_instance", "b"),
},
},
&ModuleState{
Path: []string{"root", "child"},
Resources: map[string]*ResourceState{
"aws_instance.a": resourceState("aws_instance", "a"),
},
Outputs: map[string]*OutputState{
"a_output": &OutputState{
Type: "string",
Sensitive: false,
Value: "a",
},
},
},
state := states.NewState()
child := state.EnsureModule(addrs.RootModuleInstance.Child("child", addrs.NoKey))
child.SetResourceInstanceCurrent(
mustResourceInstanceAddr("aws_instance.a").Resource,
&states.ResourceInstanceObjectSrc{
Status: states.ObjectReady,
AttrsJSON: []byte(`{"id":"a"}`),
},
})
mustProviderConfig("provider.aws"),
)
root := state.EnsureModule(addrs.RootModuleInstance)
root.SetResourceInstanceCurrent(
mustResourceInstanceAddr("aws_instance.b").Resource,
&states.ResourceInstanceObjectSrc{
Status: states.ObjectReady,
AttrsJSON: []byte(`{"id":"b"}`),
Dependencies: []addrs.AbsResource{mustResourceAddr("module.child.aws_instance.a")},
},
mustProviderConfig("provider.aws"),
)
ctx := testContext2(t, &ContextOpts{
Config: m,
@ -5763,196 +5618,6 @@ aws_instance.foo:
}
}
func TestContext2Apply_provisionerDestroyModule(t *testing.T) {
m := testModule(t, "apply-provisioner-destroy-module")
p := testProvider("aws")
pr := testProvisioner()
p.ApplyFn = testApplyFn
p.DiffFn = testDiffFn
pr.ApplyFn = func(rs *InstanceState, c *ResourceConfig) error {
val, ok := c.Config["command"]
if !ok || val != "value" {
t.Fatalf("bad value for foo: %v %#v", val, c)
}
return nil
}
state := MustShimLegacyState(&State{
Modules: []*ModuleState{
&ModuleState{
Path: []string{"root", "child"},
Resources: map[string]*ResourceState{
"aws_instance.foo": &ResourceState{
Type: "aws_instance",
Primary: &InstanceState{
ID: "bar",
},
},
},
},
},
})
ctx := testContext2(t, &ContextOpts{
Config: m,
State: state,
Destroy: true,
ProviderResolver: providers.ResolverFixed(
map[addrs.Provider]providers.Factory{
addrs.NewLegacyProvider("aws"): testProviderFuncFixed(p),
},
),
Provisioners: map[string]ProvisionerFactory{
"shell": testProvisionerFuncFixed(pr),
},
})
if _, diags := ctx.Plan(); diags.HasErrors() {
t.Fatalf("plan errors: %s", diags.Err())
}
state, diags := ctx.Apply()
if diags.HasErrors() {
t.Fatalf("diags: %s", diags.Err())
}
checkStateString(t, state, `<no state>`)
// Verify apply was invoked
if !pr.ProvisionResourceCalled {
t.Fatalf("provisioner not invoked")
}
}
func TestContext2Apply_provisionerDestroyRef(t *testing.T) {
m := testModule(t, "apply-provisioner-destroy-ref")
p := testProvider("aws")
pr := testProvisioner()
p.ApplyFn = testApplyFn
p.DiffFn = testDiffFn
pr.ApplyFn = func(rs *InstanceState, c *ResourceConfig) error {
val, ok := c.Config["command"]
if !ok || val != "hello" {
return fmt.Errorf("bad value for command: %v %#v", val, c)
}
return nil
}
state := MustShimLegacyState(&State{
Modules: []*ModuleState{
&ModuleState{
Path: rootModulePath,
Resources: map[string]*ResourceState{
"aws_instance.bar": &ResourceState{
Type: "aws_instance",
Primary: &InstanceState{
ID: "bar",
Attributes: map[string]string{
"value": "hello",
},
},
Provider: "provider.aws",
},
"aws_instance.foo": &ResourceState{
Type: "aws_instance",
Primary: &InstanceState{
ID: "bar",
},
Provider: "provider.aws",
},
},
},
},
})
ctx := testContext2(t, &ContextOpts{
Config: m,
State: state,
Destroy: true,
ProviderResolver: providers.ResolverFixed(
map[addrs.Provider]providers.Factory{
addrs.NewLegacyProvider("aws"): testProviderFuncFixed(p),
},
),
Provisioners: map[string]ProvisionerFactory{
"shell": testProvisionerFuncFixed(pr),
},
})
if _, diags := ctx.Plan(); diags.HasErrors() {
t.Fatalf("plan errors: %s", diags.Err())
}
state, diags := ctx.Apply()
if diags.HasErrors() {
t.Fatalf("diags: %s", diags.Err())
}
checkStateString(t, state, `<no state>`)
// Verify apply was invoked
if !pr.ProvisionResourceCalled {
t.Fatalf("provisioner not invoked")
}
}
// Test that a destroy provisioner referencing an invalid key errors.
func TestContext2Apply_provisionerDestroyRefInvalid(t *testing.T) {
m := testModule(t, "apply-provisioner-destroy-ref-invalid")
p := testProvider("aws")
pr := testProvisioner()
p.ApplyFn = testApplyFn
p.DiffFn = testDiffFn
pr.ApplyFn = func(rs *InstanceState, c *ResourceConfig) error {
return nil
}
state := MustShimLegacyState(&State{
Modules: []*ModuleState{
&ModuleState{
Path: rootModulePath,
Resources: map[string]*ResourceState{
"aws_instance.bar": &ResourceState{
Type: "aws_instance",
Primary: &InstanceState{
ID: "bar",
},
},
"aws_instance.foo": &ResourceState{
Type: "aws_instance",
Primary: &InstanceState{
ID: "bar",
},
},
},
},
},
})
ctx := testContext2(t, &ContextOpts{
Config: m,
State: state,
Destroy: true,
ProviderResolver: providers.ResolverFixed(
map[addrs.Provider]providers.Factory{
addrs.NewLegacyProvider("aws"): testProviderFuncFixed(p),
},
),
Provisioners: map[string]ProvisionerFactory{
"shell": testProvisionerFuncFixed(pr),
},
})
// this was an apply test, but this is now caught in Validation
if diags := ctx.Validate(); !diags.HasErrors() {
t.Fatal("expected error")
}
}
func TestContext2Apply_provisionerResourceRef(t *testing.T) {
m := testModule(t, "apply-provisioner-resource-ref")
p := testProvider("aws")
@ -8350,259 +8015,32 @@ aws_instance.bar:
`)
}
func TestContext2Apply_destroyProvisionerWithLocals(t *testing.T) {
m := testModule(t, "apply-provisioner-destroy-locals")
p := testProvider("aws")
p.ApplyFn = testApplyFn
p.DiffFn = testDiffFn
pr := testProvisioner()
pr.ApplyFn = func(_ *InstanceState, rc *ResourceConfig) error {
cmd, ok := rc.Get("command")
if !ok || cmd != "local" {
return fmt.Errorf("provisioner got %v:%s", ok, cmd)
}
return nil
}
pr.GetSchemaResponse = provisioners.GetSchemaResponse{
Provisioner: &configschema.Block{
Attributes: map[string]*configschema.Attribute{
"command": {
Type: cty.String,
Required: true,
},
"when": {
Type: cty.String,
Optional: true,
},
},
},
}
ctx := testContext2(t, &ContextOpts{
Config: m,
ProviderResolver: providers.ResolverFixed(
map[addrs.Provider]providers.Factory{
addrs.NewLegacyProvider("aws"): testProviderFuncFixed(p),
},
),
Provisioners: map[string]ProvisionerFactory{
"shell": testProvisionerFuncFixed(pr),
},
State: MustShimLegacyState(&State{
Modules: []*ModuleState{
&ModuleState{
Path: []string{"root"},
Resources: map[string]*ResourceState{
"aws_instance.foo": resourceState("aws_instance", "1234"),
},
},
},
}),
Destroy: true,
// the test works without targeting, but this also tests that the local
// node isn't inadvertently pruned because of the wrong evaluation
// order.
Targets: []addrs.Targetable{
addrs.RootModuleInstance.Resource(
addrs.ManagedResourceMode, "aws_instance", "foo",
),
},
})
if _, diags := ctx.Plan(); diags.HasErrors() {
t.Fatal(diags.Err())
}
if _, diags := ctx.Apply(); diags.HasErrors() {
t.Fatal(diags.Err())
}
if !pr.ProvisionResourceCalled {
t.Fatal("provisioner not called")
}
}
// this also tests a local value in the config referencing a resource that
// wasn't in the state during destroy.
func TestContext2Apply_destroyProvisionerWithMultipleLocals(t *testing.T) {
m := testModule(t, "apply-provisioner-destroy-multiple-locals")
p := testProvider("aws")
p.ApplyFn = testApplyFn
p.DiffFn = testDiffFn
pr := testProvisioner()
pr.GetSchemaResponse = provisioners.GetSchemaResponse{
Provisioner: &configschema.Block{
Attributes: map[string]*configschema.Attribute{
"id": {
Type: cty.String,
Required: true,
},
"command": {
Type: cty.String,
Required: true,
},
"when": {
Type: cty.String,
Optional: true,
},
},
},
}
pr.ApplyFn = func(is *InstanceState, rc *ResourceConfig) error {
cmd, ok := rc.Get("command")
if !ok {
return errors.New("no command in provisioner")
}
id, ok := rc.Get("id")
if !ok {
return errors.New("no id in provisioner")
}
switch id {
case "1234":
if cmd != "local" {
return fmt.Errorf("provisioner %q got:%q", is.ID, cmd)
}
case "3456":
if cmd != "1234" {
return fmt.Errorf("provisioner %q got:%q", is.ID, cmd)
}
default:
t.Fatal("unknown instance")
}
return nil
}
ctx := testContext2(t, &ContextOpts{
Config: m,
ProviderResolver: providers.ResolverFixed(
map[addrs.Provider]providers.Factory{
addrs.NewLegacyProvider("aws"): testProviderFuncFixed(p),
},
),
Provisioners: map[string]ProvisionerFactory{
"shell": testProvisionerFuncFixed(pr),
},
State: MustShimLegacyState(&State{
Modules: []*ModuleState{
&ModuleState{
Path: []string{"root"},
Resources: map[string]*ResourceState{
"aws_instance.foo": resourceState("aws_instance", "1234"),
"aws_instance.bar": resourceState("aws_instance", "3456"),
},
},
},
}),
Destroy: true,
})
if _, diags := ctx.Plan(); diags.HasErrors() {
t.Fatal(diags.Err())
}
if _, diags := ctx.Apply(); diags.HasErrors() {
t.Fatal(diags.Err())
}
if !pr.ProvisionResourceCalled {
t.Fatal("provisioner not called")
}
}
func TestContext2Apply_destroyProvisionerWithOutput(t *testing.T) {
m := testModule(t, "apply-provisioner-destroy-outputs")
p := testProvider("aws")
p.ApplyFn = testApplyFn
p.DiffFn = testDiffFn
pr := testProvisioner()
pr.ApplyFn = func(is *InstanceState, rc *ResourceConfig) error {
cmd, ok := rc.Get("command")
if !ok || cmd != "3" {
return fmt.Errorf("provisioner for %s got %v:%s", is.ID, ok, cmd)
}
return nil
}
ctx := testContext2(t, &ContextOpts{
Config: m,
ProviderResolver: providers.ResolverFixed(
map[addrs.Provider]providers.Factory{
addrs.NewLegacyProvider("aws"): testProviderFuncFixed(p),
},
),
Provisioners: map[string]ProvisionerFactory{
"shell": testProvisionerFuncFixed(pr),
},
State: MustShimLegacyState(&State{
Modules: []*ModuleState{
&ModuleState{
Path: []string{"root"},
Resources: map[string]*ResourceState{
"aws_instance.foo": resourceState("aws_instance", "1"),
},
Outputs: map[string]*OutputState{
"value": {
Type: "string",
Value: "3",
},
},
},
&ModuleState{
Path: []string{"root", "mod"},
Resources: map[string]*ResourceState{
"aws_instance.baz": resourceState("aws_instance", "3"),
},
// state needs to be properly initialized
Outputs: map[string]*OutputState{},
},
&ModuleState{
Path: []string{"root", "mod2"},
Resources: map[string]*ResourceState{
"aws_instance.bar": resourceState("aws_instance", "2"),
},
},
},
}),
Destroy: true,
// targeting the source of the value used by all resources should still
// destroy them all.
Targets: []addrs.Targetable{
addrs.RootModuleInstance.Child("mod", addrs.NoKey).Resource(
addrs.ManagedResourceMode, "aws_instance", "baz",
),
},
})
if _, diags := ctx.Plan(); diags.HasErrors() {
t.Fatal(diags.Err())
}
state, diags := ctx.Apply()
if diags.HasErrors() {
t.Fatal(diags.Err())
}
if !pr.ProvisionResourceCalled {
t.Fatal("provisioner not called")
}
// confirm all outputs were removed too
for _, mod := range state.Modules {
if len(mod.OutputValues) > 0 {
t.Fatalf("output left in module state: %#v\n", mod)
}
}
}
func TestContext2Apply_targetedDestroyCountDeps(t *testing.T) {
m := testModule(t, "apply-destroy-targeted-count")
p := testProvider("aws")
p.ApplyFn = testApplyFn
p.DiffFn = testDiffFn
state := states.NewState()
root := state.EnsureModule(addrs.RootModuleInstance)
root.SetResourceInstanceCurrent(
mustResourceInstanceAddr("aws_instance.foo").Resource,
&states.ResourceInstanceObjectSrc{
Status: states.ObjectReady,
AttrsJSON: []byte(`{"id":"i-bcd345"}`),
},
mustProviderConfig("provider.aws"),
)
root.SetResourceInstanceCurrent(
mustResourceInstanceAddr("aws_instance.bar").Resource,
&states.ResourceInstanceObjectSrc{
Status: states.ObjectReady,
AttrsJSON: []byte(`{"id":"i-abc123"}`),
Dependencies: []addrs.AbsResource{mustResourceAddr("aws_instance.foo")},
},
mustProviderConfig("provider.aws"),
)
ctx := testContext2(t, &ContextOpts{
Config: m,
ProviderResolver: providers.ResolverFixed(
@ -8610,17 +8048,7 @@ func TestContext2Apply_targetedDestroyCountDeps(t *testing.T) {
addrs.NewLegacyProvider("aws"): testProviderFuncFixed(p),
},
),
State: MustShimLegacyState(&State{
Modules: []*ModuleState{
&ModuleState{
Path: rootModulePath,
Resources: map[string]*ResourceState{
"aws_instance.foo": resourceState("aws_instance", "i-bcd345"),
"aws_instance.bar": resourceState("aws_instance", "i-abc123"),
},
},
},
}),
State: state,
Targets: []addrs.Targetable{
addrs.RootModuleInstance.Resource(
addrs.ManagedResourceMode, "aws_instance", "foo",

View File

@ -1,14 +0,0 @@
locals {
value = "local"
}
resource "aws_instance" "foo" {
provisioner "shell" {
command = "${local.value}"
when = "create"
}
provisioner "shell" {
command = "${local.value}"
when = "destroy"
}
}

View File

@ -1,10 +0,0 @@
variable "key" {}
resource "aws_instance" "foo" {
foo = "bar"
provisioner "shell" {
command = "${var.key}"
when = "destroy"
}
}

View File

@ -1,4 +0,0 @@
module "child" {
source = "./child"
key = "value"
}

View File

@ -1,26 +0,0 @@
locals {
value = "local"
foo_id = aws_instance.foo.id
// baz is not in the state during destroy, but this is a valid config that
// should not fail.
baz_id = aws_instance.baz.id
}
resource "aws_instance" "baz" {}
resource "aws_instance" "foo" {
provisioner "shell" {
id = self.id
command = local.value
when = "destroy"
}
}
resource "aws_instance" "bar" {
provisioner "shell" {
id = self.id
command = local.foo_id
when = "destroy"
}
}

View File

@ -1,23 +0,0 @@
module "mod" {
source = "./mod"
}
locals {
value = "${module.mod.value}"
}
resource "aws_instance" "foo" {
provisioner "shell" {
command = "${local.value}"
when = "destroy"
}
}
module "mod2" {
source = "./mod2"
value = "${module.mod.value}"
}
output "value" {
value = "${local.value}"
}

View File

@ -1,5 +0,0 @@
output "value" {
value = "${aws_instance.baz.id}"
}
resource "aws_instance" "baz" {}

View File

@ -1,10 +0,0 @@
variable "value" {
}
resource "aws_instance" "bar" {
provisioner "shell" {
command = "${var.value}"
when = "destroy"
}
}

View File

@ -1,12 +0,0 @@
resource "aws_instance" "bar" {
value = "hello"
}
resource "aws_instance" "foo" {
foo = "bar"
provisioner "shell" {
command = aws_instance.bar.does_not_exist
when = "destroy"
}
}

View File

@ -1,12 +0,0 @@
resource "aws_instance" "bar" {
value = "hello"
}
resource "aws_instance" "foo" {
foo = "bar"
provisioner "shell" {
command = "${aws_instance.bar.value}"
when = "destroy"
}
}

View File

@ -2,6 +2,6 @@ resource "aws_instance" "bar" {
for_each = toset(["a"])
provisioner "shell" {
when = "destroy"
command = "echo ${each.value}"
command = "echo ${each.key}"
}
}