# l4 diff

> Show how a Terraform or CloudFormation change moves monthly cloud cost, measured against a git ref or a saved snapshot.

Source: https://docs.levelfour.ai/cli/commands/diff


`l4 diff` shows the cost delta between your Terraform and CloudFormation as they are now and a baseline. By default the baseline is the git merge-base (`main` or `master`); you can also point it at a saved snapshot file.

```bash
l4 diff main.tf
l4 diff ./infra/
l4 diff template.yaml --parameters-file params/prod.json
l4 diff --base main ./infra/
l4 diff baseline.json ./infra/
```

> **Warning**
>
> The default baseline comes out of git history, and both GitHub Actions and GitLab CI check out a shallow clone, which leaves no merge-base to compare against. [CI/CD integration](/guides/ci-cd#diffing-a-change) sets the checkout depth each runner needs. Without history, diff against a saved baseline instead.

## Flags

| Flag                       | Description                                                                                                                                                                         |
| -------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `--base <ref>`             | Git ref to diff against (default: auto-detect `main` or `master`)                                                                                                                   |
| `--region <r>`             | AWS region for pricing. Order: `--region`, then `region_override` in `.levelfour/config.yml`, then the template's `samconfig` (for Terraform, its provider block), then `us-east-1` |
| `--gcp-region <r>`         | GCP region (default: auto-detect or `us-central1`)                                                                                                                                  |
| `--azure-region <r>`       | Azure region (default: auto-detect or `eastus`)                                                                                                                                     |
| `--var <key=value>`        | Terraform variable (repeatable)                                                                                                                                                     |
| `--var-file <path>`        | Terraform variable file (repeatable)                                                                                                                                                |
| `--download-modules`       | Download remote modules for accurate estimates (default `true`)                                                                                                                     |
| `--parameter <Key=Value>`  | CloudFormation parameter value, given to every root template that declares `Key` (repeatable). A nested stack gets the parameters its parent passes                                 |
| `--parameters-file <path>` | CloudFormation parameters file for the root templates, in the AWS CLI JSON format or the CodePipeline format                                                                        |
| `--config-env <env>`       | The `samconfig` environment whose parameters and region apply (default `default`)                                                                                                   |
| `--fail-above <amount>`    | Exit code `2` if monthly delta exceeds this threshold                                                                                                                               |
| `--format`                 | `table`, `json`, or `github-comment` (default `table`)                                                                                                                              |

Global flags (`--json`, `--jq`, `--template`, `--quiet`, `--token`, `--api`) apply. See [CLI overview](/cli#global-flags).

Against the merge-base, `l4 diff` uploads your CloudFormation templates as they are at the merge-base and as they are now. [`l4 estimate`](/cli/commands/estimate#cloudformation) covers what the upload holds and where parameter values come from.

## CI gate

Fail the build when a pull request adds more than $100 a month:

```bash
l4 diff --fail-above 100 -q ./infra/
```

Over the threshold `l4 diff` exits `2` (`ExitIssuesFound`), which a job can tell apart from the `1` a generic failure returns. [Exit codes](/cli#exit-codes) has the full set.

## Comparing against a saved baseline

Outside a git repository, or while you stage a multi-step deployment, diff against a snapshot that [`l4 estimate --out-file`](/cli/commands/estimate) wrote earlier. A snapshot holds Terraform resources only, so against one `l4 diff` prices every CloudFormation template as added:

```bash
l4 estimate --out-file baseline.json ./infra/
# ... make changes ...
l4 diff baseline.json ./infra/
```

## Posting to a pull request

`--format github-comment` emits Markdown you can pipe into a comment:

```bash
l4 diff --base main --format github-comment ./infra/ \
  | gh pr comment "$PR_NUMBER" --body-file -
```

## Related

* [`l4 estimate`](/cli/commands/estimate): the absolute monthly cost, and the `--out-file` snapshot this command reads
* [CI/CD integration](/guides/ci-cd): the GitHub Actions and GitLab CI jobs that run `l4 diff` on a pull request
* [Output formats](/cli/output-formats): `--json`, `--jq`, `--template` and `--quiet`
