coreos-vagrantでDockerしてみてわかったこととかハマったこととか

ちょっとDocker試してみたいならCoreOSが簡単そうなのでやってみた。ホストはWindows8

CoreOSの起動

> git clone https://github.com/coreos/coreos-vagrant/
> cd coreos-vagrant
> vagrant up

vagrant sshはWindowsでは使えないので、vagrant ssh-configの出力を~/.ssh/configに貼り付けて、ssh defaultする。sshは多分Git for Windowsについてきたのを使ってます。

そうそう。この時点でVAIO ProのBIOSの設定の問題でvagrant upしなかったんだった。そういう時はVagrantfileでgui = trueしましょう。

Vagrant.configure("2") do |config|
  ...
  config.vm.provider "virtualbox" do |v|
    v.gui = true
  end
end

Configuration - VirtualBox Provider - Vagrant Documentation

とりあえずDockerを動かす

Dockerfileに1行だけ書いてビルドしてみる。

core@localhost ~ $ cat Dockerfile
FROM ubuntu
core@localhost ~ $ docker build .
Uploading context 10240 bytes
Step 1 : FROM ubuntu
Pulling repository ubuntu
Pulling image (precise) from ubuntu, endpoint: https://cdn-registry-1.docker.io/Pulling image (quantal) from ubuntu, endpoint: https://cdn-registry-1.docker.io/ ---> 8dbd9e392a96MB/94.86 MB (100%)
Successfully built 8dbd9e392a96

ベースとなるイメージをダウンロードするので結構時間がかかる。これを動かす方法はよそを見てください。で、Dockerfileに1行追加して再度ビルド。

core@localhost ~ $ cat Dockerfile
FROM ubuntu

RUN apt-get update
core@localhost ~ $ docker build .
Uploading context 10240 bytes
Step 1 : FROM ubuntu
 ---> 8dbd9e392a96
Step 2 : RUN apt-get update
 ---> Running in 28931b426f0e
Ign http://archive.ubuntu.com precise InRelease
Hit http://archive.ubuntu.com precise Release.gpg
Hit http://archive.ubuntu.com precise Release
Hit http://archive.ubuntu.com precise/main amd64 Packages
Get:1 http://archive.ubuntu.com precise/main i386 Packages [1641 kB]
Get:2 http://archive.ubuntu.com precise/main TranslationIndex [3706 B]
Get:3 http://archive.ubuntu.com precise/main Translation-en [893 kB]
Fetched 2537 kB in 46s (54.6 kB/s)
Reading package lists...
 ---> 5ecf56680d71
Successfully built 5ecf56680d71

今度はイメージはもうあるのでダウンロードしないけど、apt-get updateに少々時間がかかる。さらにvimをインストールしてみよう。

core@localhost ~ $ cat Dockerfile
FROM ubuntu

RUN apt-get update
RUN apt-get install -y vim
core@localhost ~ $ docker build .
Uploading context 10240 bytes
Step 1 : FROM ubuntu
 ---> 8dbd9e392a96
Step 2 : RUN apt-get update
 ---> Using cache
 ---> 5ecf56680d71
Step 3 : RUN apt-get install -y vim
 ---> Running in 5319a6fcb1ed
Reading package lists...
Building dependency tree...
(中略)
update-alternatives: using /usr/bin/vim.basic to provide /usr/bin/editor (editor) in auto mode.
Processing triggers for libc-bin ...
ldconfig deferred processing now taking place
 ---> c4732c1418de
Successfully built c4732c1418de

ubuntuベースで、apt-get updateしたところまではもう出来てるから、それを再利用してvimのインストールだけをやっている。さらにgitをインストール。

core@localhost ~ $ cat Dockerfile
FROM ubuntu

RUN apt-get update
RUN apt-get install -y vim
RUN apt-get install -y git
core@localhost ~ $ docker build .
Uploading context 10240 bytes
Step 1 : FROM ubuntu
 ---> 8dbd9e392a96
Step 2 : RUN apt-get update
 ---> Using cache
 ---> 5ecf56680d71
Step 3 : RUN apt-get install -y vim
 ---> Using cache
 ---> c4732c1418de
