Skip to content
application · iac · devops

Automation without agents,Ansible.

Agentless IT automation over SSH and Python — Ansible ships small programs called modules to your hosts, does the work, and cleans up after itself. This guide walks through installing a control node, writing YAML playbooks, the module ecosystem across clouds and systems, AWX for team-scale automation, and a command cheatsheet.

Infrastructure as code

From provisioning servers to configuring networks and deploying applications, Ansible turns manual, error-prone processes into consistent, repeatable automation — no daemons on managed nodes, just SSH and Python.

  • Playbooks — declarative, idempotent YAML plays.
  • Modules — cloud, network, system, and database tasks.
  • AWX — web UI, REST API, and scheduling on top.
SSHTransport
YAMLPlaybook format
PythonRuntime
AWXWeb UI

Start here

Information

With Ansible, you can automate complex IT operations with clarity and control. It simplifies system management, application deployment, and workflow orchestration through powerful, modular building blocks. Powered by open source, Python, and SSH, Ansible connects seamlessly to your devices—no agents required. It sends lightweight programs called modules to perform tasks precisely where they are needed, then removes them once finished. From provisioning servers to configuring networks and deploying applications, Ansible turns manual, error-prone processes into consistent, repeatable automation.

Jump to install, playbooks, modules, AWX, or the cheatsheet.

Get running

Install

To install Ansible, you will need two types of machines:
a control node (where Ansible runs) and one or more managed nodes (where Ansible performs tasks).

  1. Set up your Control and Managed Nodes
    The control node is where you run Ansible commands and playbooks.
    It can be any UNIX-like system with Python 3.9+ installed.
    The managed node is any system that supports Python 2.7+ and communicates via SSH (or PowerShell on Windows).

  2. Install Ansible
    Depending on your operating system, there are multiple installation paths:

    • Ubuntu / Debian: Use apt install ansible from the official repositories.
    • Windows: Enable Windows Subsystem for Linux (WSL) and install Ansible using pip install ansible or pip3 install ansible.
    • Source: Clone the Ansible GitHub repository and build from source to get the latest development version.
  3. Configure Ansible
    Set up your inventory file to list managed nodes and their connection details.
    You can further customize settings in the ansible.cfg file or override them using environment variables or command-line options.

  4. Verify the Installation
    Run a quick test to ensure Ansible is configured properly:

    Terminal window
    ansible all -m ping

    If everything is set up correctly, you will receive a pong response from your managed nodes.

Automation blueprint

Playbook

An Ansible playbook is your automation blueprint written in YAML/JSON. The purpose of the playbook is to tell Ansible what to do, where to do it, and how to do it. With a playbook, you can transform your IT tasks into simple and repeatable steps that run on any number of hosts. Whether you need to install software, configure settings, run commands, or anything else, an Ansible playbook will make it happen in a snap.

Let me dazzle you with an example of a playbook that I borrowed from the Ansible documentation.

- name: Update web servers
hosts: webservers
remote_user: root
tasks:
- name: Ensure apache is at the latest version
ansible.builtin.yum:
name: httpd
state: latest
- name: Write the apache config file
ansible.builtin.template:
src: /srv/httpd.j2
dest: /etc/httpd.conf
- name: Update db servers
hosts: databases
remote_user: root
tasks:
- name: Ensure postgresql is at the latest version
ansible.builtin.yum:
name: postgresql
state: latest
- name: Ensure that postgresql is started
ansible.builtin.service:
name: postgresql
state: started

This playbook has two plays. The first one updates the web servers by installing the latest version of apache and writing a config file. The second one updates the database servers by installing the latest version of postgresql and starting the service. Each play has a name, a list of hosts to target, a remote user to execute the tasks, and a list of tasks to perform. Each task has a name and a module to call with some parameters.

- name: Update Minecraft server
hosts: minecraft
vars:
minecraft_version: latest
minecraft_url: https://s3.amazonaws.com/Minecraft.Download/versions
minecraft_home: /srv/minecraft
tasks:
- name: Get latest Minecraft version
uri:
url: '{{ minecraft_url }}/latest.json'
return_content: yes
register: latest_version
when: minecraft_version == "latest"
- name: Set Minecraft version
set_fact:
minecraft_version: '{{ latest_version.json.id }}'
when: minecraft_version == "latest"
- name: Check if Minecraft server jar exists
stat:
path: '{{ minecraft_home }}/minecraft_server.{{ minecraft_version }}.jar'
register: jar_file
- name: Download Minecraft server jar
get_url:
url: '{{ minecraft_url }}/{{ minecraft_version }}/minecraft_server.{{ minecraft_version }}.jar'
dest: '{{ minecraft_home }}'
when: not jar_file.stat.exists
- name: Restart Minecraft service
systemd:
name: minecraft
state: restarted
when: not jar_file.stat.exists

