<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: codebarber</title>
    <description>The latest articles on DEV Community by codebarber (@codebarber).</description>
    <link>https://dev.to/codebarber</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F311258%2F05994fd1-b44c-4260-b45b-8f14ce95db75.jpeg</url>
      <title>DEV Community: codebarber</title>
      <link>https://dev.to/codebarber</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/codebarber"/>
    <language>en</language>
    <item>
      <title>Dockerfile: ansible, awscli, packer, terraform</title>
      <dc:creator>codebarber</dc:creator>
      <pubDate>Sat, 14 Mar 2020 01:44:06 +0000</pubDate>
      <link>https://dev.to/codebarber/dockerfile-ansible-awscli-packer-terraform-4ppi</link>
      <guid>https://dev.to/codebarber/dockerfile-ansible-awscli-packer-terraform-4ppi</guid>
      <description>&lt;p&gt;The other day I was asked to convert the shell scripts used to build out our AWS AMI images into ansible playbooks.  The issue, we use docker with the hashicorp/packer image, which doesn't have ansible.  That set me on this short journey to build a docker image that had the tools we needed, and then some.&lt;/p&gt;

&lt;p&gt;For those that just want to jump to the good stuff, here's the links to my Github and Docker Hub repos.&lt;/p&gt;


&lt;div class="ltag-github-readme-tag"&gt;
  &lt;div class="readme-overview"&gt;
    &lt;h2&gt;
      &lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--qF2jUiUG--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://practicaldev-herokuapp-com.freetls.fastly.net/assets/github-logo-6a5bca60a4ebf959a6df7f08217acd07ac2bc285164fae041eacb8a148b1bab9.svg" alt="GitHub logo"&gt;
      &lt;a href="https://github.com/codebarber"&gt;
        codebarber
      &lt;/a&gt; / &lt;a href="https://github.com/codebarber/ansible-packer-terraform"&gt;
        ansible-packer-terraform
      &lt;/a&gt;
    &lt;/h2&gt;
    &lt;h3&gt;
      Docker image with ansible awscli packer and terraform
    &lt;/h3&gt;
  &lt;/div&gt;
&lt;/div&gt;



&lt;center&gt;&lt;a href="https://hub.docker.com/r/codebarber/ansible-packer-terraform"&gt;dockerhub: codebarber/ansible-packer-terraform&lt;/a&gt;&lt;/center&gt;

&lt;p&gt;With docker the image is defined as layers in the build file called Dockerfile.  Additional layers are added as needed, and all these layers are steps taken to build your final docker image. &lt;/p&gt;

&lt;p&gt;So let's get started writing the dockerfile.  In the text editor of your choosing type:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="n"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;ubuntu&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="n"&gt;bionic&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;20200219&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;This is the first layer instructing docker to pull that docker image as the base layer.&lt;/p&gt;

&lt;p&gt;To allow easy version updates lets setup some arguments with defaults set by adding:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="n"&gt;ARG&lt;/span&gt; &lt;span class="n"&gt;TERRAFORM_VERSION&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="s"&gt;"0.12.23"&lt;/span&gt;
&lt;span class="n"&gt;ARG&lt;/span&gt; &lt;span class="n"&gt;ANSIBLE_VERSION&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="s"&gt;"2.5.1"&lt;/span&gt;
&lt;span class="n"&gt;ARG&lt;/span&gt; &lt;span class="n"&gt;PACKER_VERSION&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="s"&gt;"1.5.4"&lt;/span&gt;
&lt;span class="n"&gt;ARG&lt;/span&gt; &lt;span class="n"&gt;AWSCLI_VERSION&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="s"&gt;"1.18.19"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;Next we add the metadata for the docker image:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="n"&gt;LABEL&lt;/span&gt; &lt;span class="n"&gt;maintainer&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="s"&gt;"Codebarber &amp;lt;ernest@codebarber.com&amp;gt;"&lt;/span&gt;
&lt;span class="n"&gt;LABEL&lt;/span&gt; &lt;span class="n"&gt;terraform_version&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="n"&gt;TERRAFORM_VERSION&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="n"&gt;LABEL&lt;/span&gt; &lt;span class="n"&gt;ansible_version&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="n"&gt;ANSIBLE_VERSION&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="n"&gt;LABEL&lt;/span&gt; &lt;span class="n"&gt;aws_cli_version&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="n"&gt;AWSCLI_VERSION&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;You would obviously want to update maintainer if you'll be publishing your own version to Docker Hub.  So now we're coming to the next big layer.  Here we are installing the packages we want in our image.&lt;/p&gt;

