Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
29 changes: 28 additions & 1 deletion cmd/terraform/destroy.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,10 +2,15 @@ package terraform

import (
"github.com/spf13/cobra"
"github.com/spf13/viper"

"github.com/cloudposse/atmos/cmd/internal"
"github.com/cloudposse/atmos/pkg/flags"
)

// destroyParser handles flag parsing for the destroy command.
var destroyParser *flags.StandardParser

// destroyCmd represents the terraform destroy command.
var destroyCmd = &cobra.Command{
Use: "destroy",
Expand All @@ -16,11 +21,33 @@ For complete Terraform/OpenTofu documentation, see:
https://developer.hashicorp.com/terraform/cli/commands/destroy
https://opentofu.org/docs/cli/commands/destroy`,
RunE: func(cmd *cobra.Command, args []string) error {
return terraformRun(terraformCmd, cmd, args)
v := viper.GetViper()

if err := terraformParser.BindFlagsToViper(cmd, v); err != nil {
return err
}
if err := destroyParser.BindFlagsToViper(cmd, v); err != nil {
return err
}

opts := ParseTerraformRunOptions(v)
return terraformRunWithOptions(terraformCmd, cmd, args, opts)
},
}

func init() {
destroyParser = flags.NewStandardParser(
WithBackendExecutionFlags(),
flags.WithBoolFlag("affected", "", false, "Destroy the affected components in reverse dependency order"),
flags.WithBoolFlag("all", "", false, "Destroy all components in all stacks"),
)

destroyParser.RegisterFlags(destroyCmd)

if err := destroyParser.BindToViper(viper.GetViper()); err != nil {
panic(err)
}

// Register completions for destroy command.
RegisterTerraformCompletions(destroyCmd)

Expand Down
15 changes: 15 additions & 0 deletions cmd/terraform/destroy_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
package terraform

import (
"testing"

"github.com/stretchr/testify/assert"
"github.com/stretchr/testify/require"
)

func TestDestroyCmd_MultiComponentFlagsRegistered(t *testing.T) {
require.NotNil(t, destroyParser)
assert.NotNil(t, destroyCmd.Flags().Lookup("all"), "destroy should register --all")
assert.NotNil(t, destroyCmd.Flags().Lookup("affected"), "destroy should register --affected")
assert.NotNil(t, destroyCmd.Flags().Lookup("auto-generate-backend-file"), "destroy should register backend execution flags")
}
92 changes: 91 additions & 1 deletion website/docs/cli/commands/terraform/terraform-destroy.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ import Terminal from '@site/src/components/Terminal'
import DemoVideo from '@site/src/components/Video/DemoVideo'

<Intro>
Use this command to destroy Terraform-managed infrastructure for an Atmos component in a stack. This operation removes all resources managed by the component.
Use this command to destroy Terraform-managed infrastructure for an Atmos component in a stack, or across multiple components using the same multi-component flags as `plan`, `apply`, and `deploy`. Destroys respect dependency order: dependents are destroyed before their dependencies.
</Intro>

<DemoVideo id="terraform-destroy" title="atmos terraform destroy" showCaption={false} />
Expand All @@ -25,6 +25,12 @@ Execute the `terraform destroy` command like this:
atmos terraform destroy <component> -s <stack> [options]
```

For multiple components (for example `--all` scoped to one stack):

```shell
atmos terraform destroy --all -s <stack> [options]
```

This command creates a plan to destroy all resources managed by the given configuration and state, and then applies that plan.

:::info Atmos Enhancements
Expand All @@ -34,6 +40,7 @@ Atmos enhances the destroy command with:
- **Automatic variable file generation and passing**
- Backend configuration
- Component validation and locking support
- **Multi-component destroys** (`--all`, `--affected`, `--components`, `--query`) run in **reverse dependency order** when `settings.depends_on` is set
:::

## Configuration
Expand Down Expand Up @@ -75,6 +82,16 @@ atmos terraform destroy vpc -s dev -auto-approve
atmos terraform destroy vpc -s dev -target=aws_instance.web
```

### Destroy All Components in a Stack

```shell
# Preview order and commands (strongly recommended)
atmos terraform destroy --all -s dev --dry-run

# Destroy every Terraform component in the stack (use with extreme caution)
atmos terraform destroy --all -s dev -auto-approve
```

## Arguments

<dl>
Expand Down Expand Up @@ -109,6 +126,79 @@ atmos terraform destroy vpc -s dev -target=aws_instance.web
atmos terraform destroy vpc -s dev --dry-run
```
</dd>

<dt>`--affected` <em>(optional)</em></dt>
<dd>
Destroy only components affected by changes in the repository (requires git). Components are processed in reverse dependency order.

```shell
atmos terraform destroy --affected -s dev
```
</dd>

<dt>`--all` <em>(optional)</em></dt>
<dd>
Destroy every Terraform component in the stack given by `--stack` / `-s`. Order follows reverse dependency order when components declare `settings.depends_on`.

```shell
atmos terraform destroy --all -s dev --dry-run
```
</dd>
</dl>

## Multi-Component Operations

Execute `terraform destroy` across multiple components using the same filtering model as [`atmos terraform apply`](/cli/commands/terraform/apply). All flags can be combined with `--dry-run` to preview which components would run and in what order.

:::warning
Multi-component destroys are destructive. Always use `--dry-run` first and ensure stack and scope are correct.
:::

### Destroy All Components in a Stack

`--all` uses dependency-ordered execution and **requires** `--stack` / `-s`:

```shell
# Preview destroys for every Terraform component in the stack
atmos terraform destroy --all -s prod --dry-run

# Actually destroy (use with extreme caution)
atmos terraform destroy --all -s prod -auto-approve
```

To run every component in a stack **without** `--all`, `atmos terraform destroy -s <stack>` is still supported, but execution order follows map iteration (not dependency order). Prefer `--all -s <stack>` when components use `settings.depends_on`.

### Destroy Affected Components

Destroy only components affected by git changes. Processing order is reverse dependency order:

```shell
atmos terraform destroy --affected
atmos terraform destroy --affected -s prod
atmos terraform destroy --affected --include-dependents
```

### Destroy Specific Components or by Query

Same as apply: use `--components` or `--query` (see [`atmos terraform apply` multi-component flags](/cli/commands/terraform/apply#multi-component-flags)).

### Multi-Component Flags

<dl>
<dt>`--all`</dt>
<dd>Destroy every Terraform component in the stack specified by `--stack` / `-s`. Uses reverse dependency order from `settings.depends_on`.</dd>

<dt>`--affected`</dt>
<dd>Destroy components affected by git changes in reverse dependency order. Supports flags from [`atmos describe affected`](/cli/commands/describe/affected).</dd>

<dt>`--components`</dt>
<dd>Destroy specific components by name (comma-separated or repeated flag).</dd>

<dt>`--query`</dt>
<dd>Destroy components matching a YQ expression against component configuration.</dd>

<dt>`--include-dependents`</dt>
<dd>With `--affected`, also destroy components that depend on affected components, recursively.</dd>
</dl>

## Native Terraform Flags
Expand Down
Loading