ひよこインフラてっく!

ひよこインフラエンジニア「ひよこ大佐」による技術ブログ的なもの。インフラ技術や仮想化、Pythonなど。

AnsibleでDockerコンテナを操作してみよう

こんにちは、ひよこ大佐です。 いよいよ2017年も今日が最後の日となりました。皆様いかがお過ごししょうか。 大掃除もようやく終わり、無事今年も新年を迎えることができそうです。

そういえば、大掃除という習慣ですが、その起源は神道の「煤払い」から来ているとのことです。

jinja.jp

家を綺麗にし歳神様をお迎えする習わしが、その宗教的意義が薄れ年末の恒例行事として定着したもののようです。 何気なくやっている新年の恒例行事も、調べてみるといろいろな発見がありますね。

Ansible Connection Pluginについて

さて、今日はAnsibleの記事です。 実はAnsibleからDockerコンテナにたいして操作をすることが可能です。 Ansibleには「Connection Plugin」というPluginの一種として、ターゲットノードへの接続方法を拡張することができます。

通常Ansibleはターゲットノードと接続する際にSSHを使用しますが、それ以外にも現時点で下記の方式で接続することが可能です。今後も拡張が予定されています。

  • buildah - Interact with an existing buildah container
  • chroot - Interact with local chroot
  • docker - Run tasks in docker containers
  • funcd - Use funcd to connect to target
  • iocage - Run tasks in iocage jails
  • jail - Run tasks in jails
  • libvirt_lxc - Run tasks in lxc containers via libvirt
  • local - execute on controller
  • lxc - Run tasks in lxc containers via lxc python library
  • lxd - Run tasks in lxc containers via lxc CLI
  • netconf - Use netconf to run command on network appliances
  • network_cli - Use network_cli to run command on network appliances
  • paramiko_ssh - Run tasks via python ssh (paramiko)
  • persistent - Use a persistent unix socket for connection
  • saltstack - Allow ansible to piggyback on salt minions
  • winrm - Run tasks over Microsoft’s WinRM
  • zone - Run tasks in a zone instance

Connection Plugins — Ansible Documentation

AnsibleでDockerコンテナを操作する

さて、実際にAnsibleからDockerコンテナを操作してみましょう。 今回はAWS上のCentOS 7にdockerとansibleをインストール、CentOS7のdocker imageからコンテナを作成し検証しています。

Dockerのコンテナを作成する

※dockerのコンテナイメージは事前にpullしておきます。

$ sudo docker run -itd --name test-01 centos /bin/bash
$ sudo docker run -itd --name test-02 centos /bin/bash

$ sudo docker ps
CONTAINER ID        IMAGE               COMMAND             CREATED             STATUS              PORTS               NAMES
220b31f3c7c0        centos              "/bin/bash"         3 seconds ago       Up 2 seconds                            test-02
1be95b60e618        centos              "/bin/bash"         59 seconds ago      Up 58 seconds                           test-01

inventoryとplaybookを定義する

以下のようにinventoryとplaybookを定義します。

test_inventory

ローカルのdockerコンテナへの接続となるので、コンテナの名前のみをinventoryに記載しています。

[test_servers]
test-01
test-02

docker_test.yml

playbookの内容は非常にシンプルで、ディレクトリとファイルを作成しているだけです。 ここでのキモは、「connection: docker」という行。 これにより、dockerコンテナへの操作であることを定義しています。

---
- hosts: test_servers
  connection: docker
  tasks:
    - name: create directory
      file:
        path: /home/test/
        state: directory
        mode: 0755

    - name: create file
      file:
        path: /home/test/test.txt
        state: touch
        mode: 0644

Playbookの文法チェックをする

下記コマンドで実行前にPlaybookの文法をチェックすることができます。 実行した際に文法エラーで弾かれることを未然に防ぐ事ができるため、Playbookを作成および変更した際には必ず実施しましょう。

$ sudo ansible-playbook -i ./test_inventory ./docker_test.yml --syntax-check

playbook: ./docker_test.yml

ansibleでテスト実行する

実際にAnsibleで実行する前に、テスト実行します。 --checkオプションをつけることで実際に実行することなくどのように変更されるのか確認できます。--diffオプションで変更後の差分も表示可能です。

$ sudo ansible-playbook -i ./test_inventory ./docker_test.yml --check --diff

PLAY [test_servers] ********************************************************************************************************************

