You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Gitlab CI Registry变量配置问题:docker-compose运行报错排查

问题排查:GitLab CI/CD中Docker Compose无法识别CI变量

我在配置GitLab CI/CD时,按照要求把镜像名格式$CI_REGISTRY/organisation/path-to-project/project_image:$CI_ENVIRONMENT_SLUG-$CI_COMMIT_SHA写入.env文件的IMAGE_NAME变量。但执行docker compose up时,提示这些CI变量未设置,镜像格式无效。奇怪的是,.gitlab-ci.yml的before_script里docker login -u $CI_REGISTRY_USER -p $CI_REGISTRY_PASSWORD $CI_REGISTRY能正常使用这些变量。

报错信息

level=warning msg="The \"CI_REGISTRY\" variable is not set. Defaulting to a blank string."
level=warning msg="The \"CI_ENVIRONMENT_SLUG\" variable is not set. Defaulting to a blank string."
level=warning msg="The \"CI_COMMIT_SHA\" variable is not set. Defaulting to a blank string."
Error response from daemon: no such image: organisation/path-to-project/project_image:-: invalid reference format

相关配置

.gitlab-ci.yml配置

image: docker/compose:alpine-1.28.0

stages:
  - build
  - deploy

before_script:
  - apk add make
  - docker login -u $CI_REGISTRY_USER -p $CI_REGISTRY_PASSWORD $CI_REGISTRY
  - cp $ENV $(pwd)/src/.env

build:
  stage: build
  script:
    - make build push
  tags:
    - job:build
  only:
    - main
  environment:
    name: production

deploy:
  stage: deploy
  script:
    - make pull down migrate up
  tags:
    - job:deploy
  only:
    - main
  environment:
    name: production

注:$ENV是GitLab上配置的变量。

docker-compose.yml配置

services:
  app1:
    build: .
    image: ${IMAGE_NAME}
    env_file:
      - .env
    # ...

  app2:
    build: .
    image: ${IMAGE_NAME}
    env_file:
      - .env
    # ...
问题原因及解决方法

核心原因

直接把包含CI变量的字符串写入.env文件是无效的——GitLab CI的变量仅在CI运行环境中生效,.env文件里的$CI_REGISTRY这类变量不会被CI自动解析替换。当Docker Compose读取.env时,这些变量在当前环境中不存在,会被替换为空字符串,最终导致镜像名格式错误。

解决步骤

方法1:动态生成.env文件

不要直接复制预先写好的.env文件,而是通过模板动态生成:

  1. 在代码仓库中保存.env模板文件(比如命名为.env.template),内容用占位符代替CI变量:
    IMAGE_NAME={{CI_REGISTRY}}/organisation/path-to-project/project_image:{{CI_ENVIRONMENT_SLUG}}-{{CI_COMMIT_SHA}}
    # 其他环境变量...
    
  2. 在.gitlab-ci.yml的before_script中,用envsubst替换模板占位符生成实际.env:
    - envsubst < .env.template > $(pwd)/src/.env
    
    CI运行时会自动将环境变量值填入占位符,生成正确的IMAGE_NAME。

方法2:直接给Docker Compose传入变量

跳过.env文件,在执行docker compose命令时直接注入变量:
修改deploy阶段的script命令:

- IMAGE_NAME="$CI_REGISTRY/organisation/path-to-project/project_image:$CI_ENVIRONMENT_SLUG-$CI_COMMIT_SHA" docker compose up -d

Docker Compose会直接使用CI环境中的变量值,无需读取.env。

方法3:通过makefile传递变量

如果依赖makefile执行构建/部署命令,在CI调用make时传入变量:

# build阶段
- make build push IMAGE_NAME="$CI_REGISTRY/organisation/path-to-project/project_image:$CI_ENVIRONMENT_SLUG-$CI_COMMIT_SHA"
# deploy阶段
- make pull down migrate up IMAGE_NAME="$CI_REGISTRY/organisation/path-to-project/project_image:$CI_ENVIRONMENT_SLUG-$CI_COMMIT_SHA"

同时调整makefile中的对应命令,使用传入的IMAGE_NAME变量。

内容的提问来源于stack exchange,提问作者fgrd4035

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.23 14:52:42