Step 4 : RUN apt-get install -y git
 ---> Running in 3cb53352601d
Reading package lists...
Building dependency tree...
(以下略)

ちゃんとキャッシュが使われていて、gitのインストールだけ実行される。試しにvimとgitの順番を逆にしてみよう。

core@localhost ~ $ cat Dockerfile
FROM ubuntu

RUN apt-get update
RUN apt-get install -y git
RUN apt-get install -y vim
core@localhost ~ $ docker build .
Uploading context 10240 bytes
Step 1 : FROM ubuntu
 ---> 8dbd9e392a96
Step 2 : RUN apt-get update
 ---> Using cache
 ---> 5ecf56680d71
Step 3 : RUN apt-get install -y git
 ---> Running in 1ab66552b670
Reading package lists...
(中略)
 ---> a20b0df862d3
Step 4 : RUN apt-get install -y vim
 ---> Running in 747722a3d60f
Reading package lists...

これだと、apt-get updateは実行されないが、gitとvimのインストールはそれぞれ実行される。なるほど。この辺のイメージはドキュメントの用語のところの図がわかりやすいと思った。

f:id:iakio:20131128014249p:plain

今日apt-get updateした結果と明日apt-get updateした結果は違うかもしれないから、同じDockerfileを使ってビルドすれば同じイメージになるとは限らない(当たり前か)。キャッシュを使わずに0からビルドしたい場合はdocker build -no-cacheするかコンテナを消してしまえばよさそうだ。

chownでハマる

必要そうなものを入れつつ、Docker (土曜日に podcast します) - naoyaのはてなダイアリーみたいにsshできるようにしようと思ったのだけれどどうにも上手くいかない。どうもauthorized_keysが見えていないようだ。

FROM ubuntu

RUN apt-get update
RUN apt-get install -y ssh sudo
RUN apt-get install -y git tmux vim build-essential man

RUN useradd -m -s /bin/bash core
RUN mkdir /home/core/.ssh
RUN chmod 700 /home/core/.ssh
ADD authorized_keys /home/core/.ssh/
RUN chmod 600 /home/core/.ssh/authorized_keys
RUN chown -R core:core /home/core/.ssh

何が起きているのか把握するためにもうちょっと小さくしてみる。

core@localhost ~/chown-test $ cat Dockerfile
FROM ubuntu

RUN useradd -m -s /bin/bash core

RUN mkdir /home/core/.ssh
RUN chmod 700 /home/core/.ssh
RUN chown -R core:core /home/core/.ssh
core@localhost ~/chown-test $ docker build  -t chown-test .
(中略)
Successfully built 3b689d443f97
core@localhost ~/chown-test $ docker run -i -t chown-test /bin/bash
root@4d09c1303f3a:/# ls -la /home/core/.ssh/
total 8
drwx------ 2 core core 4096 Nov 27 12:05 .
drwxr-xr-x 5 core core 4096 Nov 27 12:05 ..
root@4d09c1303f3a:/# su - core
core@4d09c1303f3a:~$ ls -la /home/core/.ssh/
ls: cannot open directory /home/core/.ssh/: Permission denied
core@4d09c1303f3a:~$

一見chown出来ているように見えるのに、実際にはPermission deniedになってしまう。なんだかよくわからないんだけどこれが関係しているのか。

Permission denied for directories created automatically by Dockerfile ADD command · Issue #1295 · dotcloud/docker

mkdirせずに、いきなりファイルをADDしてからchmod, chownだと大丈夫なようだ。

ADD authorized_keys /home/core/.ssh/
RUN chmod 600 /home/core/.ssh/authorized_keys
RUN chown -R core:core /home/core/.ssh

あと、mkdirからchownまで1行で書いても大丈夫なようだ。上記のnaoyaさんのエントリもそうなってた。

RUN mkdir /home/core/.ssh && chmod 700 /home/core/.ssh && chown -R core:core /home/core/.ssh

その他

CoreOSのssh_configは、何でknown_hostsを~/.ssh/じゃなくて~/user/.ssh/に保存しようとするのか。https://github.com/coreos/init/blob/master/configs/ssh_config