This playbook is composed of four parts:

  • The name of the playbook, which is Update Minecraft server.
  • The hosts that the playbook will run on, which are the ones in the minecraft group in the inventory file.
  • The variables that the playbook will use, such as minecraft_version, minecraft_url, and minecraft_home.
  • The tasks that the playbook will execute, such as getting the latest Minecraft version, downloading the server jar file, and restarting the Minecraft service.

Each task has a name, a module to use, and some parameters for the module. Some tasks also have a condition (when) that determines when they will run. For example, the task Download Minecraft server jar will only run if the jar file does not exist in the minecraft_home directory. The playbook uses the register keyword to store the output of some tasks in variables, such as latest_version and jar_file. These variables can be used in later tasks or conditions and this playbook could be expanded to include file checks with hashing.

Building blocks

Modules

Cloud modules can be used to interact with different cloud providers, such as AWS, Azure, Google Cloud, etc.

The cloud modules within Ansible are a set of modules that can be used to interact with different cloud providers and services. They allow you to provision, configure and manage cloud resources, such as virtual machines, networks, storage, databases, etc.


The CI/CD modules enable you to run Ansible playbooks directly within automated pipelines. They are useful for testing, provisioning, or deploying infrastructure and applications as part of your workflow.

Module / ActionDescription
ansible/ansible-lint-actionRuns ansible-lint to validate playbooks and roles.
ansible/ansible-playbook-actionExecutes an Ansible playbook inside your GitHub Actions workflow.
ansible/galaxy-actionManages Ansible Galaxy roles and collections in your pipeline.

Here is a full featured layout with Talos OS, core addons, git ops, data plane.

  • Directory.github/
    • Directoryactions/
      • Directorysetup-ansible/ # optional composite action (cache, galaxy install)
    • Directoryworkflows/
      • check.yml # lint (ansible-lint), yamllint, jsonschema, markdown
      • test.yml # molecule with k3d/kind; idempotence checks
      • deploy.yml # on tag or manual dispatch → staged rollout
  • .env.example # sample env for CI (secrets injected via repo/env)
  • .gitignore
  • ansible.cfg
  • requirements.yml # collections: kubernetes.core, community.general, community.kubernetes
  • requirements-roles.yml
  • Directoryinventories/
    • Directoryproduction/
      • hosts.yml
      • Directorygroup_vars/
        • all.yml
        • gitops.yml # argo root app repo/branch/path
        • storage.yml # default sc, longhorn, nfs, cnpg
        • observability.yml # loki, prom, grafana toggles
        • networking.yml # cni options, lb, svc CIDRs (reference-only if Talos-managed)
    • Directorystaging/
      • hosts.yml
      • Directorygroup_vars/
        • all.yml
  • Directorygroup_vars/
    • all.yml # cluster_name, domain, issuer, registry creds (non-secret)
  • Directoryhost_vars/
    • cp-01.yml
    • worker-01.yml
  • Directorycollections/ # (optional, if vendored)
  • Directoryroles/
    • Directorytalos_bootstrap/
      • Directorytasks/
        • main.yml # talosctl gen secrets/apply, kubeconfig export
    • Directorykubernetes_cluster/
      • Directorytasks/
        • main.yml # kube-api reachability, ns, rbac, psp replacement, quotas
    • Directoryhelm_release/
      • Directorytasks/
        • main.yml
    • Directorycert_manager/
      • Directorytasks/
        • main.yml # ClusterIssuer (LE DNS/HTTP), CRDs, health checks
    • Directoryingress_nginx/
      • Directorytasks/
        • main.yml # controller, TCP services, proxy settings
    • Directoryargocd/
      • Directorytasks/
        • main.yml # install, admin secret mgmt (sealed-secrets optional)
    • Directorysealed_secrets/
      • Directorytasks/
        • main.yml
    • Directorylonghorn/
      • Directorytasks/
        • main.yml
    • Directorycnpg/
      • Directorytasks/
        • main.yml # CloudNativePG operator
    • Directoryclickhouse_operator/
      • Directorytasks/
        • main.yml
    • Directoryapps_catalog/
      • Directorytasks/
        • main.yml # app-of-apps: ergo-irc, restreamer, etc.
  • Directoryplaybooks/
    • 00-bootstrap.yml # includes: talos_bootstrap (optional if you do Talos externally)
    • 10-cluster.yml # includes: kubernetes_cluster
    • 20-core.yml # includes: cert_manager, ingress_nginx, sealed_secrets
    • 30-gitops.yml # includes: argocd (+ root apps)
    • 40-storage.yml # includes: longhorn, cnpg, clickhouse_operator
    • 99-apps.yml # includes: apps_catalog (ergo, restreamer, etc.)
  • Directoryvars/
    • issuers.yml
    • registries.yml
    • domains.yml
    • storage.yml
  • Directoryfiles/
    • kubeconfig.sample # for local dev (never commit real kubeconfigs)
    • Directorymanifests/
      • Directoryargocd/
        • root-app.yaml # optional if you don’t bootstrap via Helm
  • Directorytemplates/
    • argocd-values.yaml.j2
    • cert-manager-values.yaml.j2
    • ingress-nginx-values.yaml.j2
  • Directorymolecule/
    • Directoryk3d-default/
      • converge.yml
      • verify.yml
      • molecule.yml
  • Directorydocs/
    • ADR-0001-ci-approach.md
    • ADR-0002-gitops-structure.md
  • README.md
  • Talos handles OS + kubelet; Ansible focuses on cluster add-ons (Helm + Kubernetes modules) and GitOps bootstrap.
  • CI stages are there for a quick check, test and deploy.

