Atlantis on AWS User Guide
Overview
This image runs Atlantis 0.46 (Apache-2.0), the open source server that automates Terraform and OpenTofu pull request workflows, on Ubuntu 24.04 LTS. Atlantis listens for webhooks from your Git provider and runs plan and apply on your pull requests, posting the plan output back to the pull request as a comment and locking each workspace so two changes cannot touch the same state at once. The single Go binary is run by an unprivileged atlantis system account under a systemd service that starts it on boot and restarts it on failure.
The bundled infrastructure-as-code engine is OpenTofu, not Terraform. OpenTofu 1.12 (Mozilla Public License 2.0) is installed at /usr/local/bin/tofu and Atlantis is configured with ATLANTIS_DEFAULT_TF_DISTRIBUTION=opentofu so it drives OpenTofu. OpenTofu is a fully open source, drop-in replacement for Terraform; Terraform itself moved to the Business Source License in version 1.6, so this image deliberately ships OpenTofu. If you prefer to run your own Terraform, you can install it and repoint the engine.
Atlantis serves its web UI (the locks and jobs dashboard) on the loopback address 127.0.0.1:4141 - the atlantis server process has no bind-address flag, so port 4141 is never opened in the security group. nginx fronts the application on port 80 and enforces HTTP Basic authentication for the dashboard, which is the only intended access path. On the first boot of every deployed instance a one-shot service generates a fresh per-instance web password, writes it into the nginx htpasswd file and to /root/atlantis-credentials.txt (mode 0600, root only), and sets the Atlantis base URL to the instance's public IP. Two instances launched from the same AMI never share a password, and no default password ships in the image.
Atlantis orchestrates nothing until you connect your own version control. The image ships with non-functional placeholder VCS credentials and a deny-all repository allowlist so the server starts and serves its dashboard, but it acts on no repository until you add your own GitHub, GitLab, Bitbucket or Azure DevOps credentials, webhook secret and allowlist (Step 7). Nothing is automated behind your back.
The default security group for this listing opens port 22 (SSH) and port 80 (HTTP) only.
Prerequisites
- An AWS account subscribed to this product in AWS Marketplace.
- An EC2 key pair in your target region for SSH access.
- A security group allowing inbound TCP 22 (SSH) from your IP and TCP 80 (HTTP) from your users (and from your Git provider's webhook egress, if you connect a repository).
- Recommended instance type:
m5.largeor larger.
Connecting to your instance
SSH in as the default login user for your operating system variant, using the key pair you launched with.
| OS variant | Login user | Example |
|---|---|---|
| Ubuntu 24.04 | ubuntu |
ssh -i your-key.pem ubuntu@<instance-public-ip> |
Step 1 - Launch from the AWS Marketplace console
- Open the product page in AWS Marketplace and choose Continue to Subscribe, then Continue to Configuration.
- Select the software version and your AWS Region, then choose Continue to Launch.
- Choose an instance type (
m5.largeor larger), your VPC subnet, the security group described above, and your EC2 key pair. - Launch the instance and wait for it to reach the running state with status checks passed.
Step 2 - Launch from the AWS CLI (alternative)
Replace the AMI id, key name, security group and subnet with your own values:
aws ec2 run-instances \
--image-id ami-xxxxxxxxxxxxxxxxx \
--instance-type m5.large \
--key-name your-key \
--security-group-ids sg-xxxxxxxx \
--subnet-id subnet-xxxxxxxx \
--metadata-options "HttpTokens=required" \
--tag-specifications 'ResourceType=instance,Tags=[{Key=Name,Value=atlantis}]'
Step 3 - Retrieve the per-instance web password
SSH to the instance and read the credentials file written on first boot. It is mode 0600 and owned by root, so read it with sudo:
sudo cat /root/atlantis-credentials.txt
You will see the unique URL and web password generated for this instance:
# Atlantis - generated on first boot by atlantis-firstboot.service
# This password is unique to this instance. Store it somewhere safe.
ATLANTIS_URL=http://203.0.113.10/
ATLANTIS_WEB_USER=admin
ATLANTIS_WEB_PASSWORD=... (unique per instance)
Step 4 - Sign in to the Atlantis dashboard
Browse to http://<instance-public-ip>/ and sign in with user admin and the password from Step 3. The dashboard shows the workspace Locks and running Jobs - both empty until you connect a repository - and the apply-lock controls.

Step 5 - Verify the service and the OpenTofu engine
On the instance, confirm both services are active and check the Atlantis and OpenTofu versions. The unauthenticated liveness endpoint returns {"status":"ok"}:
systemctl is-active atlantis nginx
atlantis version
tofu version | head -1
curl -s http://127.0.0.1/healthz

The liveness endpoint is also reachable in a browser at http://<instance-public-ip>/healthz (no authentication - so load balancers and probes can hit it directly):

The dashboard itself refuses unauthenticated requests and accepts the per-instance password (substitute the password from Step 3):
# Without credentials the dashboard is refused (401)
curl -s -o /dev/null -w 'no-auth: %{http_code}\n' http://127.0.0.1/
# With the per-instance admin password it succeeds (200)
curl -s -o /dev/null -w 'auth: %{http_code}\n' -u admin:YOUR_PASSWORD http://127.0.0.1/
Step 6 - Run the bundled OpenTofu plan round-trip self-test
Every instance ships a small self-test that runs a real OpenTofu plan through the same engine Atlantis drives, proving the plan machinery executes end to end before you connect any repository. Run it as the atlantis service user:
sudo -u atlantis bash /opt/cloudimg/atlantis-selftest/plan-proof.sh
It runs tofu init, tofu plan and tofu show against a tiny bundled configuration and asserts that the known resource is planned for creation and the known value appears in the saved plan, printing PLAN_PROOF_OK. You can inspect the plan yourself by copying /opt/cloudimg/atlantis-selftest/main.tf into a working directory owned by the atlantis user and running tofu init then tofu plan - the plan reports one resource to add:
# terraform_data.cloudimg_plan_probe will be created
+ resource "terraform_data" "cloudimg_plan_probe" {
+ input = "cloudimg-atlantis-plan-proof"
}
Plan: 1 to add, 0 to change, 0 to destroy.

Step 7 - Connect your Git provider and webhook
Atlantis does nothing until you connect it to your own version control. Edit the environment file and replace the placeholder values:
sudo nano /etc/atlantis/atlantis.env
Set your VCS credentials and replace the deny-all allowlist with your own repositories. For GitHub:
ATLANTIS_GH_USER=your-github-user
ATLANTIS_GH_TOKEN=your-personal-access-token
ATLANTIS_GH_WEBHOOK_SECRET=a-long-random-secret
ATLANTIS_REPO_ALLOWLIST=github.com/your-org/*
GitLab, Bitbucket and Azure DevOps are supported with the equivalent ATLANTIS_GITLAB_*, ATLANTIS_BITBUCKET_* and ATLANTIS_AZUREDEVOPS_* variables. Restart Atlantis to apply:
sudo systemctl restart atlantis
Then add a webhook in your repository pointing at your instance:
- Payload URL:
http://<instance-public-ip>/events - Content type:
application/json - Secret: the same value as
ATLANTIS_GH_WEBHOOK_SECRET - Events: Pull requests, Pushes, Issue comments
Open a pull request and comment atlantis plan - Atlantis clones the repository, runs the OpenTofu plan and posts the result back on the pull request.
Step 8 - Enable HTTPS (recommended)
A continuous-delivery server that can run apply against your cloud is a high-value target, so run it over TLS. Terminate HTTPS at an upstream AWS Application Load Balancer or CloudFront, or install a certificate directly on the instance with Let's Encrypt:
sudo apt-get update && sudo apt-get install -y certbot python3-certbot-nginx
sudo certbot --nginx -d your-domain.example.com
Point your webhook at the https:// URL once TLS is in place.
Step 9 - Maintenance
- Configuration:
/etc/atlantis/atlantis.env(server flags, VCS credentials, allowlist). - Service management:
sudo systemctl status atlantisandsudo systemctl status nginx. - Web password: stored in
/root/atlantis-credentials.txt; rotate it by editing the nginx htpasswd withsudo htpasswd /etc/nginx/.htpasswd adminand reloading nginx. - Logs:
sudo journalctl -u atlantis -f. - Data: ephemeral repository clones and plan working directories live under
/var/lib/atlantis; durable infrastructure state lives in your own OpenTofu/Terraform backend, not on this instance.
Support
cloudimg provides 24/7 technical support for this product by email and live chat, with a one-hour average response for critical issues. Our engineers help with deployment, connecting Git providers and webhooks, repository allowlists, workflow customization, OpenTofu, TLS termination and upgrades.
- Email: support@cloudimg.co.uk
- Live chat: available 24/7 at www.cloudimg.co.uk