メインコンテンツへ移動
SEMentor
運用 約12分

Docker基礎

コンテナ技術の仕組みとDockerの基本操作・Dockerfile作成・docker-compose によるマルチコンテナ管理を学ぶ

コンテナとは何か

コンテナは、アプリケーションとその依存関係(ライブラリ・設定・ランタイム)を1つのパッケージにまとめて、どこでも同じように動かす仕組みです。

仮想マシン(VM)          コンテナ
┌────────────────┐        ┌────────────────┐
│   アプリ A     │        │   アプリ A     │
│   Python 3.11  │        │   Python 3.11  │
│   ライブラリ群  │        │   ライブラリ群  │
├────────────────┤        ├────────────────┤
│  ゲストOS      │        │   Docker Engine│ ← OS共有
│  (Ubuntu等)    │        ├────────────────┤
├────────────────┤        │   ホストOS     │
│  ハイパーバイザー│        └────────────────┘
├────────────────┤
│  ホストOS      │
└────────────────┘
VMはGByte、コンテナはMByte。起動はVMが分単位、コンテナは秒単位。

コンテナのメリット:

  • 「手元では動くのに本番では動かない」問題を解消
  • 開発・ステージング・本番で同じ環境を使える
  • 複数の言語・バージョンをホスト環境に影響なく共存

Dockerの基本概念

概念説明例え
Imageコンテナの設計図(不変)クラス
ContainerImageから作った実行インスタンスインスタンス
DockerfileImageを作るための手順書レシピ
RegistryImageの保管場所Docker Hub, ECR
Volumeコンテナ外の永続ストレージ外付けHDD
Networkコンテナ間の仮想ネットワークLAN

基本コマンド

# イメージの操作
docker pull nginx:latest            # レジストリからイメージを取得
docker images                       # ローカルのイメージ一覧
docker rmi nginx:latest             # イメージを削除
docker image prune                  # 未使用イメージを一括削除

# コンテナの起動
docker run nginx                          # フォアグラウンドで起動
docker run -d nginx                       # バックグラウンド(detached)
docker run -d -p 8080:80 nginx            # ホスト8080→コンテナ80にポートマップ
docker run -d --name my-nginx nginx       # コンテナに名前をつける
docker run -it ubuntu bash               # 対話的シェル起動(-i: 入力, -t: 疑似端末)

# コンテナの操作
docker ps                           # 実行中のコンテナ一覧
docker ps -a                        # 全コンテナ(停止中も含む)
docker stop my-nginx                # コンテナを停止(SIGTERM)
docker kill my-nginx                # コンテナを強制停止(SIGKILL)
docker rm my-nginx                  # コンテナを削除
docker rm -f my-nginx               # 実行中でも削除

# コンテナの中に入る
docker exec -it my-nginx bash       # 実行中のコンテナでbashを起動
docker logs my-nginx                # ログを表示
docker logs -f my-nginx             # ログをリアルタイム追跡

# ボリューム
docker run -v /host/path:/container/path nginx  # ホストのディレクトリをマウント
docker run -v my-volume:/data nginx             # 名前付きボリューム
docker volume ls                                # ボリューム一覧
docker volume rm my-volume                      # ボリューム削除

Dockerfile の書き方

# Python FastAPIアプリの例
FROM python:3.11-slim          # ベースイメージ(alpine/slimで軽量化)

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

# 依存関係ファイルだけを先にコピー(キャッシュ最適化)
COPY requirements.txt .
RUN pip install --no-cache-dir -r requirements.txt

# アプリのソースをコピー
COPY . .

# ポートを公開(ドキュメント目的、実際の公開はrunの-p)
EXPOSE 8000

# 非rootユーザーで実行(セキュリティ)
RUN useradd -m appuser
USER appuser

# コンテナ起動時のコマンド
CMD ["uvicorn", "main:app", "--host", "0.0.0.0", "--port", "8000"]

レイヤーキャッシュの最適化

# ❌ 悪い例: コードが変わるたびにpip installが走る
COPY . .
RUN pip install -r requirements.txt

# ✅ 良い例: requirements.txtが変わらなければキャッシュが使われる
COPY requirements.txt .
RUN pip install -r requirements.txt
COPY . .                       # ソース変更時もpip installはスキップ
# イメージのビルド
docker build -t my-app:1.0 .                    # タグ付きでビルド
docker build -t my-app:latest -f Dockerfile.prod .  # Dockerfileを指定
docker build --no-cache -t my-app .             # キャッシュなし

マルチステージビルド

# ビルドステージ(コンパイル等に使うツールを含む)
FROM node:20 AS builder
WORKDIR /app
COPY package*.json ./
RUN npm ci
COPY . .
RUN npm run build

# 本番ステージ(軽量)
FROM nginx:alpine
COPY --from=builder /app/dist /usr/share/nginx/html
EXPOSE 80
CMD ["nginx", "-g", "daemon off;"]

ビルドツールを含まない軽量なイメージが生成されます。

docker-compose によるマルチコンテナ管理

複数のコンテナをまとめて管理します。Webアプリ+DB+キャッシュのような構成で活躍します。

# docker-compose.yml
version: "3.9"

services:
  # Webアプリ
  app:
    build: .
    ports:
      - "8000:8000"
    environment:
      DATABASE_URL: postgresql://user:pass@db:5432/mydb
      REDIS_URL: redis://cache:6379
    depends_on:
      db:
        condition: service_healthy   # DBが起動してから起動
    volumes:
      - ./src:/app/src              # ホットリロード用

  # PostgreSQL
  db:
    image: postgres:15
    environment:
      POSTGRES_USER: user
      POSTGRES_PASSWORD: pass
      POSTGRES_DB: mydb
    volumes:
      - postgres_data:/var/lib/postgresql/data  # データを永続化
    healthcheck:
      test: ["CMD-SHELL", "pg_isready -U user -d mydb"]
      interval: 10s
      timeout: 5s
      retries: 5

  # Redis
  cache:
    image: redis:7-alpine
    volumes:
      - redis_data:/data

volumes:
  postgres_data:
  redis_data:
# docker-compose の基本操作
docker compose up -d            # バックグラウンドで全サービス起動
docker compose up --build       # イメージを再ビルドして起動
docker compose down             # 全コンテナを停止・削除
docker compose down -v          # ボリュームも削除
docker compose logs -f app      # appサービスのログを追跡
docker compose exec app bash    # appコンテナに入る
docker compose ps               # サービスの状態確認
docker compose restart app      # appサービスを再起動

.dockerignore

不要なファイルをイメージに含めないためのファイルです。

# .dockerignore
node_modules/
.git/
.env
*.log
dist/
__pycache__/
*.pyc
.pytest_cache/

これがないと node_modules(数百MB)や .git が含まれてイメージが肥大化します。

よくあるパターン

環境変数の管理

# .env ファイルを使う(.gitignore に追加すること)
docker run --env-file .env my-app
docker compose --env-file .env up

ヘルスチェック

HEALTHCHECK --interval=30s --timeout=10s --retries=3 \
  CMD curl -f http://localhost:8000/health || exit 1

まとめ

用途コマンド
イメージ取得docker pull
コンテナ起動docker run -d -p 8080:80
イメージビルドdocker build -t name .
コンテナ内に入るdocker exec -it name bash
ログ確認docker logs -f name
マルチコンテナdocker compose up -d

Docker は現代の開発・デプロイ基盤の中心です。まず docker rundocker compose up から始めて、徐々に Dockerfile の最適化を学んでいきましょう。

このレッスンは未完了です。