At Red Hat Tech Day Netherlands 2026 in Bunnik, Fred van Zwieten and Ismail Dhaoui demoed the new Automation Portal in AAP 2.7, a self-service template gallery where every job template gets a one-click "Start" button. One of the templates shown in the catalog was "Cloud - Provision AWS EC2 Instance", described as spinning up an EC2 instance with standard tagging. Here's a runnable playbook that matches what that template would launch behind the button.
---
- name: Cloud - Provision AWS EC2 Instance
hosts: localhost
connection: local
gather_facts: false
vars:
ec2_region: "eu-west-1"
ec2_instance_type: "t3.micro"
ec2_image_id: "ami-0abcdef1234567890"
ec2_key_name: "provisioning-key"
ec2_subnet_id: "subnet-0123456789abcdef0"
ec2_security_group: "sg-0123456789abcdef0"
owner_email: "team-cloud@example.com"
cost_center: "CC-4471"
environment_tag: "development"
tasks:
- name: Provision the EC2 instance with standard tags
amazon.aws.ec2_instance:
region: "{{ ec2_region }}"
name: "app-server-{{ environment_tag }}"
instance_type: "{{ ec2_instance_type }}"
image_id: "{{ ec2_image_id }}"
key_name: "{{ ec2_key_name }}"
vpc_subnet_id: "{{ ec2_subnet_id }}"
security_group: "{{ ec2_security_group }}"
wait: true
tags:
Name: "app-server-{{ environment_tag }}"
Environment: "{{ environment_tag }}"
Owner: "{{ owner_email }}"
CostCenter: "{{ cost_center }}"
ManagedBy: "ansible-automation-platform"
Template: "Cloud - Provision AWS EC2 Instance"
state: running
register: ec2_result
- name: Show the new instance ID and public IP
ansible.builtin.debug:
msg: >-
Instance {{ ec2_result.instances[0].instance_id }} is running
at {{ ec2_result.instances[0].public_ip_address | default('no public IP assigned') }}
What this does
The amazon.aws.ec2_instance task launches a single instance from a given AMI into an existing subnet and security group, then waits for it to reach the running state. The tags block is the point of the exercise: Name, Environment, Owner, and CostCenter are the kind of standard tags a platform team enforces across every cloud request, and ManagedBy/Template make it obvious in the AWS console that the resource came from an AAP job rather than a manual click-through. In the Automation Portal, environment_tag, owner_email, and cost_center are exactly the kind of fields a survey would collect from the requester before the job runs, so the operator starting the template from the gallery never has to touch the YAML or know where the playbook lives.
Notes / Gotchas
- Requires the
amazon.awscollection andboto3/botocoreon the execution node or execution environment. - Credentials should come from an AAP-managed AWS credential type, not hardcoded keys in the playbook.
wait: trueblocks until the instance is running; addwait_timeoutif your account's launch times are slow.- Untagged or inconsistently tagged instances are a common source of cost-allocation drift — enforcing tags in the template itself (rather than trusting the requester) is the reason this playbook exists as a governed template rather than an ad hoc script.
- Re-running the playbook without
filtersor an idempotency key will launch a second instance rather than update the first;ec2_instancematches onnameplus filters when supplied, so pin those down for safe re-runs.
Wrapping standard tagging into a self-service template turns a five-minute AWS console task into a one-click, auditable, cost-attributed request.
Related Articles
- Ansible Playbook Example: Create an S3 Bucket with Encryption
- Ansible Playbook Example: Request an Azure Resource Group with RBAC
- Ansible azure.azcollection Example: Provision Azure ML and Storage Resources