最近Docker流行っていますね。いみゅーたぶるなんとかこんとかという素敵な仕組みも流行りはじめてるので流行にのってみたいと思います。
コンテナタイプの仮想化は大好物なので、こんなに流行ってるなら一回ぐらいは触ってみようと思い少し触ってみました。Dockerを使った面白い仕組みが結構公開されていて、中でもdokkuというのが個人的には興味があったので似たようなもの自前で考えてみました。
git pushしたらWebサービスが立ち上がるプラットフォーム
目指すゴールはHerokuのようなPaaSを自前で立ち上げることです。あんまり時間かけないで(2~3時間)でそれなりに動いたので、ちょっと紹介します。
■Dockerとは
あえて紹介しません。ググッてください。ざっくり特徴だけ・LXC/AUFS がテクノロジーのベースになってる
・コンテナの起動が早い(1秒以内で立ち上がるよ)
・コンテナを再起動すると元の状態に戻っている
・コンテナのリソース消費も軽微、オーバーヘッドが少ない
・コンテナのスナップショットが取れる
・コンテナイメージが小さい(コンテナタイプはファイルシステム丸ごとが多い)
・DockerはGoで書かれている
などなど
■検証環境
OS:CentOS6.5Docker:0.8.0
・Jenkinsがインストールされている
・Gitがインストールされている
■セットアップ
Dockerのセットアップは検索すればたくさん出てきます。おそらく今後も新しい良いセットアップ方法が紹介され続けるので、あえてここも紹介しません。
簡単です。合わせてDocker化したサーバにGitとJenkinsをインストールしておいてください。
■構成概念
こんな感じのことができたら良いなという事で①から解説していきます
■事前準備
①から解説しようと思っているのですが、事前に何個かやらなければいけないことがあるので簡単に解説します・Dockerのコンテナのイメージのダウンロード
・コンテナのイメージにgitの鍵を登録しdocker commitしておく
・Dockerサーバのgitアカウントにsudo権限を付与する
・sudoersのrequirettyにコメントアウトしておく
ざっくりこんなかんじでしょうか。
あとは、これに合わせて自分の起動させたWebアプリケーションに必要な言語のインストールなどが含まれます。とりあえず素のCentOSのイメージでインストールされているpythonで簡易Webサーバが立ち上がるところまでをゴールとしましょう。
簡易Webサーバは
python -m SimpleHTTPServerで立ち上げる想定です。
■[Jenkins]Gitリポジトリの作成を依頼する所を作る
jenkinsに1個ジョブを作ります。内容としてはシェルの実行とビルドのパラメータ化が指定されています。パラメータは
文字列
名前:Email
デフォルト:
説明:作成したリポジトリ情報の通知先を指定してください
シェルスクリプトの中身は以下のとおりです
1行目 HOSTIP : DockerサーバのIPを指定
2行目 DOCKERIP : Dockerサーバのdocker0というブリッジに設定されるIPを指定
3行目 IMAGE : Dockerコンテナを起動させる際のコンテナイメージ名を指定
docker commitなどして更新されたイメージ名を指定すると良い
13行目 git-hooksのスクリプトを作成。updateされた時に新しいコンテナを立ち上げるようにします。
20行目 git-hooksでよばれるスクリプトの中でコンテナを立ち上げる部分です。ここは少し分解して解説します
docker run -i -t -d -p $PORT:8080 centoscentosイメージのコンテナを起動
$PORTで指定たポートをコンテナの8080にDNATします
$PORTは親サーバがListenします。これは7行目で動的に決定させてます。
/bin/bash -c "git clone git@${DOCKERIP}:${BASEDIR}/${REPONAME}コンテナ起動時に最新のソースコードをgit cloneするようにしています
このコンテナには親サーバとパスワード無しでsshできるよう、事前に鍵が設置してある小細工がしてあります。dockerのコンテナイメージを更新する場合はdocker commitコマンドで作成できます。
source ${REPONAME}/RUNSCRIPT && eval \\\$RUN")
リポジトリの中にRUNSCRIPTというファイルとその中身をRUN="起動コマンド"を記述しておくことで、コンテナ起動時に自動でWebサーバが起動するようになります。
Herokuではこの辺りをProcfileというファイルで定義しています。
今回のSimpleHTTPServerを立ち上げるに当たってリポジトリに入れるべきRUNSCRIPTファイルの中身は以下の通りです。
とりあえず立ち上げ確認するだけならこのファイルにこの記述だけで良いですが、ちゃんとしたアプリケーションを立ち上げる場合は、リポジトリにアプリケーション一式を入れておく必要があります。
pythonモジュールをインストールする必要があるようなアプリケーションの場合はpip freezeでrequirements.txtを作成しておいてリポジトリに追加しておきましょう。そしてRUNSCRIPTファイルには以下のように記述するとコンテナ起動時にモジュールがインストールされ、アプリケーションが起動されます。このアプリはgunicornで起動するようなアプリケーションです。
23行目 ここからはスクリプト作成後の後処理です。権限付与したりしてます。
26行目以降 最後に作成したリポジトリの簡単な使い方の説明をメールで送ります。git remote addしてRUNSCRIPTファイルをリポジトリに追加して、git pushすればWebサーバが立ち上がります。
■Webサーバを立ち上げてみよう
Herokuではこの辺りをProcfileというファイルで定義しています。
今回のSimpleHTTPServerを立ち上げるに当たってリポジトリに入れるべきRUNSCRIPTファイルの中身は以下の通りです。
RUN="python -m SimpleHTTPServer 8080"
とりあえず立ち上げ確認するだけならこのファイルにこの記述だけで良いですが、ちゃんとしたアプリケーションを立ち上げる場合は、リポジトリにアプリケーション一式を入れておく必要があります。
pythonモジュールをインストールする必要があるようなアプリケーションの場合はpip freezeでrequirements.txtを作成しておいてリポジトリに追加しておきましょう。そしてRUNSCRIPTファイルには以下のように記述するとコンテナ起動時にモジュールがインストールされ、アプリケーションが起動されます。このアプリはgunicornで起動するようなアプリケーションです。
RUN="pip install -r requirements.txt && gunicorn hello:app -b 0.0.0.0:8080"
23行目 ここからはスクリプト作成後の後処理です。権限付与したりしてます。
26行目以降 最後に作成したリポジトリの簡単な使い方の説明をメールで送ります。git remote addしてRUNSCRIPTファイルをリポジトリに追加して、git pushすればWebサーバが立ち上がります。
■Webサーバを立ち上げてみよう
これで準備は終わったので、Webサーバを立ち上げてみましょう
1:git initして手元の環境でリポジトリを作成しておく。とりあえず中身は空でも良い。
2:Jenkinsのビルド画面で自分のEmailアドレスを入力してリポジトリを作成する
3:メールで届いたremoteリポジトリを追加しましょう
$ git remote add shanon-heroku git@192.168.3.203:/home/git/Shanon-Heroku-0001
4:RUNSCRIPTの中身は先に記述した通り以下の内容で作成してgit addしておきます
RUN="python -m SimpleHTTPServer 8080"
5:RUNSCRIPTを追加したらgit pushしましょう。
$ git push shanon-heroku master
6:ブラウザから立ち上がったWebサーバにアクセスしてみましょう(例:http://192.168.3.203:10001)
SimpleHTTPServerはファイルとディレクトリ一覧が表示されます。この画面が出れば成功です。ここまで表示されれば、あとは自分のアプリケーションを起動させるようにすることも自由自在のはずです。レッツいみゅーたぶる!
■とりあえずここまで、今後の展開について
ここまでできれば、1分ぐらいでクリアな検証環境立ち上がるので非常に便利で、強力な検証環境となるでしょう。アプリケーションごとにインストールされているモジュールや対応する言語ごとのコンテナイメージを用意しておくことで、様々なアプリケーションのビルドテストの実行環境となると思っています。
個人的にはこれをプロダクトの実行環境として固く作りに行きたいなと思っています。そのためにはたくさんやる事があるのですが、思いつくままに。
- HerokuのDynoでパワーアップできるようにスケーラブルな環境にする。複数のコンテナが立ち上がるようにする
- AWS上で全て完結させる
- 必ずロードバランサ(ELB)経由でアクセスするようにする
- リポジトリ作ったタイミングでELBが作成、dynoっぽいのを増やしたら追加する
- SSLが使えるようにする
- DBやストレージなどの永続データはコンテナとは別で用意する
- memcachedなどのキャッシュストレージもコンテナとは別に作ってあげる
- ログ収集に関する仕組みを構築する。Fluentd辺りがいまだと良さそう。
- コンテナのリソースの制限
- コンテナイメージの管理方法の構築
- 脆弱性対応・セキュリティパッチ
- 対応言語の充実化 等
- 障害対応プロセスの構築
等々やらないといけないことはたくさんあります。サービスの提供環境として使うには安定化させて、他にも様々な課題を解決しに行く必要がありますが、ちゃんと投資していけば良い感じになりそうです。
ちなみにですが、OpenVZのイメージもDockerのイメージとしてインポートする事ができました。
# cat image.tar.gz | docker import - openvz-image/v1
シャノンではOpenVZで環境を多く作っているので、既存の資産も活用できそうです。
Dockerを使えば色々と夢が広がりそうな雰囲気がしますね。いみゅーたぶるな技術はまだまだ話題に出始めたばかりなので、これから注目していきたいと思います。
それでは、レッツいみゅーたぶる!