[Troubleshooting] Docker コンテナは Running なのにサービスに接続できない場合

docker ps で確認するとコンテナの状態は Up(Running) になっているにもかかわらず、
ブラウザや curl など外部からサービスに接続できないことがある。

この問題は、コンテナが「落ちているかどうか」の話ではなく、
多くの場合 ネットワークのリスニング構成ポートマッピング設定 に原因がある。


症状(The Phantom Service) #

docker ps
CONTAINER ID   IMAGE     STATUS         PORTS
abcd1234       my-app    Up 10 minutes  0.0.0.0:8080->8080/tcp

状態 #

  • コンテナは正常に起動している(Up)
  • ポートも正しくバインドされているように見える

問題 #

curl localhost:8080 やブラウザでアクセスすると、

  • Connection refused
  • もしくは無限にロードが続く

原因1:Localhost(127.0.0.1)バインディング(最も多い) #

このケースが 全体の 80〜90% を占める。

コンテナ内部のアプリケーションが 127.0.0.1 のみでリスニングしている場合、
ホスト(外部)からは 絶対にアクセスできない
コンテナ内の localhost は、そのコンテナ自身を指すだけである。

確認方法(コンテナ内部) #

docker exec -it <container_name> ss -nltp
# または netstat -nltp
LISTEN 0 128 127.0.0.1:8080   ← 問題確定(外部アクセス不可)
LISTEN 0 128 0.0.0.0:8080     ← 正常(外部アクセス可能)

補足 #

Alpine や Distroless のような軽量イメージでは、
ssnetstatcurl すら入っていないことも多い。

その場合は、アプリケーションの起動ログや
application.ymlnginx.conf などの設定ファイルを直接確認し、
バインディングアドレスをチェックする必要がある。

対処方法 #

アプリケーションのリスニングアドレスを変更する。

  • 変更前:127.0.0.1 / localhost
  • 変更後:0.0.0.0(または ::

原因2:ポート不一致(Port Mismatch) #

Docker のポート公開(-p)と、
実際にアプリケーションが使用しているポートが一致していないケース。

よくあるミス #

docker run -p 8080:8080 my-app

Docker はコンテナの 8080 番ポートに通信を転送する。
しかし、実際のアプリケーションは 3000 番ポートで起動していた場合はどうなるか。

確認と修正 #

docker exec -it <container> ss -nltp
LISTEN 0 128 0.0.0.0:3000
# ポートマッピングを修正して再起動
docker run -p 8080:3000 my-app

原因3:コンテナ内では接続できるが、外部からはできない #

コンテナ内からはアクセスできるのに、
ホストや外部からはアクセスできない場合は ネットワークの問題 である。

内部テスト #

docker exec -it <container> curl localhost:8080
  • 成功 → アプリケーション自体は正常、ネットワーク/ファイアウォールの問題
  • 失敗 → アプリケーションが異常、またはハングしている状態

確認ポイント #

  • ホスト側のファイアウォール(ufwfirewalld
  • クラウド環境のセキュリティグループ(AWS SG など)
  • 特定のプライベート IP にのみバインドされていないか

原因4:Docker ネットワーク設定の問題 #

ユーザー定義ネットワーク(user-defined bridge)を使用している場合、
設計上、外部アクセスが制限されているケースもある。

確認 #

docker inspect <container> | grep -i network
  • bridgeuser-defined ネットワークかを確認
  • 外部公開が前提のコンテナかどうかを再確認

ログで必ず確認すべきパターン #

docker logs <container>

よく見かける決定的なログ:

  • Listening on 127.0.0.1
    → 原因1が確定
  • Bind failed: Address already in use
    → ポート競合によりアプリケーションが起動していない
  • サービス起動ログ自体が存在しない
    → 初期化中にハング、またはクラッシュ

Tip #

このような状況を素早く把握するために、
Dockerfile や docker-composeHEALTHCHECK を設定しておくとよい。

サービスに接続できない場合、
ステータスが Up (unhealthy) と表示されるため、問題の切り分けが非常に楽になる。


要点まとめ #

  • Running はプロセスが生きていることを示すだけで、サービス可用性を保証しない
  • 最初に確認すべきポイント
    • リスニングアドレス(127.0.0.10.0.0.0 か)
    • ポートマッピングと実際のアプリケーションポートの一致
  • 軽量イメージでは、コマンドよりも ログと設定ファイル が重要になる

この順序で確認すれば、
Docker の「Running なのに接続できない」問題は、ほとんどの場合 10分以内に解決できる

🛠 마지막 수정일: 2025.12.23

💡 お困りですか?
Zabbix、Kubernetes、各種オープンソースインフラの構築・運用・最適化・障害解析が必要であれば、いつでもご連絡ください。

📧 メール: jikimy75@gmail.com
💼 サービス: 導入支援 | 性能チューニング | 障害解析コンサルティング

What are your feelings

Updated on 2025-12-23