🙌

【初心者向け】イラストで学ぶDocker基礎

2024/08/11に公開
2

1. はじめに

こんにちは!初めての投稿となる今回の記事では、Dockerの基礎知識を分かりやすく解説します。
Dockerに興味があるけど、どこから始めればいいのかわからないという方に向けて、イラストを交えながら、Dockerの基本概念から使用方法まで、丁寧に説明していきます。
この記事を読んで、Dockerの世界に一歩踏み出していただけたら嬉しいです!

2. Dockerとは

アプリケーションをコンテナという単位で仮想化し、作成、配布、実行するためのソフトウェアです。
Dockerを使用することで開発者はアプリケーションとその依存関係を一つのパッケージとしてまとめ、どんな環境でも一貫して動作させることができます。

3. Docker Image


コンテナを起動するためには、まずDocker Imageが必要です。
Docker Imageはアプリケーションの実行に必要なOS、ソフトウェア、コマンド、およびメタデータをまとめたパッケージであり、実行時に読み取り専用で使用される静的データです。

4. Docker Imageの構成

もう少し詳しくDocker Imageの中身について解説します。
Docker ImageはOSやソフトウェア、およびコマンドをそれぞれ「レイヤー」という単位で管理しています。
docker history コマンドを使用することでレイヤーを表示することができます。
ここではnginxのDocker Imageを例に記載します。

$ docker pull nginx:latest # イメージを取得
$ docker history nginx
IMAGE          CREATED       CREATED BY                                       SIZE      COMMENT
443d199e8bfc   3 weeks ago   CMD ["nginx" "-g" "daemon off;"]                 0B        buildkit.dockerfile.v0
<missing>      3 weeks ago   STOPSIGNAL SIGQUIT                               0B        buildkit.dockerfile.v0
<missing>      3 weeks ago   EXPOSE map[80/tcp:{}]                            0B        buildkit.dockerfile.v0
<missing>      3 weeks ago   ENTRYPOINT ["/docker-entrypoint.sh"]             0B        buildkit.dockerfile.v0
<missing>      3 weeks ago   COPY 30-tune-worker-processes.sh /docker-ent…   4.62kB    buildkit.dockerfile.v0
<missing>      3 weeks ago   COPY 20-envsubst-on-templates.sh /docker-ent…   3.02kB    buildkit.dockerfile.v0
<missing>      3 weeks ago   COPY 15-local-resolvers.envsh /docker-entryp…   336B      buildkit.dockerfile.v0
<missing>      3 weeks ago   COPY 10-listen-on-ipv6-by-default.sh /docker…   2.12kB    buildkit.dockerfile.v0
<missing>      3 weeks ago   COPY docker-entrypoint.sh / # buildkit           1.62kB    buildkit.dockerfile.v0
<missing>      3 weeks ago   RUN /bin/sh -c set -x     && groupadd --syst…   95.9MB    buildkit.dockerfile.v0
<missing>      3 weeks ago   ENV PKG_RELEASE=2~bookworm                       0B        buildkit.dockerfile.v0
<missing>      3 weeks ago   ENV NJS_RELEASE=2~bookworm                       0B        buildkit.dockerfile.v0
<missing>      3 weeks ago   ENV NJS_VERSION=0.8.4                            0B        buildkit.dockerfile.v0
<missing>      3 weeks ago   ENV NGINX_VERSION=1.27.0                         0B        buildkit.dockerfile.v0
<missing>      3 weeks ago   LABEL maintainer=NGINX Docker Maintainers <d…   0B        buildkit.dockerfile.v0
<missing>      3 weeks ago   /bin/sh -c #(nop)  CMD ["bash"]                  0B
<missing>      3 weeks ago   /bin/sh -c #(nop) ADD file:cbda549b25cd4337c…   97.1MB

各レイヤーはDockerfile(後述)で定義された内容で保存されています。

参考
https://www.techscore.com/blog/2018/12/10/docker-images-and-layers/

5. Docker Hub

Docker Image はDocker Hub上で共有、配布することが可能です。

下記のコマンドでDocker Hubからの取得と配置※が可能です。※Dockerのアカウントが必要。

