Docker生产环境代码构建

5
在使用Docker创建生产构建时,人们通常采用什么样的策略来编译和打包代码?
在Docker之外的世界中,我会创建一个构建(使用某种npm命令),它将创建一个没有任何源代码、被压缩和混淆的dist文件夹,然后我将网页服务器指向该dist文件夹。
在Docker世界中,您会在哪里构建代码?是在Docker镜像中还是在主机操作系统上,并将dist文件夹复制到Docker镜像中?基本上,我不想在Docker镜像/容器中放置整个npm_modules和所有源代码文件。
有什么好的方法可以实现这一点吗?
谢谢。

1
您可能也感兴趣了解 多阶段 Docker 构建 - Oliver Charlesworth
基本上,我不想在Docker镜像/容器中包含整个npm_modules和所有源代码文件。- 为什么不这样做? - Constantin Galbenu
1
这是因为它会使图像大小变大,当应用程序正在运行时不使用node_modules,并且在生产中部署源代码是不好的实践。 - daehaai
“当应用程序运行时,node_modules未被使用” - 为什么?有一些在生产中使用的模块是从该目录加载的。 - Constantin Galbenu
1
@ConstantinGalbenu - 不把devDependencies放在生产环境中肯定是一个好的实践。而在一个你正在运行类似Webpack的资产管道的世界中,你也不需要dependencies,因为你的生产构件是一个资产捆绑包。 - Oliver Charlesworth
@OliverCharlesworth 没有任何强制要求你将它们安装到生产环境中(https://dev59.com/hGox5IYBdhLWcg3wVS8J#9276112)。此外,我的回答仍然有效:你的镜像应该包含所有运行所需的内容,以便在任何机器上运行。 - Constantin Galbenu
2个回答

2
听起来你担心两个不同但都很重要的问题:
1. 确保隔离/可重现的生产环境。 2. 确保隔离/可重现的构建环境(用于构建#1)。
你可以通过你提出的方法实现这两个目标 - 将构建步骤作为Dockerfile的一部分运行。 但是,这种方法有你提到的缺点 - 除非你采取明确的步骤将它们全部删除,否则在运行时会留下所有源代码/开发工件。
Docker引入了多阶段构建以在一定程度上缓解这个问题 - 它实际上允许您将多个层“压缩”成一个层。 但是它并不能消除需要明确清理的问题。
因此,根据我的经验,最常见的解决方案确实是在外部构建您的工件,然后将其COPY到生产映像中。
这解决了问题#1,但没有解决问题#2。 所以再进一步 - 在Docker容器内构建您的Docker映像! CI平台越来越支持这种方法作为一流概念 - 例如,请参见Circle CI的Docker执行器

1
在Docker中,通常情况下,您需要创建一个包含所有必要内容的软件镜像,以便您的应用程序可以在任何机器上运行。这就是Docker的用途:将应用程序及其依赖项绑定到单个构件中,以便它可以在安装了Docker的任何地方运行。
自给自足的镜像在使用Docker swarm等编排程序时非常方便。编排程序可以通过拉取镜像并启动容器在网络(即swarm)中的任何机器上运行容器。如果镜像或主机都不包含所需内容,则容器将失败。
有些情况下,您需要很容易地更改容器内部运行的文件,例如在开发过程中。在这种情况下,您可以将主机上的本地目录挂载到容器中(请参见volumes);这样,您只需修改主机上的文件,修改将立即传播到容器中。即使在这种情况下,您的镜像也应包含在其他机器上运行应用程序所需的文件;使用卷只会在开发环境中隐藏它们。

我不认为这个回答直接回答了提问者的问题 - 他/她应该使用什么工作流程来获取那个自给自足的图像? - Oliver Charlesworth
@OliverCharlesworth 我希望至少能对他有所帮助。 - Constantin Galbenu

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接