【3-7】Docker Compose実践編:本番を見据えた環境分離とデバッグ手法
Docker Compose実践編③:本番を見据えた環境分離とデバッグ手法
はじめに
前回の記事では、docker compose logsやhealthcheckを駆使して、稼働中のコンテナを**「守り、治す」ための監視・トラブルシューティング手法を学びました。しかし、プロの現場ではもう一つ、絶対に越えなければならない壁があります。それが「環境の分離」**です。
開発中に使っていたテスト用のデータベース接続情報を、うっかり本番環境で使ってしまった… そんなヒューマンエラーは、時として重大なインシデントを引き起こします。
この記事では、docker-compose.ymlは一つも変更せずに、設定ファイルだけで開発環境と本番環境を安全に切り替えるためのエレガントな手法と、デバッグの基本となるコマンドをマスターしていきます。
実践:設定ファイルで環境を切り替える
~/multi-env-composeディレクトリを作成し、作業を進めていきましょう。
Step 1: 設計図を柔軟にする 〜変数を埋め込んだdocker-compose.yml〜
まず、どの環境でも共通で使う「基本の設計図」となるdocker-compose.ymlを作成します。ここでのポイントは、ポート番号や環境変数といった、環境によって変わりうる値を${WEB_PORT}のように変数として記述することです。
:-(コロンとハイフン)は、もし変数が設定されていなかった場合に適用されるデフォルト値を意味します。
# 作業ディレクトリを作成して移動
mkdir ~/multi-env-compose
cd ~/multi-env-compose
# docker-compose.yml を作成
cat > docker-compose.yml << 'EOF'
services:
web:
image: nginx:alpine
ports:
- "${WEB_PORT:-80}:80"
environment:
- ENV=${APP_ENV:-development}
networks:
- app-network
app:
image: node:18-alpine
working_dir: /app
command: npm start
environment:
- NODE_ENV=${APP_ENV:-development}
- DB_HOST=${DB_HOST:-db}
- DB_NAME=${DB_NAME:-myapp}
- DB_USER=${DB_USER:-appuser}
- DB_PASS=${DB_PASS:-apppass}
networks:
- app-network
networks:
app-network:
EOF
Step 2: 環境ごとの「設定シート」を用意する
次に、先ほど埋め込んだ変数に実際の値を設定するための「設定シート」を、環境ごとに作成します。Docker Composeは、.envという名前のファイルを自動で読み込む仕組みを持っています。
開発環境用の設定シート (.env.development)
開発中はポートが衝突しないように8080番を使い、DB接続情報もローカル開発用の分かりやすいものにします。
cat > .env.development << 'EOF'
APP_ENV=development
WEB_PORT=8080
DB_HOST=localhost
DB_NAME=dev_myapp
DB_USER=dev_user
DB_PASS=dev_pass
EOF
本番環境用の設定シート (.env.production)
本番環境ではWebサーバーの標準ポート80番を使い、DB接続情報もより強固で本番用のものに切り替えます。
cat > .env.production << 'EOF'
APP_ENV=production
WEB_PORT=80
DB_HOST=prod-db-server
DB_NAME=prod_myapp
DB_USER=prod_user
DB_PASS=strong_prod_password
EOF
これで、アプリケーションの構造と設定を綺麗に分離することができました。
Step 3: 開発環境を起動し、中を覗いてみる
それでは、実際に環境を切り替えてみましょう。
開発用の設定シートを有効にする
cpコマンドで、docker composeが読み込む.envという名前にコピーします。
cp .env.development .env
設定をプレビューする(重要!)
docker compose upを実行する前に、docker compose configコマンドを使いましょう。これは、設定ファイルが最終的にどのように解釈されるかを出力してくれる、非常に便利な「確認用」コマンドです。
docker compose config
portsが8080:80に、environmentが開発用の値になっていることが確認できればOKです。
コンテナを起動し、内部をデバッグする
設定に問題がなければ、コンテナを起動します。
docker compose up -d
次に、docker compose execを使ってappコンテナの中に入り、意図した環境変数が渡されているかを確認してみましょう。これは「設定が反映されない」といった問題の最も基本的な切り分け方法です。
# appコンテナのシェルに入る
docker compose exec app /bin/sh
# コンテナ内部で環境変数を確認
/app # env | grep -E "(NODE_ENV|DB_)"
NODE_ENV=development
DB_HOST=localhost
DB_NAME=dev_myapp
DB_USER=dev_user
DB_PASS=dev_pass
# 確認後、コンテナから抜ける
/app # exit
狙い通り、開発用の設定が反映されていますね!
Step 4: 本番環境への切り替えをシミュレートする
最後に、開発環境を停止し、本番用の設定に切り替えるシミュレーションを行います。
# 開発環境のコンテナを停止・削除
docker compose down
# 本番用の設定シートを有効にする
cp .env.production .env
# 再び設定をプレビューして、本番用に切り替わったか確認
docker compose config
WEB_PORTが80に、DB_HOSTがprod-db-serverに変わっているはずです。このように、docker-compose.ymlには一切触れずに、cpコマンドだけで環境を安全に切り替えることができました。
本番環境で何か問題が起きた際は、前回の記事で学んだdocker compose ps、docker compose logs --tail=100、そしてコンテナのイベント履歴を見るdocker compose eventsといったコマンドが診断の助けになります。
まとめ
Docker Composeの旅は、これで一つの区切りを迎えました。環境構築の自動化から始まり、コンテナの監視・デバッグ、そして安全な環境分離まで、あなたはもうDocker Composeを**「使いこなせる」**レベルに到達したはずです。このスキルは、あなたの開発・運用業務をより効率的で、より安全なものにしてくれるでしょう。
Discussion