在 .gitlab-ci.yml 中运行 docker-compose build
Posted
技术标签:
【中文标题】在 .gitlab-ci.yml 中运行 docker-compose build【英文标题】:Run docker-compose build in .gitlab-ci.yml 【发布时间】:2017-02-13 13:38:10 【问题描述】:我有一个.gitlab-ci.yml
文件,其中包含以下内容:
image: docker:latest
services:
- docker:dind
before_script:
- docker info
- docker-compose --version
buildJob:
stage: build
tags:
- docker
script:
- docker-compose build
但是在ci-log
我收到消息:
$ docker-compose --version
/bin/sh: eval: line 46: docker-compose: not found
我做错了什么?
【问题讨论】:
【参考方案1】:编辑我添加了另一个答案,为支持 docker-compose 的 .gitlab-ci.yml 配置提供了一个最小示例。
docker-compose
可以作为 Python 包安装,该包不随您的图像一起提供。您选择的图像甚至没有提供 Python 的安装:
$ docker run --rm -it docker sh
/ # find / -iname "python"
/ #
寻找 Python 会得到一个空的结果。所以你必须选择一个不同的镜像,它适合你的需求,最好安装 docker-compose 或者你自己创建一个。
您选择的 docker 映像使用 Alpine Linux。如果您不熟悉 Alpine Linux,您可以将其用作您自己的镜像的基础,或者先尝试其他镜像。
我遇到了同样的问题,我在公共 GitHub 存储库中创建了一个 Dockerfile,并将它与我的 Docker Hub 帐户连接起来,并选择了一个自动构建来在每次推送到 GitHub 存储库时构建我的图像。然后,您可以使用 GitLab CI 轻松访问自己的图像。
【讨论】:
您可以删除其中一个答案吗?很困惑地找到两个,加上很多“编辑”消息。 (如果需要,我们可以查看编辑历史记录)。【参考方案2】:如果您不想提供预安装了 docker-compose 的自定义 docker 映像,则可以通过在构建期间安装 Python 来使其正常工作。安装 Python 后,您终于可以安装 docker-compose 以启动容器了。
image: docker:latest
services:
- docker:dind
before_script:
- apk add --update python py-pip python-dev && pip install docker-compose # install docker-compose
- docker version
- docker-compose version
test:
cache:
paths:
- vendor/
script:
- docker-compose up -d
- docker-compose exec -T php-fpm composer install --prefer-dist
- docker-compose exec -T php-fpm vendor/bin/phpunit --coverage-text --colors=never --whitelist src/ tests/
如果您收到此错误或类似错误,请使用 docker-compose exec 和 -T:
$ docker-compose exec php-fpm composer install --prefer-dist
Traceback (most recent call last):
File "/usr/bin/docker-compose", line 9, in <module>
load_entry_point('docker-compose==1.8.1', 'console_scripts', 'docker-compose')()
File "/usr/lib/python2.7/site-packages/compose/cli/main.py", line 62, in main
command()
File "/usr/lib/python2.7/site-packages/compose/cli/main.py", line 114, in perform_command
handler(command, command_options)
File "/usr/lib/python2.7/site-packages/compose/cli/main.py", line 442, in exec_command
pty.start()
File "/usr/lib/python2.7/site-packages/dockerpty/pty.py", line 338, in start
io.set_blocking(pump, flag)
File "/usr/lib/python2.7/site-packages/dockerpty/io.py", line 32, in set_blocking
old_flag = fcntl.fcntl(fd, fcntl.F_GETFL)
ValueError: file descriptor cannot be a negative integer (-1)
ERROR: Build failed: exit code 1
【讨论】:
不是一般的方式,其实可以得到“apk: command not found” 这不再有效,可能是因为更新的 docker 镜像。现在python
和python-dev
不再是有效的apk包添加,然后当你指定python2时,gcc
不知何故丢失了【参考方案3】:
我创建了一个简单的 docker 容器,它在 docker:latest
之上安装了 docker-compose
。见https://hub.docker.com/r/tmaier/docker-compose/
您的.gitlab-ci.yml
文件如下所示:
image: tmaier/docker-compose:latest
services:
- docker:dind
before_script:
- docker info
- docker-compose --version
buildJob:
stage: build
tags:
- docker
script:
- docker-compose build
【讨论】:
在 gitlab cierror: command 'gcc' failed with exit status 1
中得到这个错误【参考方案4】:
关注official documentation:
# .gitlab-ci.yml
image: docker
services:
- docker:dind
build:
script:
- apk add --no-cache docker-compose
- docker-compose up -d
示例 docker-compose.yml:
version: "3.7"
services:
foo:
image: alpine
command: sleep 3
bar:
image: alpine
command: sleep 3
我们个人不再遵循此流程,因为您失去了对正在运行的容器的控制,它们最终可能会无休止地运行。这是因为 docker-in-docker 执行器。我们开发了一个 python 脚本作为解决方法来杀死我们 CI 中的所有旧容器,can be found here。但我不建议再像这样启动容器了。
【讨论】:
@tmaier 我想我也被困在这里了。您使用了哪种“Runner-Installation”?我的意思是你走的三种方式中的哪一种? docs.gitlab.com/ee/ci/docker/… 我们正在使用 docker-in-docker 执行器docs.gitlab.com/ee/ci/docker/… 虽然这可行,但这意味着在每个构建时都需要安装(并获取...)docker-compose,因此它会增加构建时间。如果您有多个需要 docker-compose 的作业(并且在生产场景中您可能会这样做),构建时间将大大增加。 如果您想更频繁地使用它,您可以使用包含在线三行的小型 Dockerfile 为您的 CI 定义自己的 docker 映像:` FROM alpine \n RUN apk add --no-cache py -pip && pip install docker-compose ` 但请记住要始终保持此映像是最新的 非常感谢您的回答。我只是有网络问题。似乎没有容器可以与另一个容器通信……这种情况下只有我一个吗? (使用共享跑步者)【参考方案5】:Docker还提供了一个官方镜像:docker/compose
如果您不想在每条管道上都安装它,这是理想的解决方案。
请注意,在最新版本的 GitLab CI/Docker 中,您可能需要授予对 GitLab CI Runner 的特权访问权限并配置/禁用 TLS。见Use docker-in-docker workflow with Docker executor
variables:
DOCKER_HOST: tcp://docker:2375/
DOCKER_DRIVER: overlay2
# Official docker compose image.
image:
name: docker/compose:latest
services:
- docker:dind
before_script:
- docker version
- docker-compose version
build:
stage: build
script:
- docker-compose down
- docker-compose build
- docker-compose up tester-image
请注意,在 docker-compose
earlier than 1.25 的版本中:
由于图像使用
docker-compose-entrypoint.sh
作为入口点,您需要在.gitlab-ci.yml
中将override it 返回到/bin/sh -c
。否则,您的管道将失败并显示No such command: sh
image:
name: docker/compose:latest
entrypoint: ["/bin/sh", "-c"]
【讨论】:
这可行,但正如您的链接源所说,它需要一个 GitLab *9.4**+ ,因为您**需要覆盖 CI yaml 中的入口点。 @webmaster777 执行到“docker-compose 版本”时出现此错误...Cannot connect to the Docker daemon at unix:///var/run/docker.sock. Is the docker daemon running? ERROR: Job failed: exit code 1
...我该如何解决?
只有在我添加变量DOCKER_HOST: tcp://docker:2375/
和DOCKER_DRIVER: overlay2
时才有效
有效!如果涉及绑定挂载或卷,则还需要一些环境变量——DOCKER_HOST=tcp://docker:2375
和DOCKER_DRIVER=overlay2
(可选)——指示 docker 与服务内部启动的守护进程(docker:dind
)进行对话。更多信息请参考Use docker-in-docker executor。
即使设置了所有变量,这对我(共享的 gitlab.com 跑步者)仍然不起作用,Cannot connect to the Docker daemon at tcp://docker:2375/. Is the docker daemon running?
【参考方案6】:
Alpine linux 现在在其“edge”分支中有一个 docker-compose 包,因此您可以在 .gitlab-ci.yml 中以这种方式安装它
a-job-with-docker-compose:
image: docker
services:
- docker:dind
script:
- apk add docker-compose --update-cache --repository http://dl-3.alpinelinux.org/alpine/edge/testing/ --allow-untrusted
- docker-compose -v
【讨论】:
不工作..需要更新答案..运行时docker-compose
抛出pkg_resources.DistributionNotFound: The 'docker-compose==1.24.0' distribution was not found and is required by the application
【参考方案7】:
我认为上面的大部分内容都很有帮助,但是我需要将它们共同应用来解决这个问题,下面是对我有用的脚本
我希望它也对你有用
另外请注意,在您的 docker compose 中,这是您必须为图像名称提供的格式
<registry base url>/<username>/<repo name>/<image name>:<tag>
image:
name: docker/compose:latest
entrypoint: ["/bin/sh", "-c"]
variables:
DOCKER_HOST: tcp://docker:2375/
DOCKER_DRIVER: overlay2
services:
- docker:dind
stages:
- build_images
before_script:
- docker version
- docker-compose version
- docker login -u $CI_REGISTRY_USER -p $CI_JOB_TOKEN $CI_REGISTRY
build:
stage: build_images
script:
- docker-compose down
- docker-compose build
- docker-compose push
【讨论】:
【参考方案8】:我真的花了一些时间才让它与 Gitlab.com 共享跑步者一起工作。
我想说“使用 docker/compose:latest
就是这样”,但不幸的是我无法让它工作,即使设置了所有 env 变量,我也会收到 Cannot connect to the Docker daemon at tcp://docker:2375/. Is the docker daemon running?
错误。
我也不喜欢安装五千个依赖项以通过 pip 安装 docker-compose
的选项。
幸运的是,对于最近的 Alpine 版本(3.10+),Alpine 存储库中有 docker-compose 包。这意味着@n2o 的answer 可以简化为:
test:
image: docker:19.03.0
variables:
DOCKER_DRIVER: overlay2
# Create the certificates inside this directory for both the server
# and client. The certificates used by the client will be created in
# /certs/client so we only need to share this directory with the
# volume mount in `config.toml`.
DOCKER_TLS_CERTDIR: "/certs"
services:
- docker:19.03.0-dind
before_script:
- apk --no-cache add docker-compose # <---------- Mind this line
- docker info
- docker-compose --version
stage: test
script:
- docker-compose build
这对我来说从第一次尝试就完美了。也许其他答案没有的原因是在 Gitlab.com 共享跑步者的某些配置中,我不知道......
【讨论】:
这真的是 2021 年的解决方案,所有其他人都没有使用自定义跑步者【参考方案9】:tiangolo/docker-with-compose
有效:
image: tiangolo/docker-with-compose
stages:
- build
- test
- release
- clean
before_script:
- docker login -u gitlab-ci-token -p $CI_BUILD_TOKEN registry.gitlab.com
build:
stage: build
script:
- docker-compose -f docker-compose-ci.yml build --pull
test1:
stage: test
script:
- docker-compose -f docker-compose-ci.yml up -d
- docker-compose -f docker-compose-ci.yml exec -T php ...
【讨论】:
这对我不起作用。我收到“连接期间出错:发布docker:2375/v1.40/auth:拨打tcp:在169.254.169.254:53 上查找docker:没有这样的主机”。然而,webmaster777 的解决方案对我有用,并且似乎是最好的解决方案,因为创建 tiangolo/docker-with-compose 的主要原因是因为 docker/compose 之前存在入口点问题。既然这不是问题,我认为这可能不再是一个好的解决方案。以上是关于在 .gitlab-ci.yml 中运行 docker-compose build的主要内容,如果未能解决你的问题,请参考以下文章
gitlab-ci.yml、before_script 和 artifact
获取使用 .gitlab-ci.yml 运行的 Windows Docker 容器
如何使用 gitlab-ci.yml 在 gitlab 中更新 JSON 文件的内容?