Ansible provides a wide range of AWS modules that let you automate tasks across Amazon Web Services, from launching EC2 instances to managing S3 buckets, security groups, and CloudFormation stacks. These modules use the AWS SDK for Python (boto3) under the hood, allowing secure, API-based interaction with your cloud resources. You can use them to playbooks to create, configure, and delete infrastructure components, making it easy to manage everything as code aka IaaC.

ModuleDescription
amazon.aws.ec2_instanceCreate and manage EC2 instances.
amazon.aws.s3_bucketCreate, delete, and configure S3 buckets.
amazon.aws.cloudformationDeploy infrastructure stacks using AWS CloudFormation.
amazon.aws.iam_userManage IAM users and access permissions.
amazon.aws.ec2_security_groupDefine and modify EC2 security groups.

With these modules, you have full control over your Microsoft Azure resources, whether they are VMs, Storage, Network or anything else. For example, you can use the azure_rm_virtualmachine module to create and manage Azure virtual machines.


You can work with any Google Cloud Platform service with these modules, such as Compute Engine, Storage, Network and more. The gcp_compute_instance module is an example of how you can achieve your goals with GCP servers using Ansible.

Official Documentation on GCP Compute Instance module

Creating a compute instance with a specific name, zone, machine type, image and network:

- name: create gcp instance
google.cloud.gcp_compute_instance:
name: test_object
zone: us-central1-a
machine_type: n1-standard-1
disks:
- auto_delete: true
boot: true
source: '{{ disk }}'
network_interfaces:
- network: '{{ network }}'
access_configs:
- name: External NAT
nat_ip: '{{ address }}'
type: ONE_TO_ONE_NAT
state: present

This example creates a compute instance with a specific name, zone, machine type, image and network. It uses the state: present parameter to indicate that the instance should exist. It also specifies the disks and network_interfaces parameters to configure the disk and network settings of the instance. The disk and network variables are assumed to be defined elsewhere in the playbook or inventory.

Deleting a compute instance with a specific name and zone:

- name: dlete gcp instance
google.cloud.gcp_compute_instance:
name: test_object
zone: us-central1-a
state: absent

For this task, it deletes a compute instance with a specific name and zone. It uses the state: absent parameter to indicate that the instance should not exist. It does not need to specify any other parameters, as the name and zone are enough to identify the instance to delete.

Updating a compute instance with a new machine type and labels

- name: update gcp instance
google.cloud.gcp_compute_instance:
name: test_object
zone: us-central1-a
machine_type: n1-standard-2
labels:
env: prod
webserver: nginx
state: present

