(packer)AWSのAMI作成を自動化する

投稿者: | 2018年3月3日

みなさんこんにちは。ヒロウミです。

PackerとAnsibleを使ってAWSのAMI作成を自動化してみたのでメモっておきます。コードとしてインフラを管理できるようになり、Gitなどと連携することによりチーム開発で大きな力を発揮するのではないでしょうか。

ツールのインストールも利用方法も簡単なため手軽に始められるところも魅力です。

前提条件

  • Packerがインストールされていること Install Packer
  • Ansibleがインストールされていること Installation
  • AWSのアカウントを保持していること
  • IAMロールが適切に付与されていること

手順

  1. テンプレートファイルを作成する
  2. Ansibleを記述する
  3. AWS環境変数を設定する
  4. packer validateを実行する
  5. packer buildを実行する

テンプレートファイルを作成する

今回はAWSで用意されているCentOS7のイメージに全サーバで共通する設定を行います。

provisionersの項目にAnsibleを設定することにより、設定内容をAnsibleで管理することができます。

{
  "builders" : [{
    "type" : "amazon-ebs",
    "region" : "ap-northeast-1",
    "instance_type" : "t2.micro",
    "source_ami" : "ami-e4599a82",
    "ssh_username" : "centos",
    "ami_name" : "golden-img-template{{isotime | clean_ami_name}}",
    "ami_description" : "This AMI is Base image for all other AMI.Disables selinux and installs utility tools."
  }],
  "provisioners" : [{
    "type" : "ansible",
    "extra_arguments" : [
      "-b"
    ],
    "playbook_file" : "../ansible/common.yml"
  }]
}

Ansibleを記述する

common.yml

- name: golden template image
  hosts: all
  become: yes
  roles:
    - common

roles/common/tasks/main.yml

- name: install utils
  yum : name={{ item }} state=present
  with_items:
    - vim
    - unzip
    - git
    - tcpdump
    - net-tools
    - epel-release

- name: disable selinux
  selinux: state=disabled

- name: set timezone to Asia/Tokyo
  timezone:
    name: Asia/Tokyo

AWS環境変数を設定する

PackerでAWSを操作するためにはAPIを利用する設定が必要です。そのため、環境変数に以下の2つを設定しましょう。

$ export AWS_ACCESS_KEY_ID=YOUR_KEY_ID
$ export AWS_SECRET_ACCESS_KEY=YOUR_ACCESS_ID

packer validateを実行する

packerのテンプレートファイルのバリデートを実行します。

エラーが出力されたらテンプレートファイルを修正しましょう。以下のように「Template validated successfully」が出力されればOKです。

$ packer validate golden-img.template
Template validated successfully.

packer buildを実行する

最後にAMIの作成を実行します

$ packer build golden-img.template
amazon-ebs output will be in this color.

==> amazon-ebs: Prevalidating AMI Name: golden-img-template2018-03-03T06-17-00Z
    amazon-ebs: Found Image ID: ami-e4599a82
==> amazon-ebs: Creating temporary keypair: packer_5a9a3ddc-f286-26e1-af94-c046827f4fbe
==> amazon-ebs: Creating temporary security group for this instance: packer_5a9a3de1-7197-a30e-c999-ac7fdf88f8fb
==> amazon-ebs: Authorizing access to port 22 from 0.0.0.0/0 in the temporary security group...
==> amazon-ebs: Launching a source AWS instance...
==> amazon-ebs: Adding tags to source instance
    amazon-ebs: Adding tag: "Name": "Packer Builder"
    amazon-ebs: Instance ID: i-050e853b4ef2912fc
==> amazon-ebs: Waiting for instance (i-050e853b4ef2912fc) to become ready...
==> amazon-ebs: Waiting for SSH to become available...
==> amazon-ebs: Connected to SSH!
==> amazon-ebs: Provisioning with Ansible...
==> amazon-ebs: Executing Ansible: ansible-playbook --extra-vars packer_build_name=amazon-ebs packer_builder_type=amazon-ebs -i /tmp/packer-provisioner-ansible577903068 /home/vagrant/devops_handson_for_ci/infra/ansible/common.yml --private-key /tmp/ansible-key135602737 -b
    amazon-ebs:
    amazon-ebs: PLAY [golden template image] ***************************************************
    amazon-ebs:
    amazon-ebs: TASK [Gathering Facts] *********************************************************
    amazon-ebs: ok: [default]
    amazon-ebs:
    amazon-ebs: TASK [common : install utils] **************************************************
    amazon-ebs: changed: [default] => (item=[u'vim', u'unzip', u'git', u'tcpdump', u'net-tools', u'epel-release'])
    amazon-ebs:
    amazon-ebs: TASK [common : set up ntp] *****************************************************
    amazon-ebs: changed: [default]
    amazon-ebs:
    amazon-ebs: TASK [common : disable selinux] ************************************************
    amazon-ebs: changed: [default]
    amazon-ebs:  [WARNING]: SELinux state temporarily changed from 'enforcing' to 'permissive'.
    amazon-ebs:
    amazon-ebs: State change will take effect next reboot.
    amazon-ebs: TASK [common : set timezone to Asia/Tokyo] *************************************
    amazon-ebs: changed: [default]
    amazon-ebs:
    amazon-ebs: PLAY RECAP *********************************************************************
    amazon-ebs: default                    : ok=5    changed=4    unreachable=0    failed=0
    amazon-ebs:
==> amazon-ebs: Stopping the source instance...
    amazon-ebs: Stopping instance, attempt 1
==> amazon-ebs: Waiting for the instance to stop...
==> amazon-ebs: Creating the AMI: golden-img-template2018-03-03T06-17-00Z
    amazon-ebs: AMI: ami-bd2c6fdb
==> amazon-ebs: Waiting for AMI to become ready...
==> amazon-ebs: Modifying attributes on AMI (ami-bd2c6fdb)...
    amazon-ebs: Modifying: description
==> amazon-ebs: Modifying attributes on snapshot (snap-0d734766d8ba0770f)...
==> amazon-ebs: Terminating the source AWS instance...
==> amazon-ebs: Cleaning up any extra volumes...
==> amazon-ebs: Destroying volume (vol-091ac02ee8b23a665)...
==> amazon-ebs: Deleting temporary security group...
==> amazon-ebs: Deleting temporary keypair...
Build 'amazon-ebs' finished.

==> Builds finished. The artifacts of successful builds are:
--> amazon-ebs: AMIs were created:
ap-northeast-1: ami-bd2c6fdb

AWSのコンソール画面で確認して見ます

AWSのAMI管理は煩雑になりやすいと思います。さらに、どんな手順を実行したのかが分からなくなってしまい、思わぬ設定漏れなども発生してしまいます。

今回ご紹介したPacker + Ansibleを用いてAMIの作成方法の統一化を行ってみてはどうでしょうか。