TASK [Gathering Facts] *****************************************************************************************************************
ok: [test-01]
ok: [test-02]

TASK [create directory] ****************************************************************************************************************
--- before
+++ after
@@ -1,4 +1,4 @@
 {
     "path": "/home/test/",
-    "state": "absent"
+    "state": "directory"
 }

changed: [test-01]
--- before
+++ after
@@ -1,4 +1,4 @@
 {
     "path": "/home/test/",
-    "state": "absent"
+    "state": "directory"
 }

changed: [test-02]

TASK [create file] *********************************************************************************************************************
--- before
+++ after
@@ -1,4 +1,4 @@
 {
     "path": "/home/test/test.txt",
-    "state": "absent"
+    "state": "touch"
 }

changed: [test-01]
--- before
+++ after
@@ -1,4 +1,4 @@
 {
     "path": "/home/test/test.txt",
-    "state": "absent"
+    "state": "touch"
 }

changed: [test-02]

PLAY RECAP *****************************************************************************************************************************
test-01                    : ok=3    changed=2    unreachable=0    failed=0   
test-02                    : ok=3    changed=2    unreachable=0    failed=0   

実際に実行する

Playbookを実行する準備ができました。 早速実行してみましょう。

$ sudo ansible-playbook -i ./test_inventory ./docker_test.yml --diff

PLAY [test_servers] ********************************************************************************************************************

TASK [Gathering Facts] *****************************************************************************************************************
ok: [test-01]
ok: [test-02]

TASK [create directory] ****************************************************************************************************************
--- before
+++ after
@@ -1,4 +1,4 @@
 {
     "path": "/home/test/",
-    "state": "absent"
+    "state": "directory"
 }

changed: [test-02]
--- before
+++ after
@@ -1,4 +1,4 @@
 {
     "path": "/home/test/",
-    "state": "absent"
+    "state": "directory"
 }

changed: [test-01]

TASK [create file] *********************************************************************************************************************
--- before
+++ after
@@ -1,4 +1,4 @@
 {
     "path": "/home/test/test.txt",
-    "state": "absent"
+    "state": "touch"
 }

changed: [test-01]
--- before
+++ after
@@ -1,4 +1,4 @@
 {
     "path": "/home/test/test.txt",
-    "state": "absent"
+    "state": "touch"
 }

changed: [test-02]

PLAY RECAP *****************************************************************************************************************************
test-01                    : ok=3    changed=2    unreachable=0    failed=0   
test-02                    : ok=3    changed=2    unreachable=0    failed=0   

問題なく実行できました。

ファイルが存在することを確認する

$ sudo docker attach test-02
[root@220b31f3c7c0 /]# 
[root@220b31f3c7c0 /]# 
[root@220b31f3c7c0 /]# cd /home/test/
[root@220b31f3c7c0 test]# ls -ltr
total 0
-rw-r--r--. 1 root root 0 Dec 31 09:58 test.txt

test.txtファイルが存在していることが確認できます。

おわりに

最後までお付き合いいただきありがとうございます。 Ansibleは様々な環境にたいして操作をすることが可能な柔軟性を兼ね備えています。 いろいろなことがあった2017年。 2018年は、Ansibleをもっと活用してみませんか?

ご意見、ご感想など、コメント欄やTwitterでリプライいただければ励みになります! 2018年も、ひよこ大佐をよろしくお願いいたします!

それでは、良いお年をお迎えください!

ツイッターで転職したいと呟いたらバズった話

これは、「転職 Advent Calendar 2017」24日目の記事です。 クリスマス・イブ、いかがお過ごしでしょうか。このたび初めてAdvent Calendarの企画に参加しました、ひよこ大佐です。

11月末、私はふとこんなツイートをしました。

するとあれよあれよという間に大量のいいねやリプライをいただき、いわゆる「バズった」状態に。

Togetterにもまとめられ、気がついたら記事にもなっていました。この件からフォロワーさんが一気に増えたので、印象に残っている方もいるかもしれません。

今回の記事では、自分の転職経験やプロフィールについてご紹介し、今後のエンジニアとしての転職のあり方や必要とされていくであろうスキルについて考えていければと思います。

プロフィール

私自身はもともとコンピューターサイエンスを専攻していたわけでもない、文系の学生でした。ただ、小さい頃から機械や電子機器を見たり触れたりするのは大好きでした。家族は別段エンジニアだったりするわけではないのですが、もともとオタクっぽい気質があったのかもしれません。

