网上有很多人以不同的方式问这个问题,但没有明确的答案。有人能充分理解为什么当<code>package-lock.json</code>文件存在于应用程序中时,<code>docker build</code<会失败,但当它不存在时,却能成功运行吗?看起来这与npm有关,但目前尚不清楚。
每个人都说删除< code>package-lock.json,但是它的存在是有原因的。
注意:npm 安装
在我的本地机器上工作正常,只是在 docker 容器中失败。
如果我有这个Dockerfile:
# First Stage: Builder
FROM node:13.12.0-alpine AS build
WORKDIR /app
COPY package*.json ./
RUN npm install
COPY . .
RUN npm run build
然后运行这个:
docker build -t container-tag ./
我明白了。
npm WARN tar ENOENT: no such file or directory, open '/app/node_modules/.staging/eventsource-c2615740/example/index.html'
npm WARN tar ENOENT: no such file or directory, open '/app/node_modules/.staging/eventsource-c2615740/example/sse-client.js'
npm WARN tar ENOENT: no such file or directory, open '/app/node_modules/.staging/react-router-a14663ae/README.md'
但是这个Dockerfile文件将成功运行:
# First Stage: Builder
FROM node:13.12.0-alpine AS build
WORKDIR /app
COPY package.json ./ #<-------- note that there is no star here
RUN npm install
COPY . .
RUN npm run build
您的本地构建成功但Docker构建失败的一些原因可能是(按可能性顺序)
但是,我无法解释为什么从 COPY 中省略 package-lock.json
会使构建工作。因此,问题也可能涉及:
包lock.json
时,您npm在本地安装
-ed,安装的节点版本与Dockerfile中指定的节点版本不同包lock.json
时,您在本地构建的操作系统与AlpineLinux包lock.json
时,您npm在本地安装
-ed,安装位置与Docker容器的npm版本不同,它可能对lockfile关系有不同的处理所有这些操作都可能导致生成 package-lock.json
,这可能会导致容器中的 npm 安装
(并且更可能导致 npm ci
)失败。我不确定为什么这些会导致您发布的特定错误。
如果这些原因可能是问题所在,那么问题的正确解决方案肯定是在您打算发布代码的同一个docker容器规范中进行所有npm操作(包括生成和操作package.json
和package-lock.json
),并找到一种将结果从那里提交到源代码控制的方法。这可能会因为一些问题而变得复杂,比如在您推送源代码更改的同一环境中需要构建node_modules
(例如,构建步骤的结果需要推送到容器中,或者需要安装的git钩子)。我还没有看到这个问题的完美解决方案
从你的问题:
注意:npm 安装在我的本地机器上工作正常,只是在 docker 容器中失败
如果您使用的是npm install
,则不确定是否具有相同版本的依赖项。
为了拥有一个可复制的环境,而不会因为依赖关系的不同版本而出现意外问题,您最好使用npm-ci
(干净安装):
此命令类似于npm-install,不同之处在于它适用于自动化环境,如测试平台、持续集成和部署,或者任何需要确保完全安装依赖项的情况。通过跳过某些面向用户的功能,它可以比常规npm安装快得多。它也比常规安装更严格,这可以帮助捕获大多数npm用户增量安装本地环境引起的错误或不一致。
简而言之,使用npm install和npm ci的主要区别在于:
Fabian Gander的一篇文章进一步阐明了< code>npm install和< code>npm ci工具,并就何时使用每种工具提供了建议。下表来自以下来源:
cases | npm install | npm ci
--------------------------------------|-------------|-------------
needs package.json | no | yes
needs package-lock.json | no | yes
installs from package.json | yes | no
installs from package-lock.json | no | yes
compares both | no | yes
updates loose package versions | yes | no
updates loose dependencies | yes | no
writes to package.json | yes | no
writes to package-lock.json | yes | no
deletes node_modules before install | no | yes
used for installing separate package | yes | no
should be used on build systems / CI | no | yes
can be used for development | yes | yes
reproducible installs | no | yes
这就是package-lock.json存在的原因,它可用于像< code>npm ci这样的工具。
在拥有可重现的环境后,如果这不能解决您的问题,您需要继续调查,但 IMO 这应该是第一步。
问题内容: 我最近才升级到 npm @ 5 。我现在有一个 package-lock.json 文件,其中包含 package.json中的 所有内容。我希望当我运行该程序时,将从锁定文件中提取依赖项版本,以确定应该在我的 node_modules 目录中安装什么。奇怪的是,它实际上最终修改并重写了 package-lock.json 文件。 例如,锁定文件的打字稿指定为版本 2.1.6 。然后,
我错过了什么?如何让npm真正尊重我的锁文件?
npm@5已经发布,它有一个新的功能文件(在之后),这让我很困惑。我想知道,这个文件有什么效果?
问题内容: 我在后台运行一个容器 它迅速退出。但是,如果我在前台运行,则可以正常运行。我使用检查了日志 没有错误。有任何想法吗? DOCKERFILE start-all.sh 问题答案: 一个Docker容器的主要过程完成后退出。 在这种情况下,它将在脚本结束时退出。我对hadoop不太了解,无法在这种情况下告诉您如何做,但是您需要要么在前台运行某些东西,要么使用诸如runit或supervis
问题内容: 好吧,我试图理解并阅读可能导致它的原因,但我却无法理解: 我的代码中有这个地方: 事实是,当它尝试调用某些方法时,它将引发而不是其他预期的异常(特别是)抛出 。我实际上知道调用了什么方法,所以我直接转到该方法代码,并为应该抛出的行添加了一个块 ,它实际上按预期抛出。然而,当它上升时,以某种方式更改了上面的代码并没有 按预期进行。 是什么原因导致这种行为的?我该如何检查? 问题答案: 通
我在尝试构建最新Spark的干净版本时出现了构建错误。我做了以下工作 1)git克隆https://github.com/apache/spark.git ... 生成失败... [错误]无法执行目标org.apache.maven.plugins:maven-enforcer-plugin:1.4:Enforce(enforce-versions)on project spark-parent2
我一直在阅读docs编写Dockerfiles的最佳实践。我遇到了小错误(IMHO),在进一步阅读后,其含义很清楚: 在RUN语句中单独使用apt-get更新会导致缓存问题和后续apt-get安装指令失败。 我想知道为什么失败。后来解释了他们所说的“失败”是什么意思: 由于apt get更新未运行,您的构建可能会获得过时版本的curl和nginx包。 但是,对于以下内容,我仍然无法理解他们所说的“
问题内容: 我添加了一个构建步骤来执行Python脚本。 在此脚本中,使用lint.Run(.. args)调用pylint来检查代码。 该脚本可以工作,但是最后,构建失败,并显示唯一的错误消息: 有人知道为什么会这样吗? 问题答案: 看来您的pylint执行退出状态为非零(缺少脚本,错误的选项…),也许您在退出脚本时引发了异常或