2018/06/24

docker build で作成した image の layer を統合してサイズを縮小する

Docker で Dockerfile を書いて image を build すると、 RUN したコマンド毎に layer ができます。
結果、次回 build 時にコマンドを再実行せず、layer を cache として使って build 時間の短縮ができます。
また、build に失敗した場合でも、layer の id を指定して docker run して原因特定、などができます。
などなど、 RUN ごとに layer を作成することには多くのメリットがあります。
ですが、'毎回 layer を作成する == 全コマンド結果保存' ということでもあるので、image のサイズが大きくなります。

ビルドする側からすると、全 layer を保存しても問題無いと思います。
ですが、ダウンロードする側、特に何度もダウンロードが発生する場合はサイズが小さいほど良い。
例えば dockerhub にイメージを登録する場合がありますね。
image 作成過程の試行錯誤を dockerhub に登録して、ダウンロード容量が大きくなるとよろしくない。

と、いうことで、layer を統合してサイズを抑えてみます。


環境

  • OS: macOS Sierra 10.12.6
  • Docker for mac: 18.03.1-ce, build 9ee9f40


export/import

と、言ったはものの、同じ考えをしている方がまとめていました
export/import すれば layer を統合できます。
統合というか結果的に1 layer になる、という言い方が正確です。
具体的なコマンドはこんな感じ。
  • $ docker run -itd --name nya big-image
  • $ docker export nya > nya.tar
  • $ cat nya.tar | docker import - big-image-single:latest
今回試してみた image では、57 layers(13GB) -> 1 layer(9GB) になりました。
イメージの性質による思いますが、なかなか効果がありますね。
ちなみに、image save/image import をすると全 layer 含めて export するので縮小はできません。


参考

2018/06/17

Mac に fontforge を直接入れずに Docker を使って Ricty を作成する

私は普段 Terminal で作業する時、フォントは Ricty を使っています。
Ricty は Inconsolata と Migu 1M の合成フォントで、生成スクリプトが公開されています。
合成には fontforge を使うのですが、 brew で入れると結構な数の依存パッケージが入ります。
fontforge  は普段使いしていないので、おそらく Ricty の生成以外に使わない。
なので Mac に直接 fontforge を入れず、コンテナに入れて合成してみます。


環境

  • OS: macOS Sierra 10.12.6
  • Docker for mac: 18.03.1-ce, build 9ee9f40
    • Distribution: CentOS Linux release 7.4.1708 (Core)
    • fontforge: 20120731
  • Ricty: 4.1.1
    • Inconsolata: v2.001
    • Migu 1M: 20150712


mac 側の事前準備(ダウンロード)

事前にダウンロードが必要なのはフォント2つ。
具体的には Inconsolata と Migu 1M の .ttf ファイルです。
加えて、Ricty の生成スクリプト ricty_generator.sh もダウンロードしておきます。
Migu 1M は unzip して、とりあえず全ファイルを ~/Downloads へ mv。

最終的な ~/Downloads はこんな感じになりました。
$ ls Downloads
Inconsolata-Bold.ttf  Inconsolata-Regular.ttf  ipag00303  migu-1m-bold.ttf  migu-1m-regular.ttf  migu-README.txt  mplus-TESTFLIGHT-060  ricty_generator.sh


Docker に ~/Downloads を mount して合成

さて、合成に必要なファイル群は ~/Downloads に集まりました。
これを mount したコンテナを立ち上げて合成します。

具体的なコマンドはこんな感じ。run に渡す用のスクリプトを書いた方がスマートかも。
  • $ docker run -v ~/Downloads/:/root/fonts -it centos:7
    • # yum install -y fontforge
    • # cd /root/fonts
    • # chmod u+x ricty_generator.sh
    • # ./ricty_generator.sh -n 4.1.1 Inconsolata-{Regular,Bold}.ttf migu-1m-{regular,bold}.ttf
生成されたフォントにバージョン番号を付けておきたいので、 "-n 4.1.1" オプションを指定しておきます。
実行した結果、~/Downloads はこんな感じになりました。
$ ls ~/Downloads
Inconsolata-Bold.ttf Inconsolata-Regular.ttf Ricty4.1.1-Bold.ttf Ricty4.1.1-BoldOblique.ttf
Ricty4.1.1-Oblique.ttf Ricty4.1.1-Regular.ttf Ricty4.1.1Discord-Bold.ttf
Ricty4.1.1Discord-BoldOblique.ttf Ricty4.1.1Discord-Oblique.ttf Ricty4.1.1Discord-Regular.ttf
ipag00303 migu-1m-bold.ttf migu-1m-regular.ttf migu-README.txt mplus-TESTFLIGHT-060
ricty_generator.sh
きちんと生成されていますね。良し良し。

2018/06/10

Docker Universal Control Plane を CentOS7 で起動してみる

前回の記事では CentOS7 に Docker EE を入れました
さて、何故入れたかと言えば Docker Universal Control Plane(UCP) を使ってみたかったからです。

Unix User を dockergroup に所属させることで、複数のユーザが root でなくても docker を利用できます。
しかし、他人が run した container に attach 可能。場合によってはよろしくない。
何か解決策が無いかと調べたところ UCP を見付けました。

