A bolt out of the blue

競プロ、その他勉強したことなど

Dockerにhello worldしました

今更ですがDockerってなんですか?

コンテナ型の仮想化環境を提供するオープンソースソフトウェア

Docker - Wikipedia

アプリケーションは、それだけでは動かない。環境とセットで初めて動く。

なのでみんな環境構築に四苦八苦するのだけれど、その泥臭くてきつい作業から解放するために生まれたのがDockerだそうだ。

そこで、環境ごとまるっとアプリケーションを包み込むように開発すれば、余計な作業がなくなる。

このような開発スタイルを、コンポーネント志向と呼ぶらしい。

仮装マシンと違うのは、コンポーネントにはOSは含まれないところだ。ゆえに仮想マシンよりも軽量に動く。

Dockerに入門するのに、以下の記事を読んだので、自分用にまとめる。

英語:Get Started, Part 1: Orientation and setup | Docker Documentation

日本語:Part 1:概要説明とセットアップ — Docker-docs-ja 17.06.Beta ドキュメント

Hello world!

docker run hello-world

このコマンドを叩くと、ターミナルに次の文字列が流れてくる。

Hello from Docker!

This message shows that your installation appears to be working correctly.



To generate this message, Docker took the following steps:

1. The Docker client contacted the Docker daemon.

2. The Docker daemon pulled the "hello-world" image from the Docker Hub.

    (amd64)

3. The Docker daemon created a new container from that image which runs the

    executable that produces the output you are currently reading.

4. The Docker daemon streamed that output to the Docker client, which sent it

    to your terminal.

~~~

訳してみると、

Dockerの世界からこんにちは!
このメッセージを受け取っているということは、インストールはうまくいっているようですね。

このメッセージを生成するために、Dockerは次のような手順で動いています。

1. DockerクライアントがDockerデーモンを呼び出す
2. デーモンはDocker Hubから"hello-world"イメージを落としてくる
3. デーモンは"hello-world"イメージから新たにコンテナを作る。このコンテナが動いて、
 今あなたが読んでいる文章を提供する
4. デーモンがDockerクライアントの出力を読みだして、ターミナルに流す

とても分かりやすい。

flask on Docker

今度はpythonの公式ランタイム上でflaskアプリを動かし、redisでホスト名を返す簡単なアプリを作る。

Part 2:コンテナ — Docker-docs-ja 17.06.Beta ドキュメント

こんな感じになる。

f:id:hazuhi:20180908114316p:plain

Dockerfileのシンタックスハイライト

主要エディタならだいたいプラグインがある。

例えばSublime textなら、

Dockerfile Syntax Highlighting - Packages - Package Control

ちなみに、はてなにDockerfileのシンタックスハイライトはない。

はてなで綺麗にDockerfileを見せたい場合は、Pythonを指定しておくと比較的マシに見える。

例えば、

# 公式 Python ランタイムを親イメージとして使用
FROM python:2.7-slim

# 作業ディレクトリを /app に設定
WORKDIR /app

# 現在のディレクトリの内容を、コンテナ内の /app にコピー
ADD . /app

# requirements.txt で指定された必要なパッケージを全てインストール
RUN pip install -r requirements.txt

# ポート 80 番をコンテナの外の世界でも利用可能に
EXPOSE 80

# 環境変数の定義
ENV NAME World

# コンテナ起動時に app.py を実行
CMD ["python", "app.py"]

ビルド -> アプリの実行

docker build -t friendlyhello .
docker run -p 4000:80 friendlyhello

buildコマンドには、-tオプションでタグを指定できる。

このとき、現在のディレクトリを表す.がコマンドの最後に必要になる(ゴミじゃないよ)。

次にrunコマンドには、-pオプションでポート番号のマッピングを指定できる。

左側がDocker外部、右側が内部のポート番号になる。

イメージの公開と共有

Dockerをインストールしているのなら、https://hub.docker.com/のアカウントはもう持っているはずだ。

このアカウントでdocker hubにログインする。

docker login

ログインした後は、アカウントのレポジトリにpushして共有する。

ただしレポジトリにpushする前に、タグとリモートレポジトリを紐付ける必要がある。

タグはバージョン管理に使えるので、指定しておくと良い(指定しないと、latestとしてpushされる)。

docker tag image username/repository:tag
docker push username/repository:tag

こうしておけば、どのマシンからでも動かすことができるようになる。

docker rm image tag
docker run -p 4000:80 username/repository:tag