Skip to content

IaC Principles

Every infrastructure change MUST be made through Infrastructure as Code. Direct console, SSH, or manual changes are prohibited and will cause configuration drift.


The Rule

CWIQ.IO infrastructure is managed entirely through code. There is one tool for each domain:

Domain Tool Repository
AWS resources (VPC, EC2, IAM, S3, RDS, Route53) Terraform terraform-plan/
Server configuration, application deployment Ansible ansible-playbooks/
Database schemas and migrations SQLAlchemy Alembic platform/server/
DNS records Terraform terraform-plan/
Tailscale ACLs Terraform Tailscale provider terraform-plan/

No exceptions. If a resource exists in production that is not defined in one of these repositories, it will eventually be overwritten or deleted.


Prohibited Actions

Non-DEV Environment Setup — Strictly Ansible Only

All orchestrator environments other than DEV (Demo, Staging, Production) MUST be configured entirely through Ansible playbooks.

CRITICAL: Non-DEV Environments

Never use SCP, rsync, or SSH to manually configure non-DEV servers. Never clone source repositories on a server to deploy from. All configuration changes use Ansible playbooks only.

Prohibited Correct Alternative
scp config.yml server:/etc/app/ Bundle in Ansible role files/ directory
ssh server "systemctl restart app" Ansible service module in a playbook
Clone repo on server to deploy RPM packages from Nexus, deployed via Ansible
docker run directly on server Ansible role with Docker Compose template

Application Deployment — Never Manually

CRITICAL: Application Deployment

Never install packages, edit config files, or run Docker commands directly on application servers.

Prohibited Correct Alternative
pip install / npm install on server CI/CD builds artifacts; Ansible deploys dependencies
Edit files directly on remote servers via SSH Edit in repo, commit, deploy via CI/CD pipeline
Modify systemd service files on servers Update in ansible-playbooks/{service}/, deploy via Ansible
Modify nginx configs on servers Update in ansible-playbooks/, deploy via Ansible
Run docker commands on application servers Use GitLab CI/CD deploy-* jobs

Ansible Server — Strict Rules

CRITICAL: Ansible Server

Only one directory is allowed for running playbooks on the ansible server.

Prohibited Correct Alternative
git clone outside /data/ansible/cwiq-ansible-playbooks/ Only use the official playbooks directory
Run ansible-playbook from /home/ansible/ Use ansible-helper function (sets up venv + Vault creds)
Checkout a feature branch on the ansible server Merge to main first, then git pull on ansible server

The ansible-helper function: 1. cd /data/ansible/cwiq-ansible-playbooks 2. source .venv/bin/activate 3. Logs into Vault and exports ROLE_ID / SECRET_ID

Infrastructure — Never Touch the Console

CRITICAL: AWS Resources

Never create or modify AWS resources in the console. Use Terraform.

Prohibited Correct Alternative
Create EC2 instance in AWS Console Terraform module in terraform-plan/organization/environments/
Manually edit security groups Update Terraform, apply via CLI
Create DNS records in Route53 Console Terraform DNS modules
Modify Tailscale ACLs in web UI Terraform Tailscale provider

Acceptable SSH Usage

SSH to servers is permitted for the following read-only and operational purposes only:

Acceptable Use Examples
Reading logs journalctl, docker logs, tail
Checking status systemctl status, docker ps
Running Ansible FROM the ansible server ssh ansible@ansible-shared-cwiq-io then ansible-helper
Emergency diagnostics top, df -h, free -m, netstat

Running Ansible from the ansible server uses the single approved pattern:

ssh ansible@ansible-shared-cwiq-io
ansible-helper
# Now in /data/ansible/cwiq-ansible-playbooks with venv activated and Vault authenticated
git pull origin main
ansible-playbook cwiq-orchestrator/playbooks/deploy-service.yml -v