Dockerでnginxサーバー立ててみた。あとDockerの使い方とか。
Dockerすごい面白そうです。 最近ハッカソンに行ったりして、プロダクション環境へのデプロイ周りですごいはまった。特にお金もない自分は1つのサーバーの中にいろいろとアプリケーションをデプロイしちゃっている訳ですが、もうごちゃごちゃになって触りたくなくなりそう...。新しくサーバーをデプロイしたいけども、既存のサービスまで影響が及ぶ危険性もあり、めんどくさいなー。あと、あとできっと破棄するだろうけど、もとに戻すこともかなりめんどくさいし、そんなことやりたくないしなー。もっとアプリケーション毎に気軽に(そしてお安く)デプロイ出来ればいいのになー。
と思っていた訳ですが、最近Dockerというものを目にしまして。
本番環境のBlue-Green Deploymentの仕組みのプロトタイプを作っていた - $shibayu36->blog;
開発合宿でDockerとMesosを使っていい感じにリソース提供とデプロイするやつを作ってた - wtatsuru's blog
Docker + Mesos + Marathon + Graphite + Fluentd + Sensuを組み合わせたデプロイ管理ツールの話 - ゆううきブログ
主にここらへんのお話を見て(こういうハッカソンおもしろそうすぎる。参加してみたい)これ使えば問題解決できるんじゃね!?と思った訳です。っという訳で触ってみることにしました。
使い方まとめて、Nginx動かすDockerfileを作ってみました。
ソースはこっちにあげておきます。
そもそもDockerとは?
公式ページ Docker is an open-source project to easily create lightweight, portable, self-sufficient containers from any application.
カンタンに言うとLinuxのなかでLinuxを動かすやつ。(通常のVMよりもめっちゃ軽い・ポータビリティ◯) ポータブルな環境構築ができるようになるアプリケーション。
インストール方法 on Mac
これだけ、かんたん!
git clone https://github.com/dotcloud/docker.git cd docker vagrant up --provider virtualbox
使い方
cd docker vagrant ssh docker Usage: docker [OPTIONS] COMMAND [arg...] -H=[unix:///var/run/docker.sock]: tcp://host:port to bind/connect to or unix://path/to/socket to use A self-sufficient runtime for linux containers. Commands: attach Attach to a running container build Build a container from a Dockerfile commit Create a new image from a container's changes cp Copy files/folders from the containers filesystem to the host path diff Inspect changes on a container's filesystem events Get real time events from the server
単発コマンドの実行方法
とりあえず、Dockerを動かして見る。起動するコンテナには、使い慣れているCentOSを選択しておく。
docker run centos /bin/echo "hello world"
でリモートリポジトリからbaseイメージをpullしてきてコンテナを起動、/bin/echo "hello world"をその中で実行する。その後、コンテナを終了する。
コンテナの中に入って操作する
docker run -i -t centos /bin/bash
-i -tについては以下の設定のよう
-t=false: Allocate a pseudo-tty -i=false: Keep stdin open even if not attached
コンテナから出るときには
exit
バックグラウンドでコンテナを起動する
vagrant@precise64:~/docker$ docker run -i -t -d centos /bin/ping -i 5 google.com 13554990c22fd701490a3e29a52cee602e11d56cd2c9bc81d3890393cb45f7ec vagrant@precise64:~/docker$ docker ps CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES 13554990c22f centos:6.4 /bin/ping -i 5 googl 8 seconds ago Up 8 seconds mad_lovelace
-dオプションについては以下のよう -d=false: Detached mode: Run container in the background, print new container id
コンテナの中の状態を覗いて見る。
docker logs <ID>
vagrant@precise64:~/docker$ docker logs 1355 PING google.com (173.194.126.134) 56(84) bytes of data. 64 bytes from 173.194.126.134: icmp_seq=1 ttl=61 time=21.1 ms 64 bytes from 173.194.126.134: icmp_seq=2 ttl=61 time=19.9 ms 64 bytes from 173.194.126.134: icmp_seq=3 ttl=61 time=22.1 ms 64 bytes from 173.194.126.134: icmp_seq=4 ttl=61 time=22.0 ms 64 bytes from 173.194.126.134: icmp_seq=5 ttl=61 time=23.2 ms 64 bytes from 173.194.126.134: icmp_seq=6 ttl=61 time=21.1 ms 64 bytes from 173.194.126.134: icmp_seq=7 ttl=61 time=23.7 ms 64 bytes from 173.194.126.134: icmp_seq=8 ttl=61 time=22.6 ms 64 bytes from 173.194.126.134: icmp_seq=9 ttl=61 time=22.1 ms 64 bytes from 173.194.126.134: icmp_seq=10 ttl=61 time=22.4 ms 64 bytes from 173.194.126.134: icmp_seq=11 ttl=61 time=20.2 ms 64 bytes from 173.194.126.134: icmp_seq=12 ttl=61 time=25.8 ms
実行中のコンテナ一覧を取得する
docker ps
vagrant@precise64:~/docker$ docker ps CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES b16cf59771cb centos:6.4 /bin/ping -i 5 googl 4 seconds ago Up 3 seconds trusting_torvalds
コンテナにアタッチしてみる
vagrant@precise64:~/docker$ docker attach 1355 64 bytes from 173.194.126.134: icmp_seq=57 ttl=61 time=24.1 ms 64 bytes from 173.194.126.134: icmp_seq=58 ttl=61 time=24.1 ms 64 bytes from 173.194.126.134: icmp_seq=59 ttl=61 time=23.5 ms * *
コンテナをデタッチする
アタッチ中の端末は Ctrl-p Ctrl-q でデタッチできる。(このとき use of closed network connection っていうエラーが出る場合 Ctrl-c で抜けるしかないっぽい。バグレポートは上がっているので、じきに直ると思う。)
なるほど、そんなバグも発生する可能性があるみたいですね。
生成したコンテナのプロセスを消す
vagrant@precise64:~/docker$ docker kill 1355 1355
コンテナ一覧を表示する。
docker ps -a -notrunc
実行されたコンテナは全て残っているようです -aコマンドを付けることで、実行完了したコンテナを表示。 -notrunc で詳細情報まで表示。
vagrant@precise64:~/docker$ docker ps -a -notrunc CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES 13554990c22fd701490a3e29a52cee602e11d56cd2c9bc81d3890393cb45f7ec centos:6.4 /bin/ping -i 5 google.com 7 minutes ago Exit 137 mad_lovelace 2ef126977876e9816525b4875a52267f23d9ec58604e849ddbe77c76ab3f4290 centos:6.4 /bin/bash 9 minutes ago Exit 0 ecstatic_pike 801aaf7f07a27cc2d8cc43a44025691a435d7810b7c4224abe81e57492ee10ad centos:6.4 /bin/bash 13 minutes ago Exit 0 compassionate_pasteur 4816df705e27ffda96f42578600f996393b8c1633a8b7b714bf38e58263f7562 centos:6.4 bash 22 minutes ago Exit 127 insane_babbage 7eb03f1209869722cf384df3f0ee3a2ccae37e5f5e279a11bcc58796231b1288 centos:6.4 biash 22 minutes ago Exit 127
コンテナの実体は/var/lib/docker/containers/
以下にID名で保存されているようです。
コンテナを消去する
docker rm <ID>
vagrant@precise64:~/docker$ docker rm 1355 1355
コンテナをイメージとして保存する
docker commit <ID> <USERNAME/CONTAINER_NAME>
作業領域として今まで使用していたコンテナをイメージとして保存する。あとから使い回せるようになる。ユーザー名/名称 が一般的なようです。
vagrant@precise64:~/docker$ docker commit b16 yss44/ping 2cea6b12c43f1ad1f57f47ef0cc9fde6341a87b0fb7afac4f5b2fa95ec593c40
イメージ一覧を取得する
docker images
vagrant@precise64:~/docker$ docker images REPOSITORY TAG IMAGE ID CREATED VIRTUAL SIZE yss44/ping latest 2cea6b12c43f 8 seconds ago 300.6 MB centos 6.4 539c0211cd76 8 months ago 300.6 MB centos latest 539c0211cd76 8 months ago 300.6 MB
イメージは複数の名称をタグ付けできるようになっており、base:latest, base:ubuntu-12.10 といった形で異なるイメージを呼び出せるようになっている。省略時は base:latest と同じ。 なるほど
イメージをレポジトリから検索する
docker search
vagrant@precise64:~/docker$ docker search base NAME DESCRIPTION STARS OFFICIAL TRUSTED base/devel Archlinux 2013.10.01 adds base-devel to ba... 3 base/arch Archlinux 2013.10.01 Minimal arch installa... 8 base DEPRECATED (use "ubuntu"): Another general... 2 modolo/base Base para outros projetos 0 zumbrunnen/base Base image with supervisord 0 [OK]
pull してくるイメージは https://index.docker.io/ から情報を持ってくる。コマンドラインで検索したい場合は search コマンドを利用する。
ローカルのイメージを削除する
docker rmi <IMAGEID>
vagrant@precise64:~/docker$ docker rmi 2ce Untagged: 2cea6b12c43f1ad1f57f47ef0cc9fde6341a87b0fb7afac4f5b2fa95ec593c40 Deleted: 2cea6b12c43f1ad1f57f47ef0cc9fde6341a87b0fb7afac4f5b2fa95ec593c40
イメージの詳細情報を取得する
docker inspect <IMAGEID>
vagrant@precise64:~/docker$ docker inspect 539 [{ "id": "539c0211cd76cdeaedbecf9f023ef774612e331137ce7ebe4ae1b61088e7edbe", "comment": "Imported from -", "created": "2013-04-01T01:20:58.331937915-07:00", "container_config": { "Hostname": "", "Domainname": "", "User": "",
ネットワーク
公式サイトのドキュメントを見て設定してみた。
docker run -p <PORT>
# Bind port 4444 of this container, and tell netcat to listen on it JOB=$(sudo docker run -d -p 4444 ubuntu:12.10 /bin/nc -l 4444) # Which public port is NATed to my container? PORT=$(sudo docker port $JOB 4444 | awk -F: '{ print $2 }') # Connect to the public port echo hello world | nc 127.0.0.1 $PORT # Verify that the network connection worked echo "Daemon received: $(sudo docker logs $JOB)"
Dockerfile使う方法
Dockerfileからコンテナをビルドする
コマンドラインから指定してコンテナを生成するだけでなく、設定ファイルからイメージの作成も可能
cd docker vim Dockerfile
FROM centos RUN /bin/echo hi
docker build .
を行うことで、docker run centos /bin/echo hi
と同じことが出来る
vagrant@precise64:~/docker$ docker build . Uploading context 10.24 kB Step 1 : FROM centos ---> 539c0211cd76 Step 2 : RUN /bin/echo hi ---> Running in ee829ee9a714 hi ---> f910e14e1f39 Successfully built f910e14e1f39
使用出来るコマンド
FROM
RUNとCMDとの違い
FROM centos RUN /bin/echo run | tee /tmp/run.log CMD /bin/echo cmd | tee /tmp/cmd.log
ビルドの実行
vagrant@precise64:~/docker$ docker build . Uploading context 10.24 kB Step 1 : FROM centos ---> 539c0211cd76 Step 2 : RUN /bin/echo run | tee /tmp/run.log ---> Running in a90496e48805 run ---> e67b0f5a30b4 Step 3 : CMD /bin/echo cmd | tee /tmp/cmd.log ---> Running in 2fa46bcdf5f9 ---> bbc2b6efbb20 Successfully built bbc2b6efbb20
RUN,CMDの実行結果の確認
vagrant@precise64:~/docker$ docker run bbc /bin/ls /tmp run.log
=> cmdがまだ実行されていない
vagrant@precise64:~/docker$ docker run bbc cmd
=> cmdが実行される
- CMDはコンテナの実行時に実行される
- RUNはコンテナのビルド時に実行される
生成されたコンテナの詳細
vagrant@precise64:~/docker$ docker inspect bbc [{ "id": "bbc2b6efbb20237d3cef264932d9eecd1ea9ee56ba32c61139a212c497b7629e", "parent": "e67b0f5a30b4698e8b72971c7005f7bf8977e6fc0b3d70463d10a34402f78d95", "created": "2013-12-26T23:27:46.019628733Z", "container": "2fa46bcdf5f99e2d6c4af4c4c07bdba3ad0e48cadf06e3a391dcd32c6635c52d", "container_config": { "Hostname": "a90496e48805", "Domainname": "", "User": "", "Memory": 0, "MemorySwap": 0, "CpuShares": 0, "AttachStdin": false, "AttachStdout": false, "AttachStderr": false, "PortSpecs": null, "ExposedPorts": {}, "Tty": false, "OpenStdin": false, "StdinOnce": false, "Env": [ "HOME=/", "PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin" ], "Cmd": [ "/bin/sh", "-c", "#(nop) CMD [/bin/sh -c /bin/echo cmd | tee /tmp/cmd.log]" ], "Dns": null, "Image": "e67b0f5a30b4698e8b72971c7005f7bf8977e6fc0b3d70463d10a34402f78d95", "Volumes": {}, "VolumesFrom": "", "WorkingDir": "", "Entrypoint": null, "NetworkDisabled": false }, "docker_version": "0.7.2", "config": { "Hostname": "a90496e48805", "Domainname": "", "User": "", "Memory": 0, "MemorySwap": 0, "CpuShares": 0, "AttachStdin": false, "AttachStdout": false, "AttachStderr": false, "PortSpecs": null, "ExposedPorts": {}, "Tty": false, "OpenStdin": false, "StdinOnce": false, "Env": [ "HOME=/", "PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin" ], "Cmd": [ "/bin/sh", "-c", "/bin/echo cmd | tee /tmp/cmd.log" ], "Dns": null, "Image": "e67b0f5a30b4698e8b72971c7005f7bf8977e6fc0b3d70463d10a34402f78d95", "Volumes": {}, "VolumesFrom": "", "WorkingDir": "", "Entrypoint": null, "NetworkDisabled": false }, "architecture": "x86_64", "Size": 0 }]
Memcached入りコンテナを作って見る
FROM ubuntu RUN echo "deb http://archive.ubuntu.com/ubuntu precise main universe" > /etc/apt/sources.list RUN apt-get update RUN apt-get install -y memcached
docker build . docker run -t -i 3b8 /bin/bash memcached > can't run as root without the -u switch
ホストからコンテナのMemcachedにアクセスする
ソースは公式から
# Memcached # # VERSION 42 # use the ubuntu base image provided by dotCloud FROM ubuntu MAINTAINER Victor Coisne [email protected] # make sure the package repository is up to date RUN echo "deb http://archive.ubuntu.com/ubuntu precise main universe" > /etc/apt/sources.list RUN apt-get update # install memcached RUN apt-get install -y memcached # Launch memcached when launching the container ENTRYPOINT ["memcached"] # run memcached as the daemon user USER daemon # expose memc
実際にコンテナをビルドして起動して見る
vagrant@precise64:~/docker$ docker build . vagrant@precise64:~/docker$ docker run -d -p 11211 4fd c976600f5345be6e26041aeaaaa763767e8c5011bec6c0539fc879b83bd2be56
起動されたコンテナの状態を確認
vagrant@precise64:~/docker$ docker ps CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES c976600f5345 4fd2c196ce20 memcached 55 seconds ago Up 54 seconds 0.0.0.0:49160->11211/tcp sleepy_shockley vagrant@precise64:~/docker$ docker port c97 11211 0.0.0.0:49160
どうやら、localhost:49160にポートフォワーディングされているようなので、localhost:49160にアクセスする
Memcachedにアクセスしてみる
import memcache ip = 'localhost' port = 49160 mc = memcache.Client(["{0}:{1}".format(ip, port)], debug=0) mc.set("MDM", "Guillaume J. C.") value = mc.get("MDM") print value
vagrant@precise64:~/docker$ python test.py Guillaume J. C.
-- ホスト側でのポートを指定して起動も出来るみたい
vagrant@precise64:~/docker$ docker run -d -p 11211:11211 4fd c976600f5345be6e26041aeaaaa763767e8c5011bec6c0539fc879b83bd2be56
これでホスト側からは11211でアクセスできる
DockerでNginxサーバー
Dockerfile
# Memcached # # VERSION 42 # use the ubuntu base image provided by dotCloud FROM centos MAINTAINER yoshiso RUN yum -y update # make sure the package repository is up to date ADD nginx.repo /etc/yum.repos.d/nginx.repo RUN chmod 0644 /etc/yum.repos.d/nginx.repo # install memcached RUN yum install -y nginx ADD nginx.conf /etc/nginx/nginx.conf Add default.conf /etc/nginx/conf.d/default.conf # Nginx public directory ADD src /var/www # expose memcached port EXPOSE 80 CMD ["service","nginx","start"]
Dockerfileはこんなかんじ。 詳細の設定ファイルはここを参照
コンテナをビルドして見る
docker build -t yoshiso/nginx .
これで、コンテナのビルド完了。 最後に作成したNginxコンテナを起動する
docker run -d -p 80:80 .
ホストから確認のためにリクエストを送ってみる。
curl http://localhost:80 > Hello, Nginx!
無事起動していることを確認しました。