&lt;p&gt;Add:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="n"&gt;ENV&lt;/span&gt; &lt;span class="n"&gt;DEBIAN_FRONTEND&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;noninteractive&lt;/span&gt;
&lt;span class="n"&gt;ENV&lt;/span&gt; &lt;span class="n"&gt;AWSCLI_VERSION&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="n"&gt;AWSCLI_VERSION&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="n"&gt;ENV&lt;/span&gt; &lt;span class="n"&gt;TERRAFORM_VERSION&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="n"&gt;TERRAFORM_VERSION&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="n"&gt;ENV&lt;/span&gt; &lt;span class="n"&gt;PACKER_VERSION&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="n"&gt;PACKER_VERSION&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="n"&gt;RUN&lt;/span&gt; &lt;span class="n"&gt;apt&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;get&lt;/span&gt; &lt;span class="n"&gt;update&lt;/span&gt; \
    &lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt; &lt;span class="n"&gt;apt&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;get&lt;/span&gt; &lt;span class="n"&gt;install&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;y&lt;/span&gt; &lt;span class="n"&gt;ansible&lt;/span&gt; &lt;span class="n"&gt;curl&lt;/span&gt; &lt;span class="n"&gt;python3&lt;/span&gt; &lt;span class="n"&gt;python3&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;pip&lt;/span&gt; &lt;span class="n"&gt;python3&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;boto&lt;/span&gt; &lt;span class="n"&gt;unzip&lt;/span&gt;  \
    &lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt; &lt;span class="n"&gt;pip3&lt;/span&gt; &lt;span class="n"&gt;install&lt;/span&gt; &lt;span class="o"&gt;--&lt;/span&gt;&lt;span class="n"&gt;upgrade&lt;/span&gt; &lt;span class="n"&gt;awscli&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="n"&gt;AWSCLI_VERSION&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt; \
    &lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt; &lt;span class="n"&gt;curl&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;LO&lt;/span&gt; &lt;span class="n"&gt;https&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;releases&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;hashicorp&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;com&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;terraform&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="n"&gt;TERRAFORM_VERSION&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;terraform_&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="n"&gt;TERRAFORM_VERSION&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="n"&gt;_linux_amd64&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="nb"&gt;zip&lt;/span&gt; \
    &lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt; &lt;span class="n"&gt;curl&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;LO&lt;/span&gt; &lt;span class="n"&gt;https&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;releases&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;hashicorp&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;com&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;packer&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="n"&gt;PACKER_VERSION&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;packer_&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="n"&gt;PACKER_VERSION&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="n"&gt;_linux_amd64&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="nb"&gt;zip&lt;/span&gt; \
    &lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt; &lt;span class="n"&gt;unzip&lt;/span&gt; &lt;span class="s"&gt;'*.zip'&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt; &lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;usr&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;local&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="nb"&gt;bin&lt;/span&gt; \
    &lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt; &lt;span class="n"&gt;apt&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;get&lt;/span&gt; &lt;span class="n"&gt;clean&lt;/span&gt; \
    &lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt; &lt;span class="n"&gt;rm&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;rf&lt;/span&gt; &lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;var&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;lib&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;apt&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;lists&lt;/span&gt;&lt;span class="o"&gt;/*&lt;/span&gt; &lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;tmp&lt;/span&gt;&lt;span class="o"&gt;/*&lt;/span&gt; &lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;var&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;tmp&lt;/span&gt;&lt;span class="o"&gt;/*&lt;/span&gt; &lt;span class="o"&gt;*.&lt;/span&gt;&lt;span class="nb"&gt;zip&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;Above since we are using an ubuntu base image we'll use ubuntu tools and package names.  That pretty much completes our image, now we just need to set the command that will be run by this image by setting the CMD as the final step.  Here we'll tell our docker image to run bash.  This allows us to run multiple tools by passing the command and options to docker run command.&lt;/p&gt;

&lt;p&gt;Add:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="n"&gt;CMD&lt;/span&gt;    &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s"&gt;"/bin/bash"&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;You can easily test it out by running the following command to get the version of tools installed.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nv"&gt;$ &lt;/span&gt;docker run &lt;span class="nt"&gt;--rm&lt;/span&gt; codebarber/ansible-packer-terraform aws &lt;span class="nt"&gt;--version&lt;/span&gt;
aws-cli/1.18.19 Python/3.6.9 Linux/4.4.59+ botocore/1.15.19

&lt;span class="nv"&gt;$ &lt;/span&gt;docker run &lt;span class="nt"&gt;--rm&lt;/span&gt; codebarber/ansible-packer-terraform ansible &lt;span class="nt"&gt;--version&lt;/span&gt;
ansible 2.5.1
  config file &lt;span class="o"&gt;=&lt;/span&gt; /etc/ansible/ansible.cfg
  configured module search path &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="o"&gt;[&lt;/span&gt;u&lt;span class="s1"&gt;'/root/.ansible/plugins/modules'&lt;/span&gt;, u&lt;span class="s1"&gt;'/usr/share/ansible/plugins/modules'&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;
  ansible python module location &lt;span class="o"&gt;=&lt;/span&gt; /usr/lib/python2.7/dist-packages/ansible
  executable location &lt;span class="o"&gt;=&lt;/span&gt; /usr/bin/ansible
  python version &lt;span class="o"&gt;=&lt;/span&gt; 2.7.17 &lt;span class="o"&gt;(&lt;/span&gt;default, Nov  7 2019, 10:07:09&lt;span class="o"&gt;)&lt;/span&gt; &lt;span class="o"&gt;[&lt;/span&gt;GCC 7.4.0]

&lt;span class="nv"&gt;$ &lt;/span&gt;docker run &lt;span class="nt"&gt;--rm&lt;/span&gt; codebarber/ansible-packer-terraform packer &lt;span class="nt"&gt;-version&lt;/span&gt;
1.5.4

&lt;span class="nv"&gt;$ &lt;/span&gt;docker run &lt;span class="nt"&gt;--rm&lt;/span&gt; codebarber/ansible-packer-terraform terraform &lt;span class="nt"&gt;-version&lt;/span&gt;
Terraform v0.12.23
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;So just about now, you might be asking yourself, well this is great, but how do I get my config, keys, scripts, templates or playbooks into that image so it can do the work?  The nice thing about docker, is its ability to map volumes/folders into the container as it runs.  Here is how you can get your &lt;code&gt;~/.ssh&lt;/code&gt;, &lt;code&gt;~/.aws&lt;/code&gt;, and current directory mapped into your container.&lt;/p&gt;

&lt;p&gt;Lets pretend you are inside your ansible folder on your host that contains the playbooks and roles.  In order to run that test-playbook.yml here's the command:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nv"&gt;$ &lt;/span&gt;docker run &lt;span class="nt"&gt;--rm&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
             &lt;span class="nt"&gt;-w&lt;/span&gt; /opt &lt;span class="se"&gt;\&lt;/span&gt;
             &lt;span class="nt"&gt;-v&lt;/span&gt; &lt;span class="si"&gt;$(&lt;/span&gt;&lt;span class="nb"&gt;pwd&lt;/span&gt;&lt;span class="si"&gt;)&lt;/span&gt;:/opt/ &lt;span class="se"&gt;\&lt;/span&gt;
             &lt;span class="nt"&gt;-v&lt;/span&gt; ~/.aws:/root/.aws &lt;span class="se"&gt;\&lt;/span&gt;
             &lt;span class="nt"&gt;-v&lt;/span&gt; ~/.ssh:/root/.ssh &lt;span class="se"&gt;\&lt;/span&gt;
             codebarber/ansible-packer-terraform ansible test-playbook.yml
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;Explaining the flags in order:&lt;br&gt;
--rm: tells docker to remove the container after it completes&lt;br&gt;
-w: sets the working directory inside the container to /opt&lt;br&gt;
-v: maps your current working directory into the containers /opt&lt;br&gt;
-v: maps our .aws folder into the containers ${HOME}/.aws&lt;br&gt;
-v: maps our .ssh folder into the containers ${HOME}/.ssh&lt;/p&gt;

&lt;p&gt;I hope you find this information useful.&lt;/p&gt;

&lt;p&gt;Have a great day!&lt;/p&gt;

</description>
      <category>docker</category>
      <category>ansible</category>
      <category>packer</category>
      <category>terraform</category>
    </item>
  </channel>
</rss>