中学生時代に富士通のノートPCをゲームやりたさに、親にねだって買ってもらいました。シングルコアのCeleronと256MBのメモリしかないWindows XPのマシンです。それでも当時は20万円は下らない、高額な買い物でした。 最初はWindowsでネットゲームやブラウジングなどをやっているだけの「高機能なゲーム機」ぐらいの感覚でしたが、ある日ふとLinuxの存在を知り、興味を持ちました。「世の中のOSはWindowsだけではない」ということを初めて知った瞬間です。 知的好奇心を抑えられない私は、Vine Linuxをインストールしました。そこにあったのは、完全に未知の世界です。それまで「自分はパソコンがわかる」と思いこんでいた中学生に襲いかかったのは、黒いTerminal、全く分からないbashのコマンド。そして消えてしまったWindowsでした。慌ててLinuxの本を図書館で借りました。

どうやらこの黒い画面にコマンドを打ちこむといろいろできるらしい。Linuxというのは狭義にはカーネルのことを指し、そのカーネルは「C言語」というので書かれているらしい。 私はLinuxについての基礎と、C言語を勉強することにしました。 非常に複雑怪奇な代物に思えましたが、サンプルコードを動かしてみると非常にワクワクするのです。実際に作ったのは本当に簡単なコードばかりでしたが、変数やポインタ、関数、メモリやCPUの概要、APIの概念について、多くの基礎的な知識を学ぶことができました。今となっては忘れてしまったもののほうが多いですが、無駄ではなかったと思います。 しかし、僕自身は「自分はプログラミングも全くわからないし、とてもじゃないがプログラマとしてやっていける域にない」と考えていました。プログラミングは楽しい。だけど数学も苦手で基礎知識もない僕はプログラミングを仕事としてできるレベルまで昇華できるはずがない。それよりも別のことを学ぼう。そう考えるようになっていきました。

高校時代にはHTMLやCSSを勉強したり、Fedoraの翻訳プロジェクトに参加したり、Ubuntuを使ってみたりしていましたが、高校でより数学が嫌いになった私に「エンジニアになる」という選択肢はありませんでした。 それよりも元々好きだった文学の世界に没頭する日々が続きました。

文系の大学に進学し就活を始めた当初は、製造業の営業などを志望しており、ITエンジニアになろうとは全く考えていませんでした。数学もできない、理系でもない自分がエンジニアになれるとは到底考えられなかったのです。しかし結果はことごとく不発に終わり、60社以上受けた時点で内定はゼロでした。 当時私はアルバイトとしてWebメディアのテクニカルライターをしており、そこでライターとしてやっていこうとぼんやりと考えていました。ただライターの仕事は出来高で安定する仕事ではありませんでしたし、どこかまだ自分のなかでこの先の生き方について納得しきれないものがあったのだと思います。結果が出ずとも就活自体はずっと続けていました。

ある時、ハローワークが主催する新卒向け合同面接会で、「未経験でもITエンジニアになれる!英語も使える!」という会社が目に止まりました。インフラのSES事業と開発を手がける小さな会社でした。その時は英語は話せるという域には達していないレベルでしたが、話を聞くうちに「この会社、良さそう!」と思い、中学・高校時代のLinuxに触れていたエピソードを話したところ、まさかの即日内定が出ました。私はこの時、SESという事業がどのようなものなのか、全く理解していなかったのです。ただ、そこには諦めていたエンジニアへの憧れがありました。 入社時にCCNAとLPIC1を取り、晴れてエンジニアとしてデビューすることになったのです。

1社目

最初に配属されたのは、大手企業の海外の事務所を含めたネットワーク監視やヘルプデスクを行っている現場でした。 アラートや問い合わせを受け、通信キャリアやベンダーと原因を調査し解決するのが主な業務です。ときおり翻訳なんかもやっていました。

海外ベンダーへの問い合わせ、お客様への報告は電話もメールも全て英語でした。当時そこまで英語力のなかった私は死に物狂いで英語を勉強し、ベンダー窓口のインド人の訛りのある英語に苦労しながらも、半年も経つと英語でのやり取りはほとんど問題なくなっていました。 ただ、この現場に所属した1年半ほどのあいだ、技術的なことはほとんどできていませんでした。深いトラブルシュートなどをするわけでもなく、ただひたすらアラートを元に電話をし、エスカレーションしつづける日々が続きました。 自分自身は自力でトラブルシュートをしたうえで、それでも解決しないことについてはエスカレーションをするように毎日意識していましたが、周りは別に技術的なことをしたいという意識もなく、ただメールを右から左に流すだけ。そんな環境に嫌気がさし、私は転属を上長に願い出ていました。

