dockerコンテナ内でNginxが動いていて、localhostでmysqlが動いていて、Nginx内からmysqlに接続したいのですが、どうすればいいですか?MySqlはlocalhostで動作しており、外部にポートを公開していないので、マシンのIPアドレスにバインドされているのではなく、localhostにバインドされています。
このドッカーコンテナの中から、このMySqlやlocalhost上の他のプログラムに接続する方法はないのでしょうか?
この質問は "How to get IP address of the docker host from inside a docker container" とは異なります。なぜなら、ドッカーホストのIPアドレスはパブリックIPであったり、ネットワーク上のプライベートIPであったり、ドッカーコンテナ内から到達可能であるかどうか(AWSなどでホストされていればパブリックIPという意味)です。たとえDockerホストのIPアドレスを知っていたとしても、そのIPアドレスでコンテナ内からDockerホストに接続できるわけではありません。Dockerネットワークがオーバーレイ、ホスト、ブリッジ、macvlan、なしなど、そのIPアドレスの到達性を制限している可能性があるためです。
編集: Docker-for-mac または Docker-for-Windows 18.03+ を使用している場合、ホスト host.docker.internal
を使用して mysql サービスに接続するだけでよいです。
Docker 18.09.3現在、Docker-for-Linuxでは動作しません。 2019年3月8日に【修正】(https://github.com/docker/libnetwork/pull/2348)が提出されており、うまくいけばコードベースにマージされる予定です。それまでは、[qoomon'の回答][1]にあるようなコンテナを使用することが回避策となります。
docker runコマンドで
--network="host"を使用すると、docker コンテナ内の
127.0.0.1` はあなたの docker ホストを指すようになります。
注意:このモードはDocker for Linuxでのみ動作しますドキュメントによる。
Dockerでは、コンテナを実行する際に異なるネットワークモードを提供します。選択したモードによって、ドッカーホスト上で動作しているMySQLデータベースへの接続が異なります。
Docker はデフォルトで docker0
という名前のブリッジを作成します。ドッカーホストとドッカーコンテナの両方がそのブリッジ上のIPアドレスを持っています。
Docker ホストで、sudo ip addr show docker0
と入力すると、次のような出力が得られます。
[vagrant@docker:~] $ sudo ip addr show docker0
4: docker0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default
link/ether 56:84:7a:fe:97:99 brd ff:ff:ff:ff:ff:ff
inet 172.17.42.1/16 scope global docker0
valid_lft forever preferred_lft forever
inet6 fe80::5484:7aff:fefe:9799/64 scope link
valid_lft forever preferred_lft forever
つまり、私のドッカーホストは docker0
ネットワークインターフェースに 172.17.42.1
というIPアドレスを持っていることになります。
では、新しいコンテナを起動し、その上でシェルを取得します。docker run --rm -it ubuntu:trusty bashと入力し、コンテナ内で
ip addr show eth0` と入力して、メインネットワークインターフェイスがどのように設定されているかを確認します。
root@e77f6a1b3740:/# ip addr show eth0
863: eth0: <BROADCAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
link/ether 66:32:13:f0:f1:e3 brd ff:ff:ff:ff:ff:ff
inet 172.17.1.192/16 scope global eth0
valid_lft forever preferred_lft forever
inet6 fe80::6432:13ff:fef0:f1e3/64 scope link
valid_lft forever preferred_lft forever
ここでは、私のコンテナのIPアドレスは「172.17.1.192」です。次にルーティングテーブルを見ます。
root@e77f6a1b3740:/# route
Kernel IP routing table
Destination Gateway Genmask Flags Metric Ref Use Iface
default 172.17.42.1 0.0.0.0 UG 0 0 0 eth0
172.17.0.0 * 255.255.0.0 U 0 0 0 eth0
つまり、ドッカーホストのIPアドレス 172.17.42.1
がデフォルトルートとして設定され、コンテナからアクセス可能になっています。
root@e77f6a1b3740:/# ping 172.17.42.1
PING 172.17.42.1 (172.17.42.1) 56(84) bytes of data.
64 bytes from 172.17.42.1: icmp_seq=1 ttl=64 time=0.070 ms
64 bytes from 172.17.42.1: icmp_seq=2 ttl=64 time=0.201 ms
64 bytes from 172.17.42.1: icmp_seq=3 ttl=64 time=0.116 ms
また、ネットワーク設定を host
に設定 して、Docker コンテナを実行することもできます。このようなコンテナはネットワークスタックをドッカーホストと共有し、コンテナの視点からは localhost
(または 127.0.0.1
) はドッカーホストを指すことになります。
ドッカーコンテナで開いたポートは、ドッカーホストで開かれることになるので注意してください。そして、これは -p
または -P
docker run
オプション を要求することなく実行されます。
私のドッカーホストでのIP設定。
[vagrant@docker:~] $ ip addr show eth0
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
link/ether 08:00:27:98:dc:aa brd ff:ff:ff:ff:ff:ff
inet 10.0.2.15/24 brd 10.0.2.255 scope global eth0
valid_lft forever preferred_lft forever
inet6 fe80::a00:27ff:fe98:dcaa/64 scope link
valid_lft forever preferred_lft forever
と、hostモードのdockerコンテナから。
[vagrant@docker:~] $ docker run --rm -it --network=host ubuntu:trusty ip addr show eth0
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
link/ether 08:00:27:98:dc:aa brd ff:ff:ff:ff:ff:ff
inet 10.0.2.15/24 brd 10.0.2.255 scope global eth0
valid_lft forever preferred_lft forever
inet6 fe80::a00:27ff:fe98:dcaa/64 scope link
valid_lft forever preferred_lft forever
このように、ドッカーホストとドッカーコンテナは全く同じネットワークインターフェースを共有しており、同じIPアドレスを持っています。
docker ホスト上で動作する MySQL に ブリッジモード でコンテナからアクセスするには、MySQL サービスが 172.17.42.1
の IP アドレスで接続を待ち受けていることを確認する必要があります。
そのためには、MySQL 設定ファイル (my.cnf) に bind-address = 172.17.42.1
または bind-address = 0.0.0
のいずれかを記述しておく必要があることを確認します。
ゲートウェイのIPアドレスを環境変数に設定する必要がある場合は、コンテナ内で次のコードを実行します。
export DOCKER_HOST_IP=$(route -n | awk '/UG[ \t]/{print $2}')
で、アプリケーションの中で、DOCKER_HOST_IP
環境変数を使用して、MySQL への接続を開始します。
注意: bind-address = 0.0.0.0
を使用した場合、MySQL サーバはすべてのネットワークインターフェイスで接続を待ち受けます。つまり、MySQLサーバーはインターネットからアクセスできる可能性があるということです。
注2: bind-address = 172.17.42.1
を使用した場合、MySQLサーバーは 127.0.0.1
への接続をリッスンすることはありません。ドッカーホスト上で動作しているプロセスでMySQLに接続したい場合は、172.17.42.1
のIPアドレスを使用しなければなりません。
ホストモード*のコンテナから docker ホスト上で動作する MySQL にアクセスするには、MySQL の設定で bind-address = 127.0.0.1
を維持すれば、あとはコンテナから 127.0.0.1
に接続するだけでよいのです。
[vagrant@docker:~] $ docker run --rm -it --network=host mysql mysql -h 127.0.0.1 -uroot -p
Enter password:
Welcome to the MySQL monitor. Commands end with ; or \g.
Your MySQL connection id is 36
Server version: 5.5.41-0ubuntu0.14.04.1 (Ubuntu)
Copyright (c) 2000, 2014, Oracle and/or its affiliates. All rights reserved.
Oracle is a registered trademark of Oracle Corporation and/or its affiliates. Other names may be trademarks of their respective owners.
Type 'help;' or '\h' for help. Type '\c' to clear the current input statement.
mysql>
note: mysql -h localhost
ではなく、mysql -h 127.0.0.1
を使用してください; そうしないと MySQL クライアントが unix ソケットを使用して接続しようとします。
Docker v 18.03以上(2018年3月21日以降)。
内部IPアドレスを使用するか、ホストが使用する内部IPアドレスに解決する特別なDNS名「host.docker.internal」に接続します。
Linuxサポートは保留中のhttps://github.com/docker/for-linux/issues/264をサポートしています。
Docker for Mac v 17.12からv 18.02 。
上記と同じですが、代わりに「docker.for.mac.host.internal」を使用してください。
Docker for Mac v 17.06からv 17.11 。
上記と同じですが、代わりに「docker.for.mac.localhost」を使用してください。
Docker for Mac 17.05以下。
ドッカーコンテナーからホストマシンにアクセスするには、ネットワークインターフェイスにIPエイリアスを添付する必要があります。 任意のIPをバインドできます。他のIPに使用していないことを確認してください。
sudo ifconfig lo0エイリアス123.123.123.123 / 24
。
次に、サーバーが上記のIPまたは「0.0.0.0」を聞いていることを確認します。 localhost 127.0.0.1
でリスニングしている場合、接続は受け入れられません。
次に、ドッカーコンテナをこのIPに向けるだけで、ホストマシンにアクセスできます。!
テストするには、コンテナ内で「curl -X GET 123.123.123:3000」のようなものを実行できます。
エイリアスはすべての再起動時にリセットされるため、必要に応じて起動スクリプトを作成します。
ソリューションとその他のドキュメントはこちら:https://docs.docker.com/docker-for-mac/networking/#use-cases-and-workarounds。
上記の投稿と同様のハックを実行して、ローカルIPをコンテナ内のエイリアス名(DNS)にマップします。 主な問題は、 LinuxとOSXの両方で機能する単純なスクリプトでホストIPアドレスを動的に取得することです。 私はこのスクリプトを両方の環境で実行しました(「$ LANG」を使用したLinuxディストリビューションでも)。 != "en_ *" 構成済み):
ifconfig | grep -E "([0-9]{1,3}\.){3}[0-9]{1,3}" | grep -v 127.0.0.1 | awk '{ print $2 }' | cut -f2 -d: | head -n1
したがって、Docker Composeを使用すると、完全な構成は次のようになります。
スタートアップスクリプト(docker-run.sh):
export DOCKERHOST=$(ifconfig | grep -E "([0-9]{1,3}\.){3}[0-9]{1,3}" | grep -v 127.0.0.1 | awk '{ print $2 }' | cut -f2 -d: | head -n1)
docker-compose -f docker-compose.yml up
docker-compose.yml :
myapp:
build: .
ports:
- "80:80"
extra_hosts:
- "dockerhost:$DOCKERHOST"
次に、コードの「http://localhost」を「http://dockerhost」に変更します。
DOCKERHOST
スクリプトをカスタマイズする方法のより高度なガイドについては、この投稿を見て、それがどのように機能するかを説明してください。
これは NGINX/PHP-FPM スタックで、コードやネットワークに一切触れずに、アプリが localhost
に接続できることを期待している状態で動作しました。
ホストからコンテナ内に mysqld.sock
をマウントします。
mysqlが動作しているホストでmysql.sockファイルの場所を確認する。 netstat -ln | awk '/mysql(.*)?.sock/ { print $9 }'`)
そのファイルをドッカーで想定される場所にマウントします。
docker run -v /hostpath/to/mysqld.sock:/containerpath/to/mysqld.sock
とします。
mysqld.sockの場所として考えられるもの。
/tmp/mysqld.sock
/var/run/mysqld/mysqld.sock
/var/lib/mysql/mysql.sock
/Applications/MAMP/tmp/mysql/mysql.sock # if running via MAMP
host.docker.internal
がすべてのプラットフォームで動作するまで、手動設定なしでNATゲートウェイとして機能するコンテナを使用できます。
Linuxのソリューション(カーネル> = 3.6)。
わかりました。ローカルホストサーバーには、デフォルトのドッカーインターフェイス docker0 とIPアドレス 172.17.0.1 があります。 コンテナは、デフォルトのネットワーク設定--net = "bridge" から始まりました。
1。 docker0インターフェイスのroute_localnetを有効にします。
$ sysctl -w net.ipv4.conf.docker0.route_localnet = 1
。
2。 このルールをiptablesに追加します。
$ iptables -t nat -I PREROUTING -i docker0 -d 172.17.0.1 -p tcp --dport 3306 -j DNAT --to 127.0.0.1:3306
。
$ iptables -t filter -I INPUT -i docker0 -d 127.0.0.1 -p tcp --dport 3306 -j ACCEPT
。
3。 mysqlユーザーを '%'からアクセスできるようにします。つまり、localhostを除く誰からでも:
ユーザー 'user' @ '%'を作成 'パスワード'によって識別されます;
。
4。 スクリプトのmysqlサーバーアドレスを172.17.0.1に変更します。
。
route_localnet -BOOLEAN:ルーティング中は、ループバックアドレスを火星ソースまたは宛先と見なさないでください。 これにより、ローカルルーティングの目的で127/8を使用できます(デフォルトFALSE )。
Windows 10のソリューション。
Docker Community Edition 17.06.0-ce-win18 2017-06-28(安定)< br />。
ホスト docker.for.win.localhost
のDNS名を使用して、内部IPに解決できます。 (一部のソースに警告すると windows
が記載されていますが、 win
である必要があります)。
概要< br /> 。 Dockerコンテナから「Azure Storage Emulator」と「CosmosDB Emulator」を実行していたlocalhostに接続するという、同様のことをする必要がありました。< br />。
「Azure Storage Emulator」はデフォルトで 127.0.0.1 を聴きますが、IPのバインドも変更できますが、デフォルト設定で機能するソリューションを探していました。
これは、Dockerコンテナから「SQL Server」と「IIS」への接続にも機能します。どちらもデフォルトのポート設定でホストでローカルに実行されます。
編集:GitHubでコンセプトをプロトタイピングしてしまいました。 チェックアウト: https://github.com/sivabudh/system-in-a-box。
----------。
まず、私の答えは、Macを使用する人とLinuxを使用する人の2つのグループに向けられています。
host ネットワークモードはMacでは機能しません。 IPエイリアスを使用する必要があります。https://stackoverflow.com/a/43541681/2713729を参照してください。
ホストネットワークモードとは何ですか? 参照:https://docs.docker.com/engine/reference/run/#/network-settings。
次に、Linuxを使用しているユーザー(私の直接の経験はUbuntu 14.04 LTSで、間もなく16.04 LTSにアップグレードします)、はい、ドッカーコンテナー内で実行されているサービスをDockerホストで実行されている「localhost」サービス(例:. あなたのラップトップ)。
どうやって?
重要なのは、Dockerコンテナを実行するときに、 host モードで実行する必要があることです。 コマンドは次のようになります。
docker run --network = "host" -id< Docker image ID>
。
コンテナ内で「ifconfig」(「ifconfig」を呼び出すには、コンテナを「apt-get install net-tools」にする必要があります)を実行すると、ネットワークインターフェイスがDockerのインターフェイスと同じであることがわかりますホスト(例:. あなたのラップトップ)。
私はMacユーザーですが、ParallelsでUbuntuを実行しているため、Macを使用することは不利ではありません。 ;-)。
これが、NGINXコンテナを「localhost」で実行されているMySQLに接続する方法です。
Mac OSX用のシンプルなソリューション。
MacのIPアドレスを使用してください。 Macでこれを実行してIPアドレスを取得し、コンテナ内から使用します。
$ ifconfig | grep 'inet 192'| awk '{ print $2}'
Macまたは別のドッカーコンテナーでローカルに実行されているサーバーが0.0.0.0を聞いている限り、ドッカーコンテナーはそのアドレスで連絡を取ることができます。
0.0.0.0でリスニングしている別のドッカーコンテナーにアクセスする場合は、172.17.0.1を使用できます。
非常にシンプルですばやく、ifconfig(linux)またはipconfig(windows)でホストIPを確認し、aを作成します。
docker-compose.yml 。
version: '3' # specify docker-compose version
services:
nginx:
build: ./ # specify the directory of the Dockerfile
ports:
- "8080:80" # specify port mapping
extra_hosts:
- "dockerhost:<yourIP>"
このようにして、コンテナはホストにアクセスできます。 DBにアクセスするときは、前に指定した名前(この場合は「dockerhost」)と、DBが実行されているホストのポートを使用することを忘れないでください。
これは実際の質問に対する答えではありません。 これが私が同様の問題を解決した方法です。 ソリューションは完全に次の要素から得られます:[コンテナが通信できるようにドッカーコンテナネットワーキングを定義][1]。 Nic Raboyに感謝します。
これをここに残して、あるコンテナと別のコンテナ間でRESTコールを実行したい他の人のために。 質問に答えます:港湾環境のローカルホストの代わりに何を使用するか?
ネットワークが「ドッカーネットワークls」のように見える方法を取得します。
新しいネットワーク「ドッカーネットワークcreate -d my-net」を作成します。
最初のコンテナ docker run -d -p 5000:5000 --network = "my-net" --name "first_container"< MyImage1:v0.1>
を開始します。
最初のコンテナ「ドッカー検査first_container」のネットワーク設定を確認してください。 "ネットワーク": 'my-net'が必要です。
2番目のコンテナ docker run -d -p 6000:6000 --network = "my-net" --name "second_container"< MyImage2:v0.1>
を開始します。
2番目のコンテナ「ドッカー検査second_container」のネットワーク設定を確認します。 "ネットワーク": 'my-net'が必要です。
2番目のコンテナ docker exec -it second_container sh
または docker exec -it second_container bash
にsshします。
2番目のコンテナ内では、「ping first_container」を使用して最初のコンテナにpingできます。 また、「http://localhost:5000」などのコードコールは、「http://first_container:5000」に置き換えることができます。
[1]:https://www.youtube.com/watch?v = RCG-5N41FpQ。
これが私の解決策です。私の場合に機能します。
-ローカルmysqlサーバーをコメントでパブリックアクセスに設定します。 `。
`。
/etc/mysql/mysql.conf.d。
-mysqlサーバーを再起動します。
sudo /etc/init.d/mysql restart
。
-次のコマンドを実行して、ユーザーのルートアクセスを任意のホストで開きます。
mysql -uroot -proot。 すべての特権を付与*。* 'root' @ '%'に 'root'によって識別されます。 グラントオプション;。 流血の特権;。
。
-shスクリプトを作成:run_docker.sh。
。 #。!ビン/バッシュ。HOSTIP = `ip -4 addr show scope global dev eth0 | grep inet | awk '{print \ $ 2}' |カット-d / -f 1`。 ドッカー実行-it -d --name web-app \。 --add-host = local:$ {HOSTIP} \。 -p 8080:8080 \。 -e DATABASE_HOST = $ {HOSTIP} \。 -e DATABASE_PORT = 3306 \。 -e DATABASE_NAME = demo \。 -e DATABASE_USER = root \。 -e DATABASE_PASSWORD = root \。 sopheamak / springboot_docker_mysql。
< / pre>。
-ドッカーコンポーザーで実行します。
<pre>。 バージョン:「2.1」。 サービス: tomcatwar: extra_hosts: -「ローカル:10.1.2.232」。 画像:sopheamak / springboot_docker_mysql。 ポート: -8080:8080。 環境: -DATABASE_HOST = local。 -DATABASE_USER = root。 -DATABASE_PASSWORD = root。 -DATABASE_NAME =デモ。 -DATABASE_PORT = 3306。
< / pre>。
いくつかの解決策が思い浮かびます。
1。 依存関係を最初にコンテナに移動します。 2。 他のサービスに外部からアクセスできるようにし、その外部IPでサービスに接続します。 3。 ネットワークを分離せずにコンテナを実行します。 4。 ネットワーク経由の接続を避け、代わりにボリュームとしてマウントされたソケットを使用します。
これがそのままでは機能しない理由は、コンテナがデフォルトで独自のネットワーク名前空間で実行されるためです。 つまり、localhost(またはループバックインターフェイスを指す127.0.0.1)はコンテナごとに一意です。 これに接続すると、コンテナ自体に接続され、ドッカーの外や別のドッカーコンテナーの内部で実行されるサービスは接続されません。
オプション1 :依存関係をコンテナに移動できる場合は、まずこれを行います。 他のユーザーが自分の環境でコンテナを実行しようとするため、アプリケーションスタックが移植可能になります。 また、移行されていない他のサービスがまだ到達できるホストにポートを公開することもできます。 公開されたポートの「-p 127.0.0.1:3306:3306」などの構文で外部からアクセスできないように、ドッカーホストのローカルホストインターフェイスにポートを公開することもできます。
オプション2 :コンテナ内からホストIPアドレスを検出する方法はさまざまですが、それぞれが機能するシナリオの数は限られています(例:. Mac用のDockerが必要です)。 最も移植性の高いオプションは、環境変数や構成ファイルのようなものでホストIPをコンテナに注入することです。:
docker run --rm -e "HOST_IP=$(ip r s 0/0 | awk '{print $3}')" ...
これには、サービスがその外部インターフェイスを聴いていることが必要であり、これはセキュリティ上の懸念となる可能性があります。 コンテナ内からホストIPアドレスを取得する他の方法については、この投稿を参照。
オプション3 :ネットワーク分離なしで実行されます。 「--net host」で実行することは、アプリケーションがホストネットワーク名前空間で実行されていることを意味します。 これはコンテナの分離が少なく、DNSで共有ドッカーネットワークを介して他のコンテナにアクセスできないことを意味します(代わりに、公開されたポートを使用して他のコンテナ化されたアプリケーションにアクセスする必要があります)。 ただし、ホストの「127.0.0.1」でのみリッスンしているホスト上の他のサービスにアクセスする必要があるアプリケーションの場合、これが最も簡単なオプションです。
オプション4 :さまざまなサービスにより、ファイルシステムベースのソケットを介したアクセスも可能になります。 このソケットは、バインドマウントされたボリュームとしてコンテナに取り付けることができ、ネットワークを経由せずにホストサービスにアクセスできます。 ドッカーエンジンへのアクセスには、「/ var / run / docker.sock」をコンテナーに取り付ける例がよく見られます(そのコンテナーのルートにホストにアクセスできるようにします)。 mysqlを使用すると、 -v / var / run / mysqld / mysqld.sock:/var/run/mysqld/mysql.sock
のようなものを試してから、mysqlがソケットの使用に変換する localhost
に接続できます。
Thomasleveilさんの回答には反対です。
mysql を 172.17.42.1 にバインドするようにすると、そのホストでデータベースを使用している他のプログラムが、そのホストに到達できなくなります。これは、すべてのデータベースユーザがドッカー化されている場合にのみ機能します。
mysql を 0.0.0.0 にバインドすると、データベースが外部に開放されることになり、これは非常に悪いことであるだけでなく、元の質問の著者がやりたいことに反しています。彼は明確に "MySqlはlocalhostで動作しており、外部にポートを公開していないので、localhostにバインドしている" と言っています。
ivant さんのコメントにお答えします。
"mysqlもdocker0にバインドしてはどうでしょうか?"
これは不可能です。mysql/mariadbのドキュメントには、複数のインターフェースにバインドすることはできないと明確に書かれています。0, 1, またはすべてのインターフェースにバインドすることしかできません。
結論から言うと、Docker コンテナからホスト上の (localhost のみの) データベースにアクセスする方法は見つかりませんでした。これは間違いなく非常によくあるパターンのように思えますが、どうすればいいのかわかりません。
CGroupsとNamespacesは、コンテナエコシステムで主要な役割を果たしています。。
名前空間は分離の層を提供します。 各コンテナは個別の名前空間で実行され、そのアクセスはその名前空間に制限されます。 Cgroupsは各コンテナーのリソース使用率を制御しますが、Namespaceはプロセスがそれぞれのリソースを表示およびアクセスできるものを制御します。
以下は、従うことができるソリューションアプローチの基本的な理解です。
ネットワーク名空間を使用する。
コンテナが画像からスポーンすると、ネットワークインターフェイスが定義されて作成されます。 これにより、コンテナに一意のIPアドレスとインターフェイスが提供されます。
$ docker run -it alpine ifconfig
名前空間をホストに変更することにより、コタイナーネットワークはそのインターフェイスに分離されたままではなくなり、プロセスはホストマシンネットワークインターフェイスにアクセスできます。
$ docker run -it --net=host alpine ifconfig
プロセスがポートをリッスンすると、ホストインターフェイスでリッスンされ、コンテナにマップされます。
PID名前空間を使用する。 Pid名前空間を変更することにより、コンテナは通常の範囲を超えて他のプロセスと対話できます。
このコンテナは独自の名前空間で実行されます。
$ docker run -it alpine ps aux
名前空間をホストに変更することにより、コンテナはシステムで実行されている他のすべてのプロセスも表示できます。
$ docker run -it --pid=host alpine ps aux
名前空間の共有。
これは、脆弱性と盗聴者への容易なアクセスを可能にするコンテナセキュリティモデルを打ち破っているため、生産でこれを行うのは悪い習慣です。 これは、ツールをデバッグし、コンテナのセキュリティの抜け穴を過小評価する場合のみです。
最初のコンテナはnginxサーバーです。 これにより、新しいネットワークとプロセス名空間が作成されます。 このコンテナは、新しく作成されたネットワークインターフェイスのポート80にバインドされます。
$ docker run -d --name http nginx:alpine
別のコンテナがこの名前空間を再利用できるようになりました。
$ docker run --net=container:http mohan08p/curl curl -s localhost
また、このコンテナは、共有コンテナ内のプロセスとのインターフェースを確認できます。
$ docker run --pid=container:http alpine ps aux
これにより、アプリケーションを変更または再起動することなく、コンテナにより多くの特権を与えることができます。 同様に、ホストでmysqlに接続し、アプリケーションを実行してデバッグできます。 しかし、このように行くことはお勧めしません。 それが役立つことを願っています。
解決する必要がある2つの問題があります。
1。 ホストのIPを取得します。 2。 Dockerがローカルホストサービスを利用できるようにします。
最初の問題は、他の回答で与えられたように、qoomonのドッカーホスト画像を使用して解決できます。
このコンテナーを他のコンテナーと同じブリッジネットワークに追加して、コンテナーにアクセスできるようにする必要があります。 コンテナ内のターミナルを開き、ping dockerhost
ができることを確認します。
bash-5.0# ping dockerhost
PING dockerhost (172.20.0.2): 56 data bytes
64 bytes from 172.20.0.2: seq=0 ttl=64 time=0.523 ms
さて、難しい問題で、サービスをドッカーがアクセスできるようにしています。
telnetを使用して、ホスト上のポートにアクセスできるかどうかを確認できます(これをインストールする必要がある場合があります)。
問題は、当社のコンテナがSSH:などのすべてのインターフェイスにバインドするサービスにのみアクセスできることです。
bash-5.0# telnet dockerhost 22
SSH-2.0-OpenSSH_7.6p1 Ubuntu-4ubuntu0.3
ただし、localhostにのみバインドされるサービスにはアクセスできません。
bash-5.0# telnet dockerhost 1025
telnet: can't connect to remote host (172.20.0.2): Connection refused
ここでの適切な解決策は、サービスをドッカーブリッジネットワークにバインドすることです。 ただし、この回答では、これを変更することは不可能であると想定しています。 代わりに「iptables」を使用します。
まず、ドッカーが ifconfig
で使用しているブリッジネットワークの名前を見つける必要があります。 名前のないブリッジを使用している場合、これは単に「docker0」になります。 ただし、名前付きネットワークを使用している場合は、ドッカーが代わりに使用する「br-」で始まるブリッジがあります。 鉱山は「br-5cd80298d6f4」です。
このブリッジの名前を取得したら、このブリッジからlocalhostへのルーティングを許可する必要があります。 これは、セキュリティ上の理由からデフォルトで無効になっています。
sysctl -w net.ipv4.conf.<bridge_name>.route_localnet=1
次に、「iptables」ルールを設定します。 私たちのコンテナはドッカーブリッジネットワークのポートにのみアクセスできるため、サービスは実際にはこのネットワークのポートにバインドされているふりをします。
これを行うには、すべてのリクエストを < docker_bridge>:port
に localhost:port
に転送します。
iptables -t nat -A PREROUTING -p tcp -i <docker_bridge_name> --dport <service_port> -j DNAT --to-destination 127.0.0.1:<service_port>
たとえば、ポート1025でのサービス。
iptables -t nat -A PREROUTING -p tcp -i br-5cd80298d6f4 --dport 1025 -j DNAT --to-destination 127.0.0.1:1025
これで、コンテナからサービスにアクセスできるようになります。
bash-5.0# telnet dockerhost 1025
220 127.0.0.1 ESMTP Service Ready