UCP には Permission Control があって、Full Control の権限をユーザに与えても
The user can view and edit volumes, networks, and images, They can create containers without any restriction, but can't see other users' containers.
とのことで、別のユーザのコンテナは見られない。
なので、root でない複数ユーザが、相互に干渉せず docker を使えそうです。


環境

  • OS: CentOS Linux release 7.4.1708 (Core)
  • Kernel: 3.10.0-693.5.2.el7.x86_64
  • Docker: docker-ee-17.03.0.ee.1-1.el7.centos.x86_64
  • Docker Universal Control Plane: 2.2.6


run UCP

公式の document に従って UCP のイメージを run します。
  • $ docker image pull docker/ucp:2.2.6
  • $ docker container run --rm -it --name ucp -v /var/run/docker.sock:/var/run/docker.sock docker/ucp:2.2.6 install --host-address 127.0.0.1 --interactive
    • --interactive が付いてるので適宜入力します
    • 具体的には Admin username や password とかですね
さてこれで起動……しません。
INFO[0000] Initializing a new swarm at 127.0.0.1     
FATA[0034] the following required ports are blocked on your host: 12385, 12376, 12383, 443, 12384, 12379, 12387, 12386, 12381, 12382, 2376, 12380.  Check your firewall settings 
と言われました。おお、結構な数の port 使うな。

ということで firewall に穴を開けます。
  • # for i in 12376 4789 12386 2376 443 12381 12380 12382 12383 12384 12385 12379 12387 ; firewall-cmd --add-port=$i/tcp --permanent
  • # firewall-cmd --reload
くらいかな。

そして再度 run してみる。今度は
FATA[0031] The following required ports are already in use on your host - 2377.  You may specify an alternative port number to 2377 with the --swarm-port argument.
と言われた。あれ。何が 2377 使ってるんだ?
  • $ netstat -lntp
すると確かに 2377 が listen になってる。 process name は dockerd か。

結論から言うと、一回目で起動した swarm が生きてたのが原因でした。なので
  • $ docker swarm leave --force
して抜ける。さて三度目のトライ。コマンドは変わらず
  • $ docker run -it --rm --name ucp -v /var/run/docker.sock:/var/run/docker.sock docker/ucp:2.2.6 install --interactive
で実行します。お、起動したっぽいですね。三度目の正直。
INFO[0007] Generating UCP Client Root CA
INFO[0007] Deploying UCP Service
INFO[0035] Installation completed on raven (node abcdefghijklmnopqrstuvwxy)
...
INFO[0035] Login to UCP at https://127.0.0.1:443
https//127.0.0.1 にアクセスすると UCP の画面が出てきました。ログインも可能。良し良し。


参考

2018/06/03

Docker EE を CentOS 7 に install する

Enterprise Edition の Docker を CentOS 7 に入れてみたのでそのメモ


環境

  • OS: CentOS Linux release 7.4.1708 (Core)
  • Kernel: 3.10.0-693.5.2.el7.x86_64
  • Docker: docker-ee-17.03.0.ee.1-1.el7.centos.x86_64


yum-config-manager --add-repo

まずは公式のドキュメントに従います。
Enterprise Edition の Docker は無料では使えないので、 subscription を買う必要があります。
なのですが、一ヶ月無料お試しもできるので、s

trial が始まるとユーザアカウント固有の URL が貰えます。
  • $ export DOCKERURL="<DOCKER-EE-URL>"
のところですね。ちなみに具体的なURL は
  • $ export DOCKERURL='https://storebits.docker.com/ee/centos/<uuid>'
でした。たぶん uuid は user ごとに違いそうなのでここには書きません。

DOCKERURL も分かったので、後は公式ドキュメント指示通りに続けます。
  • $ sudo -E sh -c 'echo "$DOCKERURL/rhel" > /etc/yum/vars/dockerurl'
  • $ sudo yum install -y yum-utils device-mapper-persistent-data lvm2
  • $ sudo -E yum-config-manager --add-repo "$DOCKERURL/rhel/docker-ee.repo"
  • $ sudo yum -y install docker-ee
でインストール……されないですね。
[Errno 14] curl#6 - "Could not resolve host: storebits.docker.com; Unknown error"
と言ってきますが、 dig では storebits.docker.com は返ってくる。謎。


DOCKERURL

結論から言うと、 DOCKERURL が間違っていました。
RHEL のドキュメントの DOCKERURL は
  • $ sudo -E yum-config-manager --add-repo "$DOCKERURL/rhel/docker-ee.repo"
ですが、store.docker.com から提供された URL は
  • https://storebits.docker.com/ee/centos/<uuid>
なので、どうも帳尻が合っていない。
いろいろ試した結果、 CentOS 用のキュメントは RHEL とは別にありました。
おお、そこまで区別してるのか。 sensitive だ。

ということで CentOS 用のドキュメントに従って
  • $ sudo -E yum-config-manager --add-repo "$DOCKERURL/centos/docker-ee.repo"
  • $ sudo yum -y install docker-ee
で Install できました。良し。


おまけ: docker-ee.repo

ちなみに DOCKERURL をブラウザで開くとファイル一覧が見られます。
ちょっと見た結果 yum の repo と rpm が置かれていました。
にしても、 yum の repo の仕様なのか、 docker-ee.repo が
  • DOCKERURL/docker-ee.repo
  • DOCKERURL/centos/docker-ee.repo
みたいに2つあって、どっちが正しいのか悩んだり。両方とも正しい可能性もあるな。



参考