我试图运行依赖于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地址相互访问。通过使用links
,depends_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地址可能是非常随机的,因此,容器间通信的唯一可行方法是使用主机名。