Ansible Playbook検証環境構築 (Windows10 + KitchenCI + Docker)


目的

Windows + kitchenCI + docker環境でansible playbookのテストを行う場合の選択肢としては以下の2つがある。

  • kitchen-ansibleを使用

対象にansibleを導入してローカル適用を行う
コントローラーノードのファイルをcopyするなどの操作ができない

  • kitchen-ansiblepushを使用

コントローラーノードにansibleを導入してsshにて適用
ansibleとしては本来の使用方法となるが、windowsに直接ansibleを導入することが困難

ここでは、ansibleを導入したdockerコンテナ(D1)から、kitchen-ansiblepushを利用したtest-kitchenにより、別のdocker環境(D2)を起動してansible playbookを適用させるKitchenCI環境を構築する例を示します。
なお、docker.sockのマウントによりコンテナ内からdockerを呼び出しているので、セキュリティ的なリスクがありうることにはご注意下さい。

MAC版はこちら

環境

  • Windows10 Pro: 1909
  • Docker Desktop on Windows: Docker version 19.03.5, build 633a0ea
  • Chef Workstation: 0.11.21
  • git for windows: git version 2.25.1.windows.1

前提

  • 操作はgit bash環境で実行する
  • Docker for windowsを設定済み
  • Gitを設定済み

test-kitchen, InSpec (Chef Workstation)の設定

$ echo "eval \"\$(/c/opscode/chef-workstation/bin/chef shell-init bash | sed -e 's|C:|/c|g' -e 's|\\|/|g' -e 's|;|:|g')\"" >> ~/.bash_profile
$ . ~/.bash_profile

パスなどの設定を行う

kitchen-ansible, kitchen-dockerの導入

$ gem install kitchen-ansible
$ gem install kitchen-docker

docker controllerコンテナ環境D1を作成するためにkitchen-ansibleを使用する。

サンプルをgit clone

$ git clone [email protected]:hiroyuki-onodera/ansible-testenv-windows.git
$ cd ansible-testenv-windows.git

Docker環境D1(ansible controller)構成用ファイル

kitchen.yml (ansible controller構成用)

kitchen.yml
driver:
  name: docker
  run_options: >-
    -v //var/run/docker.sock:/var/run/docker.sock
    -v /usr/local/bin/docker:/bin/docker
    -v <%= ENV['PWD'] %>/repo:/home/kitchen/repo
  socket: npipe:////./pipe/docker_engine

provisioner:
  name: ansible_playbook
  chef_bootstrap_url: nil
  hosts: ansible-controller
  playbook: site.yml

platforms:
  - name: centos-7

suites:
  - name: ansible-controller

site.yml (ansible controller構成用)

site.yml
- hosts: all
  gather_facts: false
  become: true
  become_user: kitchen
  tasks:
  - name: install the chef-workstation rpm from a remote repo
    become_user: root
    yum:
      name: https://packages.chef.io/files/stable/chef-workstation/0.11.21/el/7/chef-workstation-0.11.21-1.el7.x86_64.rpm

  - name: add 'eval "$(chef shell-init bash)"' to ~/.bash_profile
    lineinfile:
      dest: ~/.bash_profile
      line: eval "$(chef shell-init bash)"

  - name: gem install
    shell: |
      set -e
      . ~/.bash_profile
      gem install kitchen-ansiblepush
      gem install kitchen-docker

Docker環境D1(ansible controller)構成

$ kitchen test -d never

数分かかる。
ansible, test-kitchen, InSpec, kitchen-ansiblepush, kitchen-docker が導入され、./repo/sampleが共有されたcentos7のdockerコンテナが立ち上がる。

ansible controller環境にログインし、サンプルの設定ファイルを確認

$ kitchen login
Last login: Fri Mar  6 11:46:15 2020 from 172.17.0.1



[kitchen@8b85d4a98c06 ~]$ cd repo/sample/



[kitchen@8b85d4a98c06 sample]$ ls
kitchen.yml  site.yml  test

ここで~kitchen/repoは、Windows上の./repoの共有デバイス

repo/sample/kitchen.yml

kitchenCI設定ファイル
git cloneの対象

repo/sample/kitchen.yml
---
driver:
  name: docker
  use_sudo: true
  use_internal_docker_network: true

provisioner:
  name: ansible_push
  chef_bootstrap_url: nil

platforms:
- name: centos-7

suites:
- name: ansiblepush
  provisioner:
    playbook: ./site.yml

verifier:
  name: inspec
  inspec_tests:
  - test/integration/default

repo/sample/site.yml

ユーザーfooを追加するplaybook
git cloneの対象

repo/sample/site.yml
---
- hosts: all
  gather_facts: false
  become: true
  tasks:
  -
    user:
      name: foo

repo/sample/test/integration/default/default_test.rb