1社目(転属後)

転属が決まったのは入社して1年半が経った時でした。SI事業を本格的に始動させるために人が足りず、技術的な基礎があり学ぶ意欲がある人材を投入してSIチームを発足させる動きがあり、私に声がかかりました。 そこで初めてSIでの構築という経験を積みました。チームといいつつ3名ほどの小さなチームでしたが、学ぶことは多々ありました。そこでサーバー、ネットワーク問わずインフラエンジニアとして様々な環境での構築経験を積むことができたのは貴重だったと思います。 ただ、少人数で業務を回しているうえ、自分のスキルに見合わない内容を営業が受注してしまったりしていたので、業務はホワイトとは言い難く、案件によっては本当に辛いものもありました。給与も低く、いい環境とは言いづらいですが、それでも割と楽しく業務をこなしていたと思います。

社長との対立

SIチームに配属されてから1年とちょっと。ある日社内でパラメータシートを書いていた私は、社長に呼び出されました。 内容は、「エンジニアとしてではなく、英語がわかる要員として製造業の現場に行ってほしい」というもの。私はその申し出を断りましたが、社長は「これは社長命令だから」と取り合ってもらえませんでした。 私自身、インフラエンジニアとして積んできた経験を投げ出したくはありませんでしたし、その場で辞める旨を伝え、会社を退職しました。 SIでやってきたことはどれも勉強になりましたが、SI事業そのもの、ひいては私の成果は社内では全く評価されていなかったのです。それ以外にもいろいろな要因はありましたが、このままこの会社に居続けることはできない、と感じました。

初の転職を経験する

転職の経験がない私は、とりあえずエンジニア向けの転職サイトに登録しました。 そこでふと見つけた今の会社に、半ば何も考えずに入社しました。 私としてはSIでの構築ができれば楽しかったので、同じようなSIerへの派遣を行っている会社がいいと考えていました。 そういう意味では、現在の会社は私の理想とぴったりでした。そこで提示されたのは300万円台の給与。 前の会社ではもっと少なかったため、私は特に何も思うことなくその提示額を呑みました。

現職で

現職では前と同様に設計・構築を中心に担当していますが、設計範囲や規模がより大規模になりました。 インフラエンジニアとして前職よりももっと幅広く、かつ正確な知識を求められるため、さらにステップアップにするには最適な環境だと感じています。 ただ、SESの会社の正社員として働く意義は、完全に見失っていました。自社では帰属意識を求められますが、ただ人を送り込むだけの会社にどうすれば高い帰属意識を持てるのでしょうか。所属する同僚との人間関係に不満はありませんでしたが、周りのベンチャー外資系で働くエンジニアと交流するうちに「外の自由な世界はいいなあ」と、感じるようになっていきました。

そして、あのツイートをすることになります。

2回目の転職を決意したきっかけ

もともと転職については抵抗感はなかったものの、そこまで本気で転職を考えていたわけではありません。せいぜいLinkedInに登録して、いいオファーがないかなぁとメッセージをチェックする程度の、転職活動とも呼べない転職活動をしている状況でした。 現在のSIerでの業務は嫌いではありません。オンプレを中心に様々な環境に触れ、設計構築フェーズに関わるのは非常に勉強になりました。ただ、SESの会社に居続けること、SIer業界が本当に自分にとって最も適した環境とは思えませんでした。 旧態依然とした体制、最新技術への対応の遅さは、どんなに先鋭的になろうとしても企業文化として根付いてしまっています。また、資格をなにより重要視するSES業界の常識に疑問を抱いているのも事実です。 そういった中で、「もっと違う環境で働いてみたい」という思いは、ここ最近はずっと持ち続けていました。

現在の状況

外資系を中心に10社を超える方から直接ご連絡をいただき、そのうちとても興味を持った数社にこちらからご連絡させていただきました。 選考状況はまちまちですが、この機会に自分のスキルを発揮でき、それが評価される環境に身を置くことができればと思います。

エンジニアとしてどうしていくか

