GitLab CI 使用 Docker in Docker 无法访问 services 的坑
2019 12 26 02:12 PM 592次查看
.gitlab-ci.yml 配置时,发现一个域名无法解析的问题,部分配置如下:variables:
MYSQL_DATABASE: test
MYSQL_ROOT_PASSWORD: test
test:
stage: test
services:
- mysql:5.7
- redis:4
script:
- apk update && apk add mysql-client
- mysql -h mysql -u root -ptest < init.sql
- docker build -t test .
- docker run -t test pytest tests在执行
mysql -h mysql -u root -ptest < init.sql 的时候,代码顺利地通过了;但在执行 docker run -t test pytest tests 的时候,却会报解析不了 mysql 的异常。以我所知,Docker in Docker(dind) 实际上是调用宿主机的 Docker 进程,因此我尝试分析了一下原因:
假设宿主机叫
ci,在执行 test job 时,它会先启动 mysql 和 redis 这两个服务。这两个服务是运行在容器里的,ci 知道它们的 IP,但并不修改自己的域名解析。接着
ci 再启动一个容器(假设叫 container1),加载 dind 镜像,向 /etc/hosts 注入 mysql 和 redis 这两个域名的 IP,然后执行 script 里的代码。因此,container1 是能解析 mysql 和 redis 这两个域名的。然后
container1 在执行 docker run -t test pytest tests 的时候,实际上是调用 ci 的 Docker 来启动一个新容器(假设叫 container2)。然而 ci 并不会向 container2 注入这个两域名,container2 也无法通过桥接的网络来解析它们,于是就报错了。虽然我不知道 GitLab CI 是否有标准的解决方案,但至少我手动注入域名是可以解决的:
script:
- apk update && apk add mysql-client
- mysql -h mysql -u root -ptest < init.sql
- mysql=`grep mysql /etc/hosts | awk '{print $1}'`
- redis=`grep redis /etc/hosts | awk '{print $1}'`
- docker build -t test .
- docker run --add-host mysql:$mysql --add-host redis:$redis -t test pytest tests
0条评论 你不来一发么↓