docker pull [イメージ名]
docker push [イメージ名]

https://hub.docker.com

6. Docker Imageの管理

下記のコマンドでpullおよび作成したDocker Imageを一覧で表示することができます。

docker image ls

Docker Imageは、ベースとなるOSやアプリケーション、その依存関係が含まれているため、データサイズを大きくする要因になります。
不要なDocker Imageは下記のコマンドからまとめて削除することが可能です。

docker system prune -a

7. Dockerfile


DockerfileとはDocker Imageを作成するためのテキストベースの設計書です。
Dockerfileを作成し、インストールや実行したいコマンドを定義しdocker buildを実行することで、ソフトウェアのインストールや設定が実行されたDocker Imageを作成することができます。
例えば、rubyの実行環境を構築する場合は下記のDockerfileを作成することで実現できます。

vi Dockerfile
#rubyがインストールされたDocker Imageを指定
FROM ruby:2.7

# ライブラリのインストール
RUN bundle config --local set path 'vender/bundle' \
    && bundle install

# 起動のコマンド実行
CMD [ "bundle", "exec", "ruby", "app.rb" ]

作成したDockerfileをビルドするとDocker Imageが作成されます。

docker build [Dockerfileのパスを指定] -t [イメージ名]:[タグ名]

8. Docker Imageの再ビルド

Dockerfileで既存のDockerイメージを参照している場合、例えば、

FROM nginx:latest

この場合、ビルドされる範囲はDockerfileに新たに定義した部分のみとなります。Docker Imageはレイヤー構造で構成されており、ビルドプロセスではDockerfileに基づいて変更された部分(差分)のレイヤーのみがビルドされます。既存のレイヤーはキャッシュとして再利用されるため、効率的なビルドが可能です。これにより、不要な処理を避け、ビルド時間を短縮することができます。

# 再利用
FROM nginx:latest

# ビルド対象
RUN apt-get update 
RUN apt-get install php
WORKDIR /var/www/html
docker build . -t myDockerImage

9. Docker Container


Docker Imageが実行される環境(以下、実行環境)を管理する仕組みのことです。
下記のコマンドから実行を行うことができます。

docker run [イメージ名]

Docker Imageに格納されているパッケージ内のアプリ・コマンドを実行し「コンテナ」という単位の区分け上で動作・管理します。

各コンテナ(以下 Docker Container)はお互いが干渉することはなく、独立(プロセスやネットワーク、ファイルシステム含め)しているため、実行の確実性と安定的な管理を実現しています。

また、Docker Containerが作成される度に内部でコンテナレイヤーが生成されます。
コンテナに対して入力された動的データ(例えば、コンテナ内で追加のソフトウェアのインストールした場合など)を格納するレイヤーです。

ただし、コンテナレイヤーはコンテナを削除すると自動的に削除される一時的なデータです。
コンテナレイヤーの状態を保存したい場合は、docker commitを使用することで、コンテナレイヤーを含めた新しいDocker Imageを作成することができます。

$ docker commit [コンテナ名] [イメージ名]:[タグ名]


参考
https://qiita.com/okmtz/items/f8231c83134a6363647b#コンテナイメージのレイヤ構造

10. 同一イメージの使用

複数のコンテナはDocker Imageを共有し実行することができます。
例えば1つのnginxのDocker Imageで、複数のポートでnginxサーバを起動することが可能です。

docker run -d -p 8080:80 --name webserver1 nginx
docker run -d -p 8081:80 --name webserver2 nginx

11. Docker Containerの基本コマンド

# Docker Imageを実行し、Docker Containerを作成・起動
docker container run --name [コンテナ名] [イメージ名] 

# 作成されたDocker Containerの一覧を表示。
docker container ls --all

# Docker Containerのライフサイクル(停止、起動、再起動、削除)
docker container stop [コンテナ名]
docker container start [コンテナ名]
docker container restart [コンテナ名]
docker container rm [コンテナ名]

# 実行環境から出力されたログを取得する
docker container logs [コンテナ名]

# 作成された実行環境内でコマンドを実行する
docker exec [コンテナ名] [コマンド]

https://docs.docker.jp/index.html

12. Docker Composeとは


