Skip to main content

Install the Toolchain

You don't have OpenTofu installed — and you don't need to install it by hand. Atmos has a built-in toolchain that installs and pins the exact tools your stacks depend on, so every developer and every CI run uses the same versions.

Experimental

By the end of this step, Atmos will install OpenTofu (and a security scanner) for you, the first time a component needs them — no asdf, tfenv, or aqua required.

The transparent way: declare what you depend on

The toolchain works automatically. You declare the tools your components need, and Atmos installs them on demand and records exact versions in a lockfile. There are two small pieces.

1. Tell Atmos where to get tools. Add a toolchain: section to your atmos.yaml:

toolchain:
# Where installed tool binaries live (relative to base_path).
install_path: .tools
# Resolve installs against the committed lockfile for reproducibility.
use_lock_file: true
registries:
# The Aqua registry provides metadata for 1,000+ tools (opentofu, kubectl, …).
- name: aqua
type: aqua
priority: 100

2. Declare the tools your stacks depend on. In your stack defaults (you'll build these out in Create Stacks), pin versions with dependencies.tools:

# stacks/orgs/acme/_defaults.yaml
dependencies:
tools:
opentofu: 1.10.10
checkov: "3.2.529" # security scanner, used by a hook later

That's it. The next time you run a Terraform command, Atmos resolves these versions from the Aqua registry, installs them under .tools/, and pins the resolved versions in toolchain.lock.yaml. Tell Atmos to use OpenTofu as the Terraform binary in atmos.yaml:

components:
terraform:
command: tofu
Commit the lockfile

Check toolchain.lock.yaml into git. It records the exact resolved version for every platform, so a teammate on a different OS — or a CI runner — installs byte-for-byte the same tools. This is what turns "works on my machine" into "works everywhere."

The manual way: manage tools yourself

You can also drive the toolchain directly — useful for installing everything up front, adding a tool, or checking what's resolved.

# Install every tool declared across your stacks (reads the lockfile).
atmos toolchain install

# Install or pin a specific tool and version.
atmos toolchain add opentofu@1.10.10

# See what's installed and where it resolves.
atmos toolchain list
atmos toolchain which opentofu

Need a tool your components depend on that isn't OpenTofu — kubectl, helm, tflint, jq? Declare it the same way (dependencies.tools or atmos toolchain add), and Atmos installs it from the Aqua registry.

The payoff: the tools your infrastructure needs are declared next to the infrastructure that needs them, version-controlled in the same repo, and resolved identically everywhere — no second tool to install, no drift between laptops and CI. See the toolchain configuration reference for registries, aliases, and verification.

Tools aren't added to your system PATH — on purpose

Atmos installs tools under .tools/ and puts them on the PATH only for the commands it runs (Terraform, hooks, custom commands). It deliberately does not install them globally, so different projects can pin different versions of the same tool without colliding. When you want the pinned tools in your own shell:

  • Run eval "$(atmos toolchain env)" to add the toolchain to the current shell's PATH.
  • Run atmos toolchain exec opentofu version to invoke a single pinned tool without touching PATH.
  • Run atmos toolchain which opentofu (or atmos toolchain path) to print where a tool — or the toolchain's bin directory — resolves.

Next: with tools handled, start the sandbox your components will deploy against → Start the Local Sandbox →