DEBUG.WIKI
ZgoCloud:多地区部署,按需选节点;日本、美国、香港、德国
雨云;给项目一台云服务器
RackNerd;$21.99/年 · 1GB KVM

Compose 构建正常,Dev Container 的 COPY 找不到文件:核对忽略规则

Dev Container生成扩展Dockerfile后,原专用忽略文件可能不再被选中。对照真实override和context,再审查根规则及镜像输入。

同一项目用 docker compose build 能复制 requirements.txt,进入 Dev Container 构建却报 failed to calculate checksum、文件 not found。文件仍在正确的构建上下文内时,检查开发工具实际使用的 Dockerfile,以及跟随它生效的忽略文件;普通 Compose 与 Dev Container 可能没有使用同一份构建输入。

下面针对 Dev Containers 采用 Compose,并生成扩展 Dockerfile 的构建路径。不是所有 Dev Container 都会触发,也不能据此认定 Docker 的忽略文件优先级失效。

对应的忽略文件跟着实际 Dockerfile 名称走

Docker 默认读取上下文根目录的 .dockerignore。指定的 Dockerfile 旁若有以其文件名加 .dockerignore 命名的专用文件,则专用规则优先。例如:

project/
├── .dockerignore
├── app/
│   └── requirements.txt
└── .devcontainer/
    └── app/
        ├── Dockerfile
        └── Dockerfile.dockerignore

假设 Compose 的 context 指向 project,dockerfile 指向 .devcontainer/app/Dockerfile,普通构建会采用那份专用忽略文件。换成 dev.Dockerfile 时,对应名称也应是 dev.Dockerfile.dockerignore,而不是固定叫 Dockerfile.dockerignore。

文件在上下文外的情况,应先按COPY 构建上下文检查处理。这里只讨论 context 已正确,但不同入口过滤出了不同文件的情况。

从 Dev Container 日志查看最终构建入口

保存普通 Compose 与 Dev Container 的构建日志,对照目标服务、context、全部覆盖配置、dockerfile 路径和构建目标。特别留意开发工具输出的构建 override,以及类似 Dockerfile-with-features 的临时文件。

Dev Containers CLI 0.80.2 的 Compose 扩展构建分支会在存在 featureBuildInfo 时写入临时 Dockerfile-with-features,并把覆盖配置中的 dockerfile 指向它。在这个分支中,原 Dockerfile 邻接的专用忽略文件没有随之复制过去。原 context 可以保持不变,但选择专用忽略文件所依据的 Dockerfile 已经变了。

这个版本说明用于界定已经核对的实现,不表示所有新旧版本、所有开发配置都相同。现场必须看到相应构建分支;日志没有生成扩展 Dockerfile 时,应继续查实际忽略规则、路径大小写和其他输入差异。

还要确认失败发生在构建 COPY,而不是启动后挂载的工作区。workspaceFolder 与运行时 volumes 不会把被构建过滤掉的文件重新送进 builder。

将必要文件纳入根规则前,审查其他构建

已经确认 Dev Container 采用上下文根规则时,可以在该规则中允许构建必需的普通文件。例如根 .dockerignore 原本排除所有文件,仅需提供 app 下的一份普通依赖清单,可表达为:

*
!app/
app/**
!app/requirements.txt

目录例外之后重新排除 app 内的内容,再仅允许 requirements.txt;只写 !app/ 再放行清单,会连带重新纳入其他子项,不应忽略这一步。规则顺序有意义,应检查 .env 等其他文件仍被排除。

这只是对应示例结构的最小规则,不是整份项目忽略文件的替换方案。保留其他必要规则,并检查后面的模式是否再次排除目标。requirements.txt 不应包含凭据或以敏感私有地址代替凭据管理。

根规则可能被项目的其他 Dockerfile 共用,修改前逐个确认受影响范围;仅为这一个开发服务增加输入,也可能改变另一个使用 COPY . ... 的构建。不要删除 .dockerignore,或笼统放行全部 .env、私钥与配置目录。

如果多个服务确实需要不同输入集合,应保留明确的构建隔离设计,评估工具支持的入口或预构建镜像流程,而不是不断扩大根规则。手工修改一次生成的临时 Dockerfile 或在旁边补文件,也容易在下次生成时丢失,不能当作稳定项目配置。

在构建产物中检查文件

保存修改前的 Compose、开发配置、两类忽略文件与镜像标识,在不带真实秘密的隔离副本中验证。应检查 Dev Container 实际生成的构建参数,再核对镜像阶段中的依赖清单是否为预期内容,以及不该进入上下文的文件仍被排除。

构建通过后继续验证开发工具需要的功能、应用依赖与启动行为。只看到 COPY 不再报错,还不能说明输入范围正确;扩大规则也可能让多余文件悄悄进入镜像。

若以前的错误规则已经把秘密带进镜像或缓存,仅修正新规则不会删除旧副本,需另按实际暴露范围处理。多阶段构建在 RUN 后生成的文件则属于另一条路径,可参照忽略规则与阶段产物区分。

需要回退时一并恢复规则与配套构建配置。不要删除开发数据卷来修复构建输入,也不要把升级工具自动视为问题已修复;仍应核对升级版本实际生成的 Dockerfile、忽略文件与最终产物。