複数のDocker Containerを一元管理するツールです。
具体的にはcompose.yamlで複数のサービスを定義し、docker composeコマンドで起動・管理します。

13. compose.yaml サンプル

例えば、3つのコンテナ(mysql、php、nginx)を使用したWebアプリケーションを構築する場合、
下記のようなcompose.yamlを定義することで構築することができます。

vi compose.yaml
services:
  web:
    image: nginx:latest
    ports:
      - "8080:80"
    volumes:
      - ./www:/var/www/html
      - ./nginx/default.conf:/etc/nginx/conf.d/default.conf
    depends_on:
      - php

  php:
    image: php:7.4-fpm
    volumes:
      - ./www:/var/www/html
    depends_on:
      - db

  db:
    image: mysql:5.7
    environment:
      MYSQL_ROOT_PASSWORD: example
      MYSQL_DATABASE: exampledb
      MYSQL_USER: user
      MYSQL_PASSWORD: password
    volumes:
      - db_data:/var/lib/mysql

volumes:
  db_data:
# compose.yamlに記載した内容を実行
docker compose up

services 直下に、web(nginxサーバ)、php(アプリケーションサーバ)、db(データベースサーバ)の各サービスを定義しています。Docker Composeを使用することで、これらのサービスを一括して起動・停止し、効率的に管理することができます。
詳細な設定についてはここでは触れませんが、1つのcompose.yamlで管理するイメージを掴んでいただければと思います。

14. Docker Composeの基本コマンド

# カレントディレクトリのcompose.yamlを元にDocker Imageの実行、
# Docker Containerの作成・実行
docker compose up

# 実行中のComposeプロジェクトを一覧表示
docker compose ls

# コンテナを一覧表示します。
docker compose ps

# Docker Composeのライフサイクル(停止、起動、再起動、削除)
docker compose stop
docker compose start
docker compose restart
docker compose rm

# Docker Composeから出力されたログを取得する
docker compose logs

# 作成されたDocker Composeのコンテナに対してコマンドを実行
docker compose exec [サービス名] [コマンド]

15.(備考)従来のVM(Hypervisor)との違い

  • ディスクボリューム
    VMはそれぞれの環境にOSをインストールします。これにより、複数のVMを運用する場合は大量のディスクスペースを消費します。対照的に、Dockerは単一のOSインスタンス上(OSを実行している実体)で複数のコンテナを実行し、基本イメージを共有することでディスクスペースを大幅に節約します。
  • 仮想化の対象の違い
    VMはハードウェアレベルでホストマシンを仮想化し、それぞれのVMが独立したハードウェアのように振る舞います。一方、DockerはOSレベルで仮想化を行い、単一のOSカーネルを使用しながらも、各コンテナが独立したコンピュータのように機能します。このアプローチにより、リソースの効率的な利用と高速な起動が可能となります。
  • 実行方法
    VMはディスクボリューム上に実行環境を展開します。
    Dockerはメモリ上で実行環境が展開されます。
    VMはI/Oをボリュームから行うため、メモリ上で実行するDockerよりも低速です。
    ただし、Dockerはメモリ上で動作するためメモリの性能が一定程度必要です。

このようにDockerは、効率的なリソース利用や軽量なコンテナを実現することで、開発やデプロイのプロセスを大幅に改善するツールです。

16. 最後に

最後まで読んでいただき、ありがとうございました!今回の記事で、Dockerの基礎について少しでも理解を深めていただけたなら幸いです。
もしこの記事の内容に間違いや改善点がありましたら、ぜひご指摘ください。皆さんのフィードバックをお待ちしております!

Discussion

YuneKichiYuneKichi
  • docker compose V1 はすでにEOLです
  • docker compose V2は基本的にdockerのプラグインであるため、docker composeのように使います
  • compose.yamlが推奨、docker-compose.ymlは下位互換のためにサポートすべき、とされています Composeファイル
  • versionトップレベル要素は廃止となっています Version top-level element (obsolete)
th_codeth_code

@YuneKichi
ご指摘いただき、ありがとうございます!
docker composeにバージョンがあるのですね🧐
勉強になりました。

推奨バージョンのV2の内容で記事を更新させていただきました。