Siddheshwar More
Siddheshwar More
Software Engineer

Ansible to manage AWS infrastructure

Ansible is the fastest growing python-based open source IT automation tool that can be used to configure/manage systems, deploy applications and provision infrastructure on numerous cloud platforms. Ansible is not only limited to managing servers but it also manages network switches, provision instances, and complete cloud infrastructure. Ansible modules have been designed to work seamlessly within cloud environments like AWS, GCP, VMWare, and Microsoft Azure. With the correct configuration Ansible playbooks help to make the application deployment idempotent.

Ansible cloud library includes over 300+ modules, which manage the different services of cloud like – compute, routing, networking, access policy, permissions, load balancers, auto scaling, storage and many more.

Ansible supports the following cloud integrations:

  • Amazon Web Services (AWS)
  • Google Cloud Platform (GCP)
  • Microsoft Azure(Azure)
  • Digital Ocean
  • Linode
  • WebFaction
  • Profit Bricks
  • Rackspace
  • VmWare
  • CloudStack
  • OpenStack


In this blog we focus on Amazon Web Services ( AWS).

Prerequisites:

1. Ansible currently supports Linux workstation and requires Python 2.7 or greater to be installed.
2. AWS User Access Credentials

Architecture of Ansible Cloud Integration:

Ansible Workstation Setup:

Control Machine:
The control machine acts as the Ansible server where all the playbooks and configuration files are located. It can be configured on common Linux Distribution, OS X or BSDs. For this example, we have configured Ubuntu OS on the workstation.

To setup the ansible workstation the following commands are used

$ sudo apt-get install software-properties-common
$ sudo apt-add-repository ppa:ansible/ansible
$ sudo apt-get update
$ sudo apt-get install ansible

AWS Cloud Provider:
Amazon Web Services (AWS) is a secure public cloud services provider that offers compute, storage, networking, monitoring and other functionality that helps in application deployment.

The following AWS services are supported by the Ansible module-
– Cloud Formation templates
– AWS EC2
– ELB
– VPC
– ECS
– IAM role
– S3
– RDS
– Route 53
– Lambda
– Simple notification service
– AWS SQS queues etc.

Configuring the workstation- The Ansible AWS modules uses the Python Boto library internally.
The following commands are used to set up the boto run

$ sudo easy_install pip
$ sudo pip install boto

After installation, create a file named boto and provide the necessary credentials.

Create file ~/.boto
 
     [Credentials]
     aws_access_key_id = (access key)
     aws_secret_access_key = (secret access key)

To run Ansible on your workstation, you need to set environment variables by specifying your Secret Key and Access Key.

$ export AWS_ACCESS_KEY_ID= 'YOUR_AWS_API_KEY'
$ export AWS_SECRET_ACCESS_KEY=  'YOUR_AWS_API_SECRET_KEY'

OR
Prepare the ansible vars file and encrypt it using the ansible vault

../roles//vars/main.yml
    ---
    ec2_access_key: "--REMOVED--"
    ec2_secret_key: "--REMOVED--"

The ~/.vault_pass.txt contains the secret password.

# To encrypt the var file

ansible-vault encrypt ../roles//vars/main.yml --vault-password-file ~/.vault_pass.txt

# To decrypt the var file

ansible-vault decrypt ../roles//vars/main.yml --vault-password-file ~/.vault_pass.txt

# To run the ansible playbook

ansible-playbook -i hosts deploy.yml --vault-password-file ~/.vault_pass.txt

Note- It is recommended to use the IAM user credentials with limited and required AWS service access. Create the Private Key pair on AWS, this is used for ssh while connecting to the instance.

Here is an example of Ansible playbook that provisions the AWS instance:

Directory structure for ansible:
 
       |--aws-ansible
 	 |--roles
           |--instance_provisioning
             |--tasks
               |--main.yml
             |--vars
           |--main.yml
         |--deploy.yml
      |--hosts

The playbook tasks file contains the EC2 module used to provision the server. It requires VPC, AWS Private Key, and Security Group ID from the AWS account

~/aws-ansible/roles/instance_provisioning/tasks/main.yml:

# To include the vars

- include_vars: vars/ec2_creds.yml

# Ansible EC2 module to provision the instance

- ec2:
      key_name: "{{ qa_env.key_name }}"
      assign_public_ip: yes
      group_id: "{{ qa_env.sg_group }}"
      instance_type: "{{ qa_env.instance_type }}"
      image: "{{ qa_env.image }}"
      wait: true
      wait_timeout: 600
      exact_count: 1
      region: us-west-2
      vpc_subnet_id: "{{ qa_env.vpc_subnet_id}}"
      instance_tags:
        Name: "{{ qa_env.instance_tags.name }}"
      aws_access_key: "{{ aws_access_key }}"
      aws_secret_key: "{{ aws_secret_key }}"
    register: deploy_instance

Here we are using the vars from ec2_creds.yml file i.e encrypted using ansible vault.
aws_access_key: “{{ aws_access_key }}”
aws_secret_key: “{{ aws_secret_key }}”

# Add a host (and alternatively a group) to the ansible-playbook in-memory inventory

    - name: Add new instance to host group
    add_host: hostname={{ item.public_ip }} groupname=launched
    with_items: "{{ deploy_instance.instances }}"

# Wait until the instance is up and running and ssh is enabled

    - name: Wait for SSH to come up
    wait_for: host="{{ item.public_dns_name }}" port=22 delay=60 timeout=320 state=started
    with_items: "{{ deploy_instance.instances }}"

Check out our sample code for provisioning Ansible on AWS.

Conclusion:

The article gives you a brief idea how well Ansible integrates with AWS to build the network and instances. The Ansible AWS modules make it easy to manage and configure Amazon’s EC2 instances. In the next blog, we will see how to configure and provision Ansible playbook on Azure.

Share

Responses

Your email address will not be published.

  1. How We can define new inventory group . We are using CloudFormation stack. after making instance up, how to define hostgroup?

    • This can be achieved by using the Ansible dynamic inventory. We can use the AWS tags and fetch instances on the basis of tags to create dynamic groups on top of it.