Docker
Dockerとは
Dockerとは、アプリケーションを「コンテナ」と呼ばれる単位でまとめて動かすためのプラットフォームです。
Dockerの特徴
・軽量:仮想マシン(VM)のように重いOSごと動かすのではなく、ホストOSのカーネルを共有しているので高速・軽量です。
・環境の統一:同じDockerイメージを使えば、Windows・Mac・Linuxどこでも同じ挙動が再現できます。
・簡単:Dockerfileという設定ファイルを書くだけで、誰でも同じ環境を再現できます。
主な用途
・開発環境の構築
・本番環境へのデプロイ
・テストの自動化
・マイクロサービス構築
本番運用するメリット
DockerDesktop
GUIでDockerを操作できるソフト
DcokerToolBoxとDockerDesktopはどちら使用すればよい?
Dockerの基本
Dockerイメージ
アプリケーションを動かすために必要なコード、ライブラリ、環境設定などをひとまとめにした実行パッケージ。
このDockerイメージをもとにコンテナが作成される。
Dockerイメージの入手方法
Docker Hub からプルする
docker runで自動取得
プライベートレジストリ(例: GitHub Container Registry, GitLab Container Registry, AWS ECRなど)から取得
Dockerfileから自分でビルド
tarファイルなどで直接もらう
コンテナのライフサイクル
作成(Create)
起動(Start)
実行中(Running)
停止(Stop)
一時停止(Pause)
再起動(Restart)
終了(Exited)
削除(Remove)
Dockerコマンドの新旧
ローカルに保存されている Docker イメージの一覧を表示するコマンド
docker image ls
ローカルにあるDockerイメージを削除するコマンド
docker image rm [イメージIDまたはイメージ名]
新しいコンテナを起動するためのコマンド
docker container run イメージ名
ローカルにイメージがある場合 → そのまま即起動
ローカルにイメージがない場合 → 自動でイメージをダウンロードしてから起動
現在実行中のコンテナ一覧を表示するコマンド
docker container ls
全ての状態のコンテナ一覧を表示するコマンド
docker container ls -a
指定したコンテナを停止するコマンド
docker container stop コンテナ名またはID
指定したコンテナを再起動するためのコマンド
docker container restart コンテナ名またはID
指定したコンテナを削除するコマンド
docker container rm コンテナ名またはID
新しいコンテナを作成起動し、コマンドを打てる状態にするコマンド
docker container run -it イメージ
Dockerイメージの詳細情報を確認するコマンド
docker image inspect <イメージ名>:<タグ>
[
{
"Id": "sha256:1e4467b07108...",
"RepoTags": [
"ubuntu:20.04"
],
"Created": "2024-03-10T14:00:00.000000000Z",
"Size": 72705900,
"Architecture": "amd64",
"Os": "linux",
"Config": {
"Cmd": [
"/bin/bash"
],
"Env": [
"PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin"
],
...
},
"RootFS": {
"Type": "layers",
"Layers": [
"sha256:abc123...",
"sha256:def456..."
]
}
}
]
新しいコンテナを作成起動し、自作のコマンドを実行するコマンド
docker container run イメージ名 自作コマンド
すでに起動中のコンテナの中でコマンドを実行(新たにコンテナは作成しない)するコマンド
docker container exec コンテナ名またはID コマンド
コンテナ作成時、コンテナ名をつけるコマンド
docker container run --name <コンテナ名> <イメージ名>
一括削除するコマンド
・停止しているコンテナを一括削除
docker container prune
・ボリューム削除
docker volume prune
・ネットワーク削除
docker network prune
・イメージ削除(未使用のもの)
docker image prune
・全部まとめて削除
docker system prune
フォアグラウンドモード(通常モード)とデタッチドモード(バックグラウンドモード)
デタッチドモードからフォアグラウンドモードに切り替える
イメージレイヤーとコンテナレイヤー
コンテナのデータの永続化
以下の2種類ある。
ボリューム(Volume)
バインドマウント(Bind Mount)
複数のコンテナ間でのデータ共有可能?
ボリュームとバインドマウント可能
ホストからデータアクセス可能?
ボリュームは不可
バインドマウントは可能
ホストの環境に依存する?
ボリュームは不可
バインドマウントは可能
ボリューム(Volume)のコマンド
バインドマウント(Bind Mount)のコマンド
ホストマシーンとコンテナのポート番号を紐づけるコマンド
docker container run -p <ホスト側ポート>:<コンテナ側ポート> イメージ名
異なるコンテナ間で通信するコマンド
なお、異なるネットワーク間は通信できない
DockerFile
DockerFileとは
自作でDockerイメージを作成するためのテキストファイルのこと。
レイヤー構造とは
記述
・ARG:
セキュリティ的に残したくないもの(例:APIキー、トークン)※ただし完全なセキュリティ保証ではない。
ビルドプロセスでしか必要ないもの(例:特定のビルドフラグやバージョン指定)。
・ENV:
コンテナ実行中にも使いたいもの(例:DB接続設定、アプリ環境名など)。
WORKDIRとcdの違い
DockerFileとビルドコンテキスト
ビルドコンテキストは、
docker image buildコマンドを実行するときの、指定するディレクトリのことである。
以下の例でいうと
docker build -t myapp .
この . が「ビルドコンテキスト」です。
Dockerはこのディレクトリ(とそのサブディレクトリ)内のすべてのファイルにアクセスできるので、
・COPY ./src /app/src
・ADD myscript.sh /usr/local/bin/
のようなファイル指定がこの範囲内で動きます。
重要ポイント
・Dockerfileはビルドコンテキスト内に置くのが基本です(ただし-fで外にあるDockerfileを指定することもできます)。
・ビルドコンテキストが広いと、不要なファイルも送信してしまうので、.dockerignoreで除外リストを書くのがベストプラクティスです。
DockerFileからimageを作成するコマンド
-fで外にあるDockerfileを指定する方法
.dockerignoreで無駄なファイル・フォルダをビルドコンテキストに含めないようにする
DockerFileの容量を削減
RUNの中にコマンドを一行でまとめて書くのは容量が小さくなるが、もし変更があった場合にまた再度キャッシュを利用せずにビルドする必要があるため一行一行書いていくかはケースバイケース。
マルチステージビルドについての詳しい説明
マルチステージビルドで一つのDockerFileで開発環境と本番環境で処理を分けたり、共通処理は同じにして容量を削減したりするDocker Compose
Docker Composeとは
複数のDockerコンテナをまとめて定義・実行できるツール。
通常、Docker単体では1つのコンテナをdocker runコマンドで起動しますが、実際のアプリケーションは、
Webサーバー
データベース
キャッシュ(Redisなど)
といった複数のコンテナを連携させて動かすことが多いですよね。
そのときに役立つのがDocker Composeです。
特徴
・YAMLファイル(docker-compose.yml)で定義
コンテナの構成、ボリューム、ネットワーク、環境変数などを1つのファイルにまとめます。
version: '3.8'
services:
app:
build: .
ports:
- "8080:80"
db:
image: mysql:8
environment:
MYSQL_ROOT_PASSWORD: secret
・コマンド1つで一括操作
docker-compose up
これだけで定義したすべてのコンテナが一斉に起動します。
・ネットワークが自動構築
同じComposeファイル内のコンテナ同士は、自動的にブリッジネットワークで接続され、コンテナ名で名前解決できます。
・環境の統一
チーム開発や本番環境と同じ構成をローカルでも簡単に再現できます。
記述
コマンド
VscodeのDev Containersでdockercompse.ymlでコンテナごとに異なるExtensionsで環境構築を行う
本番環境で異なるコンテナ間で通信する際に、IPアドレスで指定するのではなくコンテナ名で指定して通信を行う
Discussion