もともと私自身は「1つのスキル」に特化したエンジニアではありません。なので知識も中途半端で、器用貧乏なところがあると思っています。 しかし、私のエンジニアとしての理想像は「スキルの掛け算ができるエンジニア」です。 例えばある特定の技術分野に秀でたエンジニアが10わかることについて、6ぐらいまでしかわからなくても、多少なりともわかる分野が沢山あれば、どのような状況においても調べたり自分の手を動かしてやってみることで対応できる。それぞれのスキルが掛け算のようにお互いの知識を補完しあい、そのなかで秀でたものが出てくればそれを中心に全体的に伸ばせばよいという考え方です。

人によって「優秀なエンジニア」の定義は様々だと思います。その中で自分が少しでも近づくためにどうすればいいのか。 インフラの世界も、クラウドの台頭などによって大きく様変わりしようとしています。そんな中で、幅広いレンジのスキルとしっかりとした基礎知識があれば、柔軟にその時の状況に適応していくことができます。

エンジニアとして若手から中堅へ成長するなかで、しっかりとした基礎知識の重要性を痛感しています。 今後エンジニアを志す学生や若手の方々は、ぜひしっかりとした基礎知識をつけて、そのうえで食わず嫌いをせずに好奇心のおもむくままいろいろ触れていってほしいと思います。

今後のITエンジニアの転職

現在売り手市場と言われる転職市場ですが、我々ITエンジニアにとってはまたとないチャンスだと考えています。 もともとIT業界は転職に対してネガティブな業界ではありません。現在の状況を改善したいと考えているエンジニアにとって、もっと気軽に転職という選択肢を選べる風潮になっていくと思いますし、そうあるべきだと思います。

長々とお付き合いいただき、ありがとうございました。この記事が皆様の転職や、ITエンジニアとして更なる飛躍のための一助となれば幸いです。

Fedora Server 26でdnf update/installするとハングアップする問題

F26でdnf install するとシステムがフリーズするbug

題記の通りのバグに遭遇しましたが、Bugzillaを読みつつ復旧できたので共有。 フリーズするとCtrl + Cでの中断も出来なくなり、Pingも応答しなくなります。

環境

Fedora Server 26 on ESXi 6.5

対処手順

下記Bugzillaを参照 https://bugzilla.redhat.com/show_bug.cgi?id=1214538

メタデータの削除と、LIBREPO_DEBUGを1に。

#dnf clean metadata
#set LIBREPO_DEBUG=1

これで一旦試してみる。

# dnf install ansible
Fedora 26 - x86_64 - Updates                    3.8 MB/s |  18 MB     00:04
Fedora 26 - x86_64                              796 kB/s |  53 MB     01:08
メタデータの期限切れの確認は、0:00:12 時間前の 2017年12月22日 19時56分15秒 に実 施しました。
依存性が解決されました。
================================================================================
 パッケージ            アーキテクチャ
                               バージョン                        リポジトリ
                                                                          サイズ
================================================================================
インストール:
 ansible               noarch  2.4.1.0-2.fc26                    updates  7.6 M
(中略)
総ダウンロードサイズ: 26 M
パッケージ展開後のサイズ: 113 M
これでいいですか? [y/N]: y

行けそうな気がするが、下記エラーが。

エラー: rpmdb: BDB0004 fop_read_meta: /var/lib/rpm/Supplementname: unexpected file type or format
エラー: cannot open Supplementname index using db5 - Invalid argument (22)
エラー: rpmdb: BDB0004 fop_read_meta: /var/lib/rpm/Enhancename: unexpected file type or format
エラー: cannot open Enhancename index using db5 - Invalid argument (22)

rpmのDBがエラーを吐いているのでリビルドする。

# rpm -vv --rebuilddb

これでめでたく解消。

VMFSの最小データストア領域サイズは1.3GB

まぁ公式ドキュメントにしっかり明記されてるんですが、1.3GB未満のデータストアは作れないよというお話。

https://docs.vmware.com/jp/VMware-vSphere/6.5/com.vmware.vsphere.storage.doc/GUID-D57FEF5D-75F1-433D-B337-E760732282FC.html

エクステントの最小サイズは 1.3 GB です。デフォルトでは、ストレージ デバイスの空き容量がすべて使用可能です。

よほどのことがないとこの制限を意識することはないですが、よほどなことはたまに起きたりすることなのです。