InSpec test
ここではユーザーfooの存在を確認
git cloneの対象

repo/sample/test/integration/default/default_test.rb
# # encoding: utf-8

describe user('foo') do
  it { should exist }
end

kitchenCIを回し、環境D2を構成し、Ansible playbookのsite.ymlを適用

なお、

  • $ kitchen test にて、対象環境構成、ansible playbook適用、verify、対象環境削除 が一括で可能。
  • $ kitchen test -d never にて、対象環境構成、ansible playbook適用、verify が一括で可能。
[kitchen@8b85d4a98c06 sample]$ kitchen converge
-----> Starting Test Kitchen (v2.3.4)
-----> Creating <ansiblepush-centos-7>...
       Sending build context to Docker daemon  15.87kB
       Step 1/17 : FROM centos:centos7
        ---> 5e35e350aded
...
       *************** AnsiblePush run ***************

PLAY [all] ***************************************************************************************************************************************************

TASK [user] **************************************************************************************************************************************************
changed: [centos-7]

PLAY RECAP ***************************************************************************************************************************************************
centos-7                   : ok=1    changed=1    unreachable=0    failed=0    skipped=0    rescued=0    ignored=0

       *************** AnsiblePush end run *******************
       Downloading files from <ansiblepush-centos-7>
       Finished converging <ansiblepush-centos-7> (0m3.94s).
-----> Test Kitchen is finished. (0m7.26s)

changed=1 は、ユーザー追加によるシステム変更を示している。

作成された環境D2に対してInSpec Testを実行

[kitchen@8b85d4a98c06 sample]$ kitchen verify
-----> Starting Test Kitchen (v2.3.4)
-----> Setting up <ansiblepush-centos-7>...
       Finished setting up <ansiblepush-centos-7> (0m0.00s).
-----> Verifying <ansiblepush-centos-7>...
       Loaded tests from {:path=>".home.kitchen.repo.sample.test.integration.default"}

Profile: tests from {:path=>"/home/kitchen/repo/sample/test/integration/default"} (tests from {:path=>".home.kitchen.repo.sample.test.integration.default"})
Version: (not specified)
Target:  ssh://[email protected]:22

  User foo
     ✔  should exist

Test Summary: 1 successful, 0 failures, 0 skipped
       Finished verifying <ansiblepush-centos-7> (0m0.96s).
-----> Test Kitchen is finished. (0m3.28s)


[kitchen@8b85d4a98c06 sample]$ kitchen list
Instance              Driver  Provisioner  Verifier  Transport  Last Action  Last Error
ansiblepush-centos-7  Docker  AnsiblePush  Inspec    Ssh        Verified     <None>

InSpec TestによりUser fooの存在が確認された

環境D2にログインして確認

[kitchen@8b85d4a98c06 sample]$ kitchen login
Last login: Fri Mar  6 11:50:30 2020 from 172.17.0.2


[kitchen@d99a512d8465 ~]$ grep foo /etc/passwd
foo:x:1001:1001::/home/foo:/bin/bash


[kitchen@d99a512d8465 ~]$ logout
Connection to 172.17.0.3 closed.

環境D2の削除

[kitchen@8b85d4a98c06 sample]$ kitchen destroy
-----> Starting Test Kitchen (v2.3.4)
-----> Destroying <ansiblepush-centos-7>...
       PID                 USER                TIME                COMMAND
       22231               root                0:00                /usr/sbin/sshd -D -o UseDNS=no -o UsePAM=no -o PasswordAuthentication=yes -o UsePrivilegeSeparation=no -o PidFile=/tmp/sshd.pid
       d99a512d84657b1dc5b1d1a0eff8298fadd26d3009fe32b6496a2cf25ff36592
       d99a512d84657b1dc5b1d1a0eff8298fadd26d3009fe32b6496a2cf25ff36592
       Finished destroying <ansiblepush-centos-7> (0m0.47s).
-----> Test Kitchen is finished. (0m2.81s)

環境D1の削除

[kitchen@8b85d4a98c06 sample]$ logout
Connection to localhost closed.


$ kitchen destroy
-----> Starting Test Kitchen (v2.3.4)
-----> Destroying <ansible-controller-centos-7>...
       PID                 USER                TIME                COMMAND
       21479               root                0:00                /usr/sbin/sshd -D -o UseDNS=no -o UsePAM=no -o PasswordAuthentication=yes -o UsePrivilegeSeparation=no -o PidFile=/tmp/sshd.pid
       8b85d4a98c067c99a20d2163d9e04cad63718c537d9506921004f8203fc61589
       8b85d4a98c067c99a20d2163d9e04cad63718c537d9506921004f8203fc61589
       Finished destroying <ansible-controller-centos-7> (0m2.21s).
-----> Test Kitchen is finished. (0m3.71s)