我试图运行依赖于mysql的集成测试(在python中)。目前,它们依赖于本地运行的SQL,但我希望它们依赖于在docker中运行的MySQL。

Dockerfile的内容:

FROM continuumio/anaconda3:4.3.1
WORKDIR /opt/workdir
ADD . /opt/workdir
RUN python setup.py install

Docker Compose的内容:
version: '2'

services:
   mysql:
     image: mysql:5.6
     container_name: test_mysql_container
     environment:
       - MYSQL_ROOT_PASSWORD=test
       - MYSQL_DATABASE=My_Database
       - MYSQL_USER=my_user
       - MYSQL_PASSWORD=my_password
     volumes:
       - db_data:/var/lib/mysql
     restart: always
     expose:
       - "3306"

   my_common_package:
     image: my_common_package
     depends_on:
       - mysql
     restart: always
     links:
       - mysql

volumes:
  db_data:

现在,我尝试使用以下命令运行软件包中的测试:
docker-compose run my_common_package python testsql.py

我收到错误

最佳答案

默认情况下,docker-compose将创建虚拟网络,前提是撰写文件中的所有容器/服务都可以通过IP地址相互访问。通过使用linksdepends_on或网络别名,它们可以通过主机名相互访问。在您的情况下,主机名是服务名,但是可以覆盖它。 (请参阅:docs)

然后,您根据自己的设置将my_common_package容器/服务中的脚本连接到mysql端口上的3306。 (不是localhost端口上的3306)

还要注意,仅当服务的Dockerfile没有expose语句时,才需要使用EXPOSE。标准的mysql镜像已经做到了。

如果要将容器端口映射到localhost,则需要使用ports,但仅在必要时使用。

services:
   mysql:
     image: mysql:5.6
     container_name: test_mysql_container
     environment:
       - MYSQL_ROOT_PASSWORD=test
       - MYSQL_DATABASE=My_Database
       - MYSQL_USER=my_user
       - MYSQL_PASSWORD=my_password
     volumes:
       - db_data:/var/lib/mysql
     ports:
       - "3306:3306"

在这里我们说的是mysql容器中的端口3306应该映射到端口3306上的localhost。

现在,您可以在docker外部使用localhost:3306连接到mysql。例如,您可以尝试在本地运行testsql.py(不在容器中)。

容器到容器的通信将始终使用每个容器的主机名进行。将容器视为虚拟机。

您甚至可以找到使用docker network list创建的网络docker-compose:
1b1a54630639        myproject_default             bridge              local
82498fd930bb        bridge                        bridge              local

..然后使用docker network inspect <id>查看详细信息。

分配给容器的IP地址可能是非常随机的,因此,容器间通信的唯一可行方法是使用主机名。

07-24 09:39
查看更多