首页 > 解决方案 > 如何使用容器名称从 linux 物理机/主机操作系统连接为 mysql 主机?

问题描述

我使用 docker-compose 连接 mysql 容器查看详细信息

我想使用容器名称作为主机连接到它,但连接被拒绝。
使用 host=localhost 可以通过。

我的谷歌搜索在我们的 stackoverflow 上的搜索只给出指向使用内部 IP的结果,例如我不寻找的这篇文章。

所以我的问题是如何在连接时使用docker 容器名称作为 mysql 主机?

标签: mysqllinuxdocker

解决方案


Update: As pointed out by David Maze, the solution is OS Host specific dependant.

The OP never mentioned his Host type at the time of answering, so this solution I created is for a Linux OS host/Linux Container (and works with the OP's mariadb image).

To answer the question of container name:

There seems to be no direct way for the host to be aware of the container name itself, but docker-compose does create cpe-* entries into the firewall automatically for multi-service docker-compose projects. NOTE: These cpe entries are auto-named, and I am not aware of any way of changing those names*`

These entries resolve to the internal container IP when you ping them from the host, so you can use them instead of container name.

HOWEVER, Since this is a singular service docker-compose project (only MariaDB), it seems Docker does not create those entries automatically. You will have to create a manual host entry inside /etc/hosts so that it can resolve to container IP. Read on....

Assuming you use that docker-compose.yml with your up.sh, this is how was able to connect to a new Docker container created (from your project linked). I was able to connect to the MySQL container instance from the Host.

Before the container could even start (show nothing in docker ps), I saw that the port is 3306, it failed to start at first - because I already have a MySQL instance on that port, so this made it easy to find port!

Steps

I removed the volumes section because I don't know how they interact with your container

After running up.sh:

$ docker ps
7c13bf1855a0        bitnami/mariadb:10.3      "/opt/bitnami/script…" 4 minutes ago    Up 4 minutes   0.0.0.0:3306->3306/tcp 
 nn_mariadb

I see a new network created:

$ docker network ls
86d2c3211505        mariadb_default                   bridge              local

docker network inspect mariadb_default
(PARTIAL ONLY): 

 "Containers": {
            "7c13bf1855a083f4cba3071edc03b671346a9e8efbe60b6b4d9585113b542020": {
                "Name": "nn_mariadb",
                "EndpointID": "603851d3e134aedef126febb0c30786a5564cccd4f3803cfe965a80ed747df7a",
                "MacAddress": "02:42:ac:12:00:02",
                "IPv4Address": "172.18.0.2/16",
                "IPv6Address": ""
            }
        },

This means the IP Address of the new container is 172.18.0.2

Verify with ping on host to container IP:

myuser@myserver:/var/www/docker/stackoverflow.help/mariadb$ ping 172.18.0.2
PING 172.18.0.2 (172.18.0.2) 56(84) bytes of data.
64 bytes from 172.18.0.2: icmp_seq=1 ttl=64 time=0.107 ms
64 bytes from 172.18.0.2: icmp_seq=2 ttl=64 time=0.104 ms

Entering the container: The container does not have ping etc to verify network, but it worked as described below

docker exec -ti nn_mariadb bash

I have no name!@7c13bf1855a0:/$ mysql -u root -p -h 172.18.0.2 -P 3306
MariaDB [(none)]>

From the host to the container:

myuser@myserver:/var/www/docker/stackoverflow.help/mariadb$ mysql -u root -p -h 172.18.0.2 -P 3306
Enter password:
Welcome to the MySQL monitor.  Commands end with ; or \g.
Your MySQL connection id is 16
Server version: 5.5.5-10.3.24-MariaDB Source distribution

Copyright (c) 2000, 2020, 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> SHOW DATABASES;
+--------------------+
| Database           |
+--------------------+
| information_schema |
| mysql              |
| performance_schema |
| test               |
+--------------------+
4 rows in set (0.00 sec)

mysql>

Finally:

NOTE: I assume that your host generates the firewall entry automatically based on this : 0.0.0.0:3306->3306/tcp nn_mariadb

Firewall may interfere if port 3306 does not want to connect as I did above.

Can container name be used directly?

It does not seem the host is directly aware of the container name. Some docker-compose projects do add items into the firewall like this :

ACCEPT     tcp  --  anywhere cpe-172-100-0-2.twcny.res.rr.com  tcp dpt:http
ACCEPT     tcp  --  anywhere cpe-172-100-0-3.twcny.res.rr.com  tcp dpt:6379
ACCEPT     tcp  --  anywhere cpe-172-100-0-5.twcny.res.rr.com  tcp dpt:http-alt
ACCEPT     tcp  --  anywhere cpe-172-100-0-4.twcny.res.rr.com  tcp dpt:6082
ACCEPT     tcp  --  anywhere cpe-172-100-0-4.twcny.res.rr.com  tcp dpt:6081

I assume it only relates to multi-service docker-compose projects

However, these cpe-* names are auto-generated even if you customize your docker network. You can then connect via this name because it resolves to the container IP.

As mentioned above, it seems it only creates entries like those into the firewall when multi-service docker-compose projects are done, with this singular container it only creates:

ACCEPT     tcp  --  anywhere             172.18.0.2           tcp dpt:mysql

What can I do when these entries are not generated?

TLDR: You cannot use the container name automatically - you will have to create a custom entry.

Add the entry into your host etc/hosts file:

172.18.0.2  maria_db_host

Then:

$ mysql -u root -p -h maria_db_host -P 3306

推荐阅读