The update example performs the task of updating a compute instance with a new machine type and labels. It uses the state: present parameter to indicate that the instance should exist. It also specifies the machine_type and labels parameters to change the machine type and labels of the instance. The machine type determines the CPU and memory resources of the instance, and the labels are key-value pairs that can be used to organize and filter instances. Any other parameters that are not specified will remain unchanged.


OpenStack modules can be used to work with OpenStack, an open source cloud platform that provides infrastructure as a service (IaaS). The os_server module is an example of how you can have full control over your OpenStack servers.


You can configure and manage any network device with these modules, such as routers, switches, firewalls and beyond.


With these modules, you have full control over your system resources, whether they are users, groups, files, directories, services, packages or anything else.


Employing these modules, you have full control over your database servers and objects, from MySQL and PostgreSQL to MongoDB and more.


Windows modules can be used to manage Windows systems and applications, such as Active Directory, IIS, PowerShell, etc. For example, you can use the win_service module to manage Windows service

Team-scale automation

AWX

tldr; AWX is a web-base RESTFul API and task engine that operates on top of Ansible, thus enabling you to automate certain aspects of the IT/DevOps.

AWX is an open source project that gives you a sleek and modern web-based user interface, a powerful and flexible REST API, and a robust and scalable task engine to work with Ansible. It is the upstream project of Red Hat Ansible Automation Platform, which is a premium solution that offers additional features and support for enterprise customers. With AWX, you can easily manage your Ansible playbooks, inventories, credentials, and vaults in a collaborative and secure way among your team members. Moreover, AWX empowers you to plan and run your Ansible playbooks on your managed nodes with speed, efficiency and dependability; you can set up custom schedules, workflows, notifications, and callbacks to automate your Ansible operations and monitor their outcomes. In conclusion, AWX gives you full control and visibility over your Ansible playbooks and their execution.

The official Repository for AWX - Ansible.

The AWX repository is a GitHub repository that contains a treasure trove of source code and other resources.

More information on Terraform

Terraform AWX Provider from Denouche.

By using AWX and Terraform together, you can leverage the power and flexibility of Ansible to manage your AWS resources with ease and efficiency. The Two tools that can be used together to automate IT infrastructure.

Example Usage - With Username/Password:

provider "awx" {
hostname = "http://localhost:8078"
username = "kbvetest"
password = "changemepassword"
}

Example Usage - With Token:

provider "awx" {
hostname = "http://localhost:8078"
token = "awxtoken"
}

Remember that if you set both (username/password) and (token), then the (token) will have precedence.

Quick reference

Cheatsheet

tldr; Commands that will make it easier operate ansible scripts / playbooks. This cheatsheet is still a work-in-progress.

An Ansible cheatsheet is a quick and handy reference guide that provides examples and tips on how to use Ansible command line tools and playbooks, thus enabling you to unleash the power of Ansible! With an Ansible cheatsheet at your fingertips, you can breeze through a variety of tasks that would otherwise be tedious and time-consuming. Whether you need to test the connectivity to your nodes, switch to a different user, use a custom SSH key, use password-based authentication, run ad-hoc commands, create and run playbooks, use modules and roles, or anything else, an Ansible cheatsheet will make your life easier and more fun.

Watch and learn

Videos

Field notes

Notes

Notes for Ansible

Questions

Frequently asked

What is Ansible?

Ansible is an open-source IT automation tool for configuration management, application deployment, and orchestration. It is agentless — it connects to hosts over SSH and pushes small programs called modules to do work, then removes them — so managed machines need no special software beyond Python and SSH.

What is an Ansible playbook?

A playbook is a YAML file that describes a set of plays, each mapping a group of hosts to an ordered list of tasks. Playbooks are declarative and idempotent — running one repeatedly converges hosts to the same desired state without repeating changes that are already applied.

Why is Ansible agentless?

Ansible does not install a daemon on managed nodes. It uses existing SSH access and Python to run modules on demand, which lowers setup overhead, reduces attack surface, and means any reachable host can be managed without provisioning an agent first.

What is an Ansible module?

A module is a self-contained unit of work — like apt, copy, service, or template — that Ansible ships to a host to perform one task idempotently. Tasks in a playbook call modules with parameters, and Ansible reports whether each run changed the system.

What is AWX?

AWX is the open-source upstream of Ansible Tower (Red Hat Ansible Automation Platform). It adds a web UI, REST API, role-based access control, job scheduling, and centralized credential management on top of core Ansible for team-scale automation.