Dockerコンテナが起動しない?「Exit Code 1」などの原因を特定する4ステップ

金曜の夜8時半、帰り支度をしていた私のスマホが震えました。本番環境のアラートです。
確認すると、4つのコアサービスのコンテナがすべて「Exited」状態になっていました。
ターミナルを開き docker ps を叩くも、結果は空白。
背筋が凍る瞬間です。「週末が消えたな」と覚悟しました。
結局、2時間の調査の末に見つかった原因は、設定ファイルのパスミスという単純なものでした。もし当時の私が「体系的な調査フロー」を持っていれば、10分で解決できていたはずです。
この記事では、私が数々の失敗から学んだ「コンテナが起動しない時のトラブルシューティング手法」を共有します。Exit Code 1 や 137 を見たときに何をすべきか、もう迷うことはありません。
まず理解すべき:終了コード(Exit Code)の意味
コンテナが停止した時、Dockerは必ず「終了コード」を残します。これは死因を特定するダイイングメッセージです。
| 終了コード | 意味 | よくある原因 |
|---|---|---|
| 0 | 正常終了 | バッチ処理が完了した、など(異常ではありません)。 |
| 1 | 一般的なエラー | アプリの設定ミス、バグ、例外発生など、最も多いケース。 |
| 137 | 強制終了 (SIGKILL) | メモリ不足 (OOM Killer) が大半。または docker kill された。 |
| 127 | コマンドが見つからない | DockerfileのCMDやENTRYPOINTで指定したコマンドが存在しない。 |
| 139 | Segmentation Fault | メモリアクセス違反。C/C++等の低レイヤーアプリで発生。 |
| 1-128 | アプリ内部のエラー | 設定ファイルミス、権限不足、DB接続失敗など。 |
| 129-255 | OSシグナルによる終了 | 外部からの停止命令や強制終了。 |
特に Exit Code 137 は重要です。これは「メモリを使いすぎてLinuxカーネルに殺された」可能性が高いからです。
4ステップ排查法(トラブルシューティング・フロー)
ステップ1:コンテナの状態を確認する
まず、死んだコンテナを見つけます。docker ps では見えないので -a を付けます。
docker ps -a出力例:
CONTAINER ID IMAGE STATUS
a1b2c3d4e5f6 mysql:8.0 Exited (1) 2 minutes agoここで STATUS 列の Exited (1) に注目。終了コードは1です。「アプリ内部で何か起きたな」と推測できます。
ステップ2:ログを見る(最重要)
ほぼ全ての答えはログにあります。
docker logs <container_id>もしログが長すぎる場合は、直近100行だけ見ます:
docker logs --tail 100 <container_id>エラーメッセージ(Error, Exception, Fatal など)を探してください。「Config file not found」や「Connection refused」があれば、それが答えです。
ステップ3:コンテナの設定を深掘りする (docker inspect)
ログを見ても分からない場合、コンテナの設定自体が間違っている可能性があります。docker inspect で詳細情報を見ます。
終了コードを見る:
docker inspect --format '{{.State.ExitCode}}' <container_id>メモリ不足(OOM)で死んだか確認する:
docker inspect --format '{{.State.OOMKilled}}' <container_id>これが true なら、メモリ不足が確定です。
マウントパスを確認する:
docker inspect --format '{{.Mounts}}' <container_id>設定ファイルを置いたつもりの場所に、本当にマウントされていますか?
ステップ4:対話モードで手動起動してみる
上記でも分からない場合、コンテナの中に入って手動で動かしてみるのが確実です。
本来の起動コマンドが docker run -d my-app だとしたら、-d(バックグラウンド)の代わりに -it(対話モード)を使い、コマンドをシェル(/bin/bash や /bin/sh)で上書きします。
docker run -it my-app /bin/bashコンテナの中に入れたら、以下を試します:
- 設定ファイルはあるか? (
ls -l /etc/my-app/config.yml) - 依存サービス(DBなど)に繋がるか? (
curl db:3306やping db) - 手動でアプリを起動してみる (
./start.shやnode index.js)
これで、エラーが目の前で再現されるはずです。
よくある5つの失敗パターンと解決策
パターン1:設定ファイルパスの間違い(Exit 1)
症状:ログに No such file or directory や Config not found。
原因:ホスト側のパス、またはコンテナ側のマウント先パスを書き間違えている。
対策:
# 間違い
docker run -v /host/conf:/app/config ...
# 正解(アプリが期待しているのは /app/conf だった場合)
docker run -v /host/conf:/app/conf ...パターン2:メモリ不足 (OOM Killed)(Exit 137)
症状:突然死ぬ。docker inspect で OOMKilled: true になる。Linuxのシステムログ (dmesg) にも記録が残る。
原因:コンテナに割り当てたメモリ制限が厳しすぎるか、アプリがメモリリークしている。
対策:
- メモリ制限を増やす:
docker run -m 1g ... - Javaの場合、ヒープサイズを指定する:
-Xmx512mなど。
パターン3:ポートの競合(Exit 1)
症状:ログに Address already in use や Bind for 0.0.0.0:80 failed。
原因:そのポートを他のコンテナやホスト上のプロセス(Apache/Nginxなど)が既に使っている。
対策:
- 競合しているプロセスを止める。
- マッピングするポートを変える:
-p 8080:80(ホストの8080をコンテナの80に繋ぐ)。
パターン4:権限不足(Permission Denied)(Exit 1)
症状:ログに Permission denied や Access denied。
原因:コンテナ内のユーザー(非root)が、マウントされたホスト側のファイルを読み書きできない。
対策:
- ホスト側のファイルの所有者を変更する:
chown - コンテナをrootで実行する(開発時のみ):
--user root - コンテナ実行ユーザーとホストユーザーのUIDを合わせる。
パターン5:依存サービスが準備できていない
症状:Connection refused。DBコンテナとアプリコンテナを同時に立ち上げたが、DBの起動が遅くてアプリが先に死ぬ。
原因:コンテナの起動順序制御が甘い。
対策:
- Docker Compose:
depends_onにcondition: service_healthyを使う。 - Waitスクリプト:
wait-for-it.shなどのスクリプトを使い、DBのポートが開くまで待機してからアプリを起動する。
# 起動コマンドの例
./wait-for-it.sh mysql:3306 -- node app.jsまとめ
コンテナが起動しないときは、パニックにならず、以下のリストをチェックしてください。
docker ps -aで終了コードを見る。docker logsでエラーメッセージを読む。- Exit 137 ならメモリを疑う。
- Exit 1 なら設定ミスか権限エラーを疑う。
- どうしても分からなければ
-it /bin/bashで中に入って調査する。
このフローさえ頭に入っていれば、どんなエラーも論理的に解決できます。
Dockerコンテナ起動失敗の完全調査フロー
コンテナがExited状態になる原因を特定し、修復するための4ステップ
⏱️ Estimated time: 15 min
- 1
Step1: ステップ1:状態コードの確認
コマンド:docker ps -a
解説:STATUS列を確認します。「Exited (1)」ならアプリのエラー、「Exited (137)」ならメモリ不足(OOM)の可能性が高いです。 - 2
Step2: ステップ2:ログの分析
コマンド:docker logs <container_id>
解説:エラーメッセージを探します。ログが長すぎる場合は --tail 50 で直近のみを表示します。 - 3
Step3: ステップ3:詳細設定の検査
コマンド:docker inspect <container_id>
解説:State.OOMKilledがtrueになっていないか、Mounts(マウントパス)が正しいかを確認します。 - 4
Step4: ステップ4:手動起動による検証
コマンド:docker run -it <image> /bin/bash
解説:対話モードでコンテナ内に入り、手動でアプリを起動してエラーを再現させます。設定ファイルの存在確認やネットワーク疎通確認も行います。
FAQ
Exit Code 137とは何ですか?
docker logsを見ても何も表示されません。
コンテナ起動直後にExited (0)になります。
3 min read · 公開日: 2025年12月18日 · 更新日: 2026年1月22日
関連記事
Next.js ファイルアップロード完全ガイド:S3/Qiniu Cloud 署名付き URL 直接アップロード実践

Next.js ファイルアップロード完全ガイド:S3/Qiniu Cloud 署名付き URL 直接アップロード実践
Next.js Eコマース実践:カートと Stripe 決済の完全実装ガイド

Next.js Eコマース実践:カートと Stripe 決済の完全実装ガイド
Next.js ユニットテスト実践:Jest + React Testing Library 完全設定ガイド


コメント
GitHubアカウントでログインしてコメントできます