From c6a7d080d9e8b3cf04e32b8af758402185d293eb Mon Sep 17 00:00:00 2001 From: Martin Atkins Date: Mon, 5 Apr 2021 15:22:30 -0700 Subject: [PATCH] core: Generalize the idea of a "plan mode", vs just destroy flag Previously there were only two planning modes: normal mode and destroy mode. In that context it made sense for these to be distinguished only by a boolean flag. We're now getting ready to add our third mode, "refresh only". This establishes the idea that planning can be done in one of a number of mutually-exclusive "modes", which are related to but separate from the various other options that serve as modifiers for the plan operation. This commit only introduces the new plans.Mode type and replaces the existing "destroy" flag with a variable of that type. This doesn't cause any change in effective behavior because Terraform Core still supports only NormalMode and DestroyMode, with NewContext rejecting an attempt to create a RefreshMode context for now. It is in retrospect a little odd that the "destroy" flag was part of ContextOpts rather than just an argument to the Plan method, but refactoring that would be too invasive a change for right now so we'll leave this as a field of the context for now and save revisiting that for another day. --- backend/local/backend_local.go | 8 +- backend/remote/backend_context.go | 8 +- command/test.go | 11 +- plans/mode.go | 31 +++++ plans/mode_string.go | 33 +++++ terraform/context.go | 32 +++-- terraform/context_apply2_test.go | 3 +- terraform/context_apply_test.go | 200 ++++++++++++++--------------- terraform/context_plan2_test.go | 4 +- terraform/context_plan_test.go | 28 ++-- terraform/context_validate_test.go | 3 +- 11 files changed, 230 insertions(+), 131 deletions(-) create mode 100644 plans/mode.go create mode 100644 plans/mode_string.go diff --git a/backend/local/backend_local.go b/backend/local/backend_local.go index 6287d43fa..65a2f3566 100644 --- a/backend/local/backend_local.go +++ b/backend/local/backend_local.go @@ -10,6 +10,7 @@ import ( "github.com/hashicorp/terraform/backend" "github.com/hashicorp/terraform/configs" "github.com/hashicorp/terraform/configs/configload" + "github.com/hashicorp/terraform/plans" "github.com/hashicorp/terraform/plans/planfile" "github.com/hashicorp/terraform/states/statemgr" "github.com/hashicorp/terraform/terraform" @@ -65,7 +66,12 @@ func (b *Local) context(op *backend.Operation) (*terraform.Context, *configload. } // Copy set options from the operation - opts.Destroy = op.Destroy + switch { + case op.Destroy: + opts.PlanMode = plans.DestroyMode + default: + opts.PlanMode = plans.NormalMode + } opts.Targets = op.Targets opts.UIInput = op.UIIn opts.Hooks = op.Hooks diff --git a/backend/remote/backend_context.go b/backend/remote/backend_context.go index 1c75a4ba6..eb9c92bba 100644 --- a/backend/remote/backend_context.go +++ b/backend/remote/backend_context.go @@ -12,6 +12,7 @@ import ( "github.com/hashicorp/hcl/v2/hclsyntax" "github.com/hashicorp/terraform/backend" "github.com/hashicorp/terraform/configs" + "github.com/hashicorp/terraform/plans" "github.com/hashicorp/terraform/states/statemgr" "github.com/hashicorp/terraform/terraform" "github.com/hashicorp/terraform/tfdiags" @@ -61,7 +62,12 @@ func (b *Remote) Context(op *backend.Operation) (*terraform.Context, statemgr.Fu } // Copy set options from the operation - opts.Destroy = op.Destroy + switch { + case op.Destroy: + opts.PlanMode = plans.DestroyMode + default: + opts.PlanMode = plans.NormalMode + } opts.Targets = op.Targets opts.UIInput = op.UIIn diff --git a/command/test.go b/command/test.go index 6d46630d0..9e6d19e04 100644 --- a/command/test.go +++ b/command/test.go @@ -501,6 +501,11 @@ func (c *TestCommand) testSuiteContext(suiteDirs testCommandSuiteDirs, providerF changes = plan.Changes } + planMode := plans.NormalMode + if destroy { + planMode = plans.DestroyMode + } + return terraform.NewContext(&terraform.ContextOpts{ Config: suiteDirs.Config, Providers: providerFactories, @@ -515,9 +520,9 @@ func (c *TestCommand) testSuiteContext(suiteDirs testCommandSuiteDirs, providerF Env: "test_" + suiteDirs.SuiteName, }, - State: state, - Changes: changes, - Destroy: destroy, + State: state, + Changes: changes, + PlanMode: planMode, }) } diff --git a/plans/mode.go b/plans/mode.go new file mode 100644 index 000000000..7e78ea859 --- /dev/null +++ b/plans/mode.go @@ -0,0 +1,31 @@ +package plans + +// Mode represents the various mutually-exclusive modes for creating a plan. +type Mode rune + +//go:generate go run golang.org/x/tools/cmd/stringer -type Mode + +const ( + // NormalMode is the default planning mode, which aims to synchronize the + // prior state with remote objects and plan a set of actions intended to + // make those remote objects better match the current configuration. + NormalMode Mode = 0 + + // DestroyMode is a special planning mode for situations where the goal + // is to destroy all remote objects that are bound to instances in the + // prior state, even if the configuration for those instances is still + // present. + // + // This mode corresponds with the "-destroy" option to "terraform plan", + // and with the plan created by the "terraform destroy" command. + DestroyMode Mode = 'D' + + // RefreshOnlyMode is a special planning mode which only performs the + // synchronization of prior state with remote objects, and skips any + // effort to generate any change actions for resource instances even if + // the configuration has changed relative to the state. + // + // This mode corresponds with the "-refresh-only" option to + // "terraform plan". + RefreshOnlyMode Mode = 'R' +) diff --git a/plans/mode_string.go b/plans/mode_string.go new file mode 100644 index 000000000..f1757e8f0 --- /dev/null +++ b/plans/mode_string.go @@ -0,0 +1,33 @@ +// Code generated by "stringer -type Mode"; DO NOT EDIT. + +package plans + +import "strconv" + +func _() { + // An "invalid array index" compiler error signifies that the constant values have changed. + // Re-run the stringer command to generate them again. + var x [1]struct{} + _ = x[NormalMode-0] + _ = x[DestroyMode-68] + _ = x[RefreshOnlyMode-82] +} + +const ( + _Mode_name_0 = "NormalMode" + _Mode_name_1 = "DestroyMode" + _Mode_name_2 = "RefreshOnlyMode" +) + +func (i Mode) String() string { + switch { + case i == 0: + return _Mode_name_0 + case i == 68: + return _Mode_name_1 + case i == 82: + return _Mode_name_2 + default: + return "Mode(" + strconv.FormatInt(int64(i), 10) + ")" + } +} diff --git a/terraform/context.go b/terraform/context.go index 3809061ab..40688e872 100644 --- a/terraform/context.go +++ b/terraform/context.go @@ -46,7 +46,7 @@ type ContextOpts struct { Targets []addrs.Targetable Variables InputValues Meta *ContextMeta - Destroy bool + PlanMode plans.Mode SkipRefresh bool Hooks []Hook @@ -102,7 +102,7 @@ type Context struct { targets []addrs.Targetable variables InputValues meta *ContextMeta - destroy bool + planMode plans.Mode hooks []Hook components contextComponentFactory @@ -253,6 +253,20 @@ func NewContext(opts *ContextOpts) (*Context, tfdiags.Diagnostics) { } } + switch opts.PlanMode { + case plans.NormalMode, plans.DestroyMode: + // OK + default: + // The CLI layer (and other similar callers) should not try to + // create a context for a mode that Terraform Core doesn't support. + diags = diags.Append(tfdiags.Sourceless( + tfdiags.Error, + "Unsupported plan mode", + fmt.Sprintf("Terraform Core doesn't know how to handle plan mode %s. This is a bug in Terraform.", opts.PlanMode), + )) + return nil, diags + } + log.Printf("[TRACE] terraform.NewContext: complete") // By the time we get here, we should have values defined for all of @@ -270,7 +284,7 @@ func NewContext(opts *ContextOpts) (*Context, tfdiags.Diagnostics) { return &Context{ components: components, schemas: schemas, - destroy: opts.Destroy, + planMode: opts.PlanMode, changes: changes, hooks: hooks, meta: opts.Meta, @@ -461,7 +475,7 @@ func (c *Context) Apply() (*states.State, tfdiags.Diagnostics) { // Determine the operation operation := walkApply - if c.destroy { + if c.planMode == plans.DestroyMode { operation = walkDestroy } @@ -470,7 +484,7 @@ func (c *Context) Apply() (*states.State, tfdiags.Diagnostics) { diags = diags.Append(walker.NonFatalDiagnostics) diags = diags.Append(walkDiags) - if c.destroy && !diags.HasErrors() { + if c.planMode == plans.DestroyMode && !diags.HasErrors() { // If we know we were trying to destroy objects anyway, and we // completed without any errors, then we'll also prune out any // leftover empty resource husks (left after all of the instances @@ -532,11 +546,13 @@ The -target option is not for routine use, and is provided only for exceptional var plan *plans.Plan var planDiags tfdiags.Diagnostics - switch { - case c.destroy: + switch c.planMode { + case plans.NormalMode: + plan, planDiags = c.plan() + case plans.DestroyMode: plan, planDiags = c.destroyPlan() default: - plan, planDiags = c.plan() + panic(fmt.Sprintf("unsupported plan mode %s", c.planMode)) } diags = diags.Append(planDiags) if diags.HasErrors() { diff --git a/terraform/context_apply2_test.go b/terraform/context_apply2_test.go index dd028726c..841d24680 100644 --- a/terraform/context_apply2_test.go +++ b/terraform/context_apply2_test.go @@ -9,6 +9,7 @@ import ( "github.com/hashicorp/terraform/addrs" "github.com/hashicorp/terraform/configs/configschema" + "github.com/hashicorp/terraform/plans" "github.com/hashicorp/terraform/providers" "github.com/hashicorp/terraform/states" "github.com/zclconf/go-cty/cty" @@ -161,7 +162,7 @@ output "data" { ctx = testContext2(t, &ContextOpts{ Config: m, Providers: ps, - Destroy: true, + PlanMode: plans.DestroyMode, }) _, diags = ctx.Plan() diff --git a/terraform/context_apply_test.go b/terraform/context_apply_test.go index f8c4c23c6..d7d0910c7 100644 --- a/terraform/context_apply_test.go +++ b/terraform/context_apply_test.go @@ -400,8 +400,8 @@ func TestContext2Apply_resourceDependsOnModuleDestroy(t *testing.T) { Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, - State: globalState, - Destroy: true, + State: globalState, + PlanMode: plans.DestroyMode, }) if _, diags := ctx.Plan(); diags.HasErrors() { @@ -1157,8 +1157,8 @@ func TestContext2Apply_destroyComputed(t *testing.T) { Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, - State: state, - Destroy: true, + State: state, + PlanMode: plans.DestroyMode, }) if p, diags := ctx.Plan(); diags.HasErrors() { @@ -1226,7 +1226,7 @@ func testContext2Apply_destroyDependsOn(t *testing.T) { addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, State: state, - Destroy: true, + PlanMode: plans.DestroyMode, Parallelism: 1, // To check ordering }) @@ -1322,7 +1322,7 @@ func testContext2Apply_destroyDependsOnStateOnly(t *testing.T, state *states.Sta addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, State: state, - Destroy: true, + PlanMode: plans.DestroyMode, Parallelism: 1, // To check ordering }) @@ -1419,7 +1419,7 @@ func testContext2Apply_destroyDependsOnStateOnlyModule(t *testing.T, state *stat addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, State: state, - Destroy: true, + PlanMode: plans.DestroyMode, Parallelism: 1, // To check ordering }) @@ -1498,9 +1498,9 @@ func TestContext2Apply_destroyData(t *testing.T) { Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("null"): testProviderFuncFixed(p), }, - State: state, - Destroy: true, - Hooks: []Hook{hook}, + State: state, + PlanMode: plans.DestroyMode, + Hooks: []Hook{hook}, }) if p, diags := ctx.Plan(); diags.HasErrors() { @@ -1566,8 +1566,8 @@ func TestContext2Apply_destroySkipsCBD(t *testing.T) { Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, - State: state, - Destroy: true, + State: state, + PlanMode: plans.DestroyMode, }) if p, diags := ctx.Plan(); diags.HasErrors() { @@ -1600,8 +1600,8 @@ func TestContext2Apply_destroyModuleVarProviderConfig(t *testing.T) { Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, - State: state, - Destroy: true, + State: state, + PlanMode: plans.DestroyMode, }) if _, diags := ctx.Plan(); diags.HasErrors() { @@ -1687,7 +1687,7 @@ func getContextForApply_destroyCrossProviders(t *testing.T, m *configs.Config, p Config: m, Providers: providerFactories, State: state, - Destroy: true, + PlanMode: plans.DestroyMode, }) return ctx @@ -2493,8 +2493,8 @@ func TestContext2Apply_moduleDestroyOrder(t *testing.T) { Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, - State: state, - Destroy: true, + State: state, + PlanMode: plans.DestroyMode, }) if _, diags := ctx.Plan(); diags.HasErrors() { @@ -2953,8 +2953,8 @@ func TestContext2Apply_moduleProviderCloseNested(t *testing.T) { Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, - State: state, - Destroy: true, + State: state, + PlanMode: plans.DestroyMode, }) if _, diags := ctx.Plan(); diags.HasErrors() { @@ -3026,7 +3026,7 @@ func TestContext2Apply_moduleVarResourceCount(t *testing.T) { SourceType: ValueFromCaller, }, }, - Destroy: true, + PlanMode: plans.DestroyMode, }) if _, diags := ctx.Plan(); diags.HasErrors() { @@ -3266,9 +3266,9 @@ func TestContext2Apply_multiProviderDestroy(t *testing.T) { p2.ApplyResourceChangeFn = applyFn ctx := testContext2(t, &ContextOpts{ - Destroy: true, - State: state, - Config: m, + PlanMode: plans.DestroyMode, + State: state, + Config: m, Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), addrs.NewDefaultProvider("vault"): testProviderFuncFixed(p2), @@ -3387,9 +3387,9 @@ func TestContext2Apply_multiProviderDestroyChild(t *testing.T) { p2.ApplyResourceChangeFn = applyFn ctx := testContext2(t, &ContextOpts{ - Destroy: true, - State: state, - Config: m, + PlanMode: plans.DestroyMode, + State: state, + Config: m, Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), addrs.NewDefaultProvider("vault"): testProviderFuncFixed(p2), @@ -4766,9 +4766,9 @@ func TestContext2Apply_provisionerDestroy(t *testing.T) { ) ctx := testContext2(t, &ContextOpts{ - Config: m, - State: state, - Destroy: true, + Config: m, + State: state, + PlanMode: plans.DestroyMode, Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, @@ -4817,9 +4817,9 @@ func TestContext2Apply_provisionerDestroyFail(t *testing.T) { ) ctx := testContext2(t, &ContextOpts{ - Config: m, - State: state, - Destroy: true, + Config: m, + State: state, + PlanMode: plans.DestroyMode, Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, @@ -4885,9 +4885,9 @@ func TestContext2Apply_provisionerDestroyFailContinue(t *testing.T) { ) ctx := testContext2(t, &ContextOpts{ - Config: m, - State: state, - Destroy: true, + Config: m, + State: state, + PlanMode: plans.DestroyMode, Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, @@ -4954,9 +4954,9 @@ func TestContext2Apply_provisionerDestroyFailContinueFail(t *testing.T) { ) ctx := testContext2(t, &ContextOpts{ - Config: m, - State: state, - Destroy: true, + Config: m, + State: state, + PlanMode: plans.DestroyMode, Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, @@ -5324,9 +5324,9 @@ func TestContext2Apply_provisionerExplicitSelfRef(t *testing.T) { { ctx := testContext2(t, &ContextOpts{ - Config: m, - Destroy: true, - State: state, + Config: m, + PlanMode: plans.DestroyMode, + State: state, Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, @@ -5559,10 +5559,10 @@ func TestContext2Apply_destroyX(t *testing.T) { // Next, plan and apply a destroy operation h.Active = true ctx = testContext2(t, &ContextOpts{ - Destroy: true, - State: state, - Config: m, - Hooks: []Hook{h}, + PlanMode: plans.DestroyMode, + State: state, + Config: m, + Hooks: []Hook{h}, Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, @@ -5620,10 +5620,10 @@ func TestContext2Apply_destroyOrder(t *testing.T) { // Next, plan and apply a destroy h.Active = true ctx = testContext2(t, &ContextOpts{ - Destroy: true, - State: state, - Config: m, - Hooks: []Hook{h}, + PlanMode: plans.DestroyMode, + State: state, + Config: m, + Hooks: []Hook{h}, Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, @@ -5685,10 +5685,10 @@ func TestContext2Apply_destroyModulePrefix(t *testing.T) { // Next, plan and apply a destroy operation and reset the hook h = new(MockHook) ctx = testContext2(t, &ContextOpts{ - Destroy: true, - State: state, - Config: m, - Hooks: []Hook{h}, + PlanMode: plans.DestroyMode, + State: state, + Config: m, + Hooks: []Hook{h}, Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, @@ -5826,10 +5826,10 @@ func TestContext2Apply_destroyModuleWithAttrsReferencingResource(t *testing.T) { { ctx := testContext2(t, &ContextOpts{ - Destroy: true, - Config: m, - State: state, - Hooks: []Hook{h}, + PlanMode: plans.DestroyMode, + Config: m, + State: state, + Hooks: []Hook{h}, Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, @@ -5902,10 +5902,10 @@ func TestContext2Apply_destroyWithModuleVariableAndCount(t *testing.T) { { ctx := testContext2(t, &ContextOpts{ - Destroy: true, - Config: m, - State: state, - Hooks: []Hook{h}, + PlanMode: plans.DestroyMode, + Config: m, + State: state, + Hooks: []Hook{h}, Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, @@ -5975,9 +5975,9 @@ func TestContext2Apply_destroyTargetWithModuleVariableAndCount(t *testing.T) { { ctx := testContext2(t, &ContextOpts{ - Destroy: true, - Config: m, - State: state, + PlanMode: plans.DestroyMode, + Config: m, + State: state, Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, @@ -6056,10 +6056,10 @@ func TestContext2Apply_destroyWithModuleVariableAndCountNested(t *testing.T) { { ctx := testContext2(t, &ContextOpts{ - Destroy: true, - Config: m, - State: state, - Hooks: []Hook{h}, + PlanMode: plans.DestroyMode, + Config: m, + State: state, + Hooks: []Hook{h}, Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, @@ -6136,9 +6136,9 @@ func TestContext2Apply_destroyOutputs(t *testing.T) { // Next, plan and apply a destroy operation ctx = testContext2(t, &ContextOpts{ - Destroy: true, - State: state, - Config: m, + PlanMode: plans.DestroyMode, + State: state, + Config: m, Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("test"): testProviderFuncFixed(p), }, @@ -6160,9 +6160,9 @@ func TestContext2Apply_destroyOutputs(t *testing.T) { // destroying again should produce no errors ctx = testContext2(t, &ContextOpts{ - Destroy: true, - State: state, - Config: m, + PlanMode: plans.DestroyMode, + State: state, + Config: m, Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("test"): testProviderFuncFixed(p), }, @@ -6239,8 +6239,8 @@ func TestContext2Apply_destroyTaintedProvisioner(t *testing.T) { Provisioners: map[string]provisioners.Factory{ "shell": testProvisionerFuncFixed(pr), }, - State: state, - Destroy: true, + State: state, + PlanMode: plans.DestroyMode, }) if _, diags := ctx.Plan(); diags.HasErrors() { @@ -7178,7 +7178,7 @@ func TestContext2Apply_targetedDestroy(t *testing.T) { addrs.ManagedResourceMode, "aws_instance", "a", ), }, - Destroy: true, + PlanMode: plans.DestroyMode, }) if diags := ctx.Validate(); diags.HasErrors() { @@ -7257,7 +7257,7 @@ func TestContext2Apply_targetedDestroyCountDeps(t *testing.T) { addrs.ManagedResourceMode, "aws_instance", "foo", ), }, - Destroy: true, + PlanMode: plans.DestroyMode, }) if _, diags := ctx.Plan(); diags.HasErrors() { @@ -7325,7 +7325,7 @@ func TestContext2Apply_targetedDestroyModule(t *testing.T) { addrs.ManagedResourceMode, "aws_instance", "foo", ), }, - Destroy: true, + PlanMode: plans.DestroyMode, }) if _, diags := ctx.Plan(); diags.HasErrors() { @@ -7413,7 +7413,7 @@ func TestContext2Apply_targetedDestroyCountIndex(t *testing.T) { addrs.ManagedResourceMode, "aws_instance", "bar", addrs.IntKey(1), ), }, - Destroy: true, + PlanMode: plans.DestroyMode, }) if _, diags := ctx.Plan(); diags.HasErrors() { @@ -8481,9 +8481,9 @@ func TestContext2Apply_destroyNestedModuleWithAttrsReferencingResource(t *testin { ctx := testContext2(t, &ContextOpts{ - Destroy: true, - Config: m, - State: state, + PlanMode: plans.DestroyMode, + Config: m, + State: state, Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("null"): testProviderFuncFixed(p), }, @@ -8803,8 +8803,8 @@ func TestContext2Apply_destroyWithLocals(t *testing.T) { Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, - State: state, - Destroy: true, + State: state, + PlanMode: plans.DestroyMode, }) if _, diags := ctx.Plan(); diags.HasErrors() { @@ -8860,8 +8860,8 @@ func TestContext2Apply_providerWithLocals(t *testing.T) { Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, - State: state, - Destroy: true, + State: state, + PlanMode: plans.DestroyMode, }) if _, diags := ctx.Plan(); diags.HasErrors() { @@ -8903,8 +8903,8 @@ func TestContext2Apply_destroyWithProviders(t *testing.T) { Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, - State: state, - Destroy: true, + State: state, + PlanMode: plans.DestroyMode, }) // test that we can't destroy if the provider is missing @@ -8920,8 +8920,8 @@ func TestContext2Apply_destroyWithProviders(t *testing.T) { Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, - State: state, - Destroy: true, + State: state, + PlanMode: plans.DestroyMode, }) if _, diags := ctx.Plan(); diags.HasErrors() { @@ -9124,7 +9124,7 @@ func TestContext2Apply_plannedDestroyInterpolatedCount(t *testing.T) { Config: m, Providers: providers, State: state, - Destroy: true, + PlanMode: plans.DestroyMode, }) plan, diags := ctx.Plan() @@ -9608,7 +9608,7 @@ func TestContext2Apply_destroyDataCycle(t *testing.T) { Config: m, Providers: Providers, State: state, - Destroy: true, + PlanMode: plans.DestroyMode, }) plan, diags := ctx.Plan() @@ -11079,7 +11079,7 @@ output "c" { Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("test"): testProviderFuncFixed(p), }, - Destroy: true, + PlanMode: plans.DestroyMode, }) _, diags = ctx.Plan() @@ -11147,8 +11147,8 @@ output "myoutput" { Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("test"): testProviderFuncFixed(p), }, - Destroy: true, - State: state, + PlanMode: plans.DestroyMode, + State: state, }) _, diags = ctx.Plan() @@ -11471,8 +11471,8 @@ output "output" { addrs.NewDefaultProvider("null"): testProviderFuncFixed(nullP), }, - State: state, - Destroy: true, + State: state, + PlanMode: plans.DestroyMode, }) if _, diags := ctx.Plan(); diags.HasErrors() { @@ -11569,8 +11569,8 @@ output "outputs" { addrs.NewDefaultProvider("test"): testProviderFuncFixed(p), }, - State: state, - Destroy: true, + State: state, + PlanMode: plans.DestroyMode, }) if _, diags := ctx.Plan(); diags.HasErrors() { diff --git a/terraform/context_plan2_test.go b/terraform/context_plan2_test.go index 73bdb283b..4fb293c91 100644 --- a/terraform/context_plan2_test.go +++ b/terraform/context_plan2_test.go @@ -359,7 +359,7 @@ resource "test_object" "a" { Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("test"): testProviderFuncFixed(p), }, - Destroy: true, + PlanMode: plans.DestroyMode, SkipRefresh: true, }) @@ -478,7 +478,7 @@ provider "test" { Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("test"): testProviderFuncFixed(p), }, - Destroy: true, + PlanMode: plans.DestroyMode, }) _, diags := ctx.Plan() diff --git a/terraform/context_plan_test.go b/terraform/context_plan_test.go index d6bfa0056..beabcc6ee 100644 --- a/terraform/context_plan_test.go +++ b/terraform/context_plan_test.go @@ -1616,8 +1616,8 @@ func TestContext2Plan_preventDestroy_destroyPlan(t *testing.T) { Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, - State: state, - Destroy: true, + State: state, + PlanMode: plans.DestroyMode, }) plan, diags := ctx.Plan() @@ -3193,8 +3193,8 @@ func TestContext2Plan_destroy(t *testing.T) { Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, - State: state, - Destroy: true, + State: state, + PlanMode: plans.DestroyMode, }) plan, diags := ctx.Plan() @@ -3256,8 +3256,8 @@ func TestContext2Plan_moduleDestroy(t *testing.T) { Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, - State: state, - Destroy: true, + State: state, + PlanMode: plans.DestroyMode, }) plan, diags := ctx.Plan() @@ -3319,8 +3319,8 @@ func TestContext2Plan_moduleDestroyCycle(t *testing.T) { Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, - State: state, - Destroy: true, + State: state, + PlanMode: plans.DestroyMode, }) plan, diags := ctx.Plan() @@ -3381,8 +3381,8 @@ func TestContext2Plan_moduleDestroyMultivar(t *testing.T) { Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, - State: state, - Destroy: true, + State: state, + PlanMode: plans.DestroyMode, }) plan, diags := ctx.Plan() @@ -4152,8 +4152,8 @@ func TestContext2Plan_targetedOrphan(t *testing.T) { Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, - State: state, - Destroy: true, + State: state, + PlanMode: plans.DestroyMode, Targets: []addrs.Targetable{ addrs.RootModuleInstance.Resource( addrs.ManagedResourceMode, "aws_instance", "orphan", @@ -4219,8 +4219,8 @@ func TestContext2Plan_targetedModuleOrphan(t *testing.T) { Providers: map[addrs.Provider]providers.Factory{ addrs.NewDefaultProvider("aws"): testProviderFuncFixed(p), }, - State: state, - Destroy: true, + State: state, + PlanMode: plans.DestroyMode, Targets: []addrs.Targetable{ addrs.RootModuleInstance.Child("child", addrs.NoKey).Resource( addrs.ManagedResourceMode, "aws_instance", "orphan", diff --git a/terraform/context_validate_test.go b/terraform/context_validate_test.go index 2c3454b1a..6c8f3000b 100644 --- a/terraform/context_validate_test.go +++ b/terraform/context_validate_test.go @@ -10,6 +10,7 @@ import ( "github.com/hashicorp/terraform/addrs" "github.com/hashicorp/terraform/configs/configschema" + "github.com/hashicorp/terraform/plans" "github.com/hashicorp/terraform/providers" "github.com/hashicorp/terraform/provisioners" "github.com/hashicorp/terraform/states" @@ -1056,7 +1057,7 @@ func TestContext2Validate_targetedDestroy(t *testing.T) { addrs.ManagedResourceMode, "aws_instance", "foo", ), }, - Destroy: true, + PlanMode: plans.DestroyMode, }) diags := ctx.Validate()