前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >使用这 3 个技巧升级您的 NodeJS Dockerfile

使用这 3 个技巧升级您的 NodeJS Dockerfile

原创
作者头像
zayyo
修改2023-11-29 21:33:10
4690
修改2023-11-29 21:33:10
举报
文章被收录于专栏:zayyo前端

Dockerfile 是创建容器的蓝图。它们是简单的文本文件,包含了创建容器镜像所需的命令,这些命令通常是您手动执行的。Dockerfile 就是您容器的源代码。

编写 Dockerfile 很容易,但它们可能很快变得复杂。以下是一些有助于编写更好的 Dockerfile 的技巧。

我将分享我多年来学到的 3 个技巧。这些技巧将有助于您编写更好的 Dockerfile。它们将使您的容器更稳定和安全。它们还将使您的容器更小更快。希望您会发现它们有用。

如果您的 Dockerfile 如下所示,可以进行改进:

代码语言:shell
复制
FROM node:lts-alpine
WORKDIR /app
COPY . .
RUN npm install
CMD ["npm", "run", "start"]

1- 选择正确的基础镜像

基础镜像是容器的起点。它是 Dockerfile 中的第一行。基础镜像是容器的基础,它是用于构建容器的操作系统和软件。

Alpine 是 Docker 容器最流行的基础镜像。它是为容器优化的轻量级 Linux 发行版。它小巧、快速和安全。对于大多数容器来说,它是一个不错的选择。但是… 它不是 Docker 官方支持的镜像,而是由 Alpine Linux 社区维护的。

更好的选择是使用 bullseye 基础镜像。这是 Docker 的官方 Debian 基础镜像。由 Debian 社区维护。对于大多数容器来说,这是一个不错的选择。它小巧、快速,如果选择 slim 变体,也更安全和更轻量级。

代码语言:shell
复制
FROM node:20.9.0-bullseye-slim

同时,请指定基础镜像的版本。这将确保您的容器始终使用相同版本的基础镜像。这将使您的容器更稳定和安全。lts 不是一个版本,而是一个标签。不建议使用基础镜像的标签,而是使用版本号。

2- 是否需要复制全部内容?

可能不需要,我很确定您在生产 Docker 容器中不需要 .prettierignore 或 .gitignore 等文件。

您可以通过两种方式解决这个问题:

  • 为每个文件/文件夹指定一系列 COPY 指令。
  • 在 .dockerignore 文件中指定不想要复制的内容列表。

我更喜欢指定我想要复制到镜像中的文件/文件夹列表。尽管如此,我建议您使用 .dockerignore 文件来避免将不必要的文件复制到镜像中,因为这是一个良好的做法。

此外,出于安全原因,您应该使用比 root 权限更少的用户,默认情况下 Docker 镜像是由 root 用户运行的(取决于您正在使用的基础镜像)。您可以在 Dockerfile 中运行 whoami 来检查这一点。

代码语言:shell
复制
RUN echo "whoami: $(whoami)" # <--- whoami: root

在 node 和其他一些镜像中(包括 Alpine 基础镜像),我们有一个名为 node 的用户,我们可以使用它代替 root,权限更少。我们应该将此用户添加到镜像中,并尽可能使用它代替 root。

代码语言:shell
复制
RUN echo "whoami: $(whoami)" # <--- whoami: root
USER node
RUN echo "whoami: $(whoami)" # <--- whoami: node
# 现在我们使用 'node' 用户而不是 root 用户进行 Dockerfile 的后续操作。

--chown=node:node 选项确保复制的文件的所有权设置为 node 用户和组。

代码语言:shell
复制
COPY --chown=node:node ./src ./src
COPY --chown=node:node ./package*.json ./

请记住,如果将 WORKDIR 设置为 /app,这意味着 COPY 指令(以及其他指令)将文件复制到 WORKDIR,您可以使用 . 来指定。

3- 多阶段构建

为什么?安全性和大小。

大小:您的最终镜像是否需要包含 package-lock.json,甚至 package.json?可能不需要,NodeJS 应用程序需要的是 node_modules 文件夹和位于 src 文件夹中的 JS 源代码,通常在 JS 项目中,如果是 TS 项目,则位于 dist 文件夹中,那是从 TS 编译为 JS 的编译后代码。

如果您的 NodeJS 应用程序是用 TypeScript 编写的,您可能会考虑:

代码语言:shell
复制
RUN apt-get update && apt-get install -y # <-- 对您的应用程序可能有用
WORKDIR /app
COPY . /app
RUN npm ci --only=production
RUN npm run build # 编译 TS 到 JS
RUN rm -rf /app/src # <------- 简单修复
CMD ["node", "dist/index.js"]

如果运行 docker history <image-name>,您将看到 NPM_TOKEN。当然,您可以始终运行 RUN export NPM_TOKEN=123 来从最终镜像中删除它,但这不是最佳做法,而且仍将在 docker history 中可见。

我正在参与2023腾讯技术创作特训营第三期有奖征文,组队打卡瓜分大奖!

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
相关产品与服务
容器服务
腾讯云容器服务(Tencent Kubernetes Engine, TKE)基于原生 kubernetes 提供以容器为核心的、高度可扩展的高性能容器管理服务,覆盖 Serverless、边缘计算、分布式云等多种业务部署场景,业内首创单个集群兼容多种计算节点的容器资源管理模式。同时产品作为云原生 Finops 领先布道者,主导开源项目Crane,全面助力客户实现资源优化、成本控制。
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档