docker build 在nestjs微服务构建上失败

Posted

技术标签:

【中文标题】docker build 在nestjs微服务构建上失败【英文标题】:docker build fail on nestjs microservice build 【发布时间】:2022-01-22 02:41:00 【问题描述】:

我有这个 docker 文件:

FROM node:14.15.0 as build

WORKDIR /node-app

COPY package*.json /node-app/
RUN npm set progress=false && npm config set depth 0 && npm cache clean --force
RUN npm install
COPY . .
RUN npm run build

FROM node:14.15 

WORKDIR /node-app
COPY package.json /node-app/

RUN npm install --only=production
COPY --from=build /node-app/dist ./dist  
RUN npm run start:prod 

使用这个 package.json


  "name": "genysis-dbservice",
  "version": "0.0.1",
  "description": "",
  "author": "",
  "license": "UNLICENSED",
  "scripts": 
    "prebuild": "rimraf dist",
    "build": "nest build",
    "format": "prettier --write \"src/**/*.ts\" \"test/**/*.ts\"",
    "start": "nest start",
    "start:dev": "nest start --watch",
    "start:debug": "nest start --debug --watch",
    "start:prod": "node dist/main",
    "lint": "eslint \"src,apps,libs,test/**/*.ts\" --fix",
    "test": "jest",
    "test:watch": "jest --watch",
    "test:cov": "jest --coverage",
    "test:debug": "node --inspect-brk -r tsconfig-paths/register -r ts-node/register node_modules/.bin/jest --runInBand",
    "test:e2e": "jest --config ./test/jest-e2e.json"
  ,
  "private": true,
  "dependencies": 
    "@nestjs/common": "^7.6.5",
    "@nestjs/config": "^0.6.1",
    "@nestjs/core": "^7.6.5",
    "@nestjs/microservices": "^7.6.5",
    "@nestjs/platform-express": "^7.6.5",
    "@nestjs/websockets": "^7.6.5",
    "core-js": "^3.6.5",
    "neo4j-driver": "^4.1.1",
    "reflect-metadata": "^0.1.12",
    "rimraf": "^2.6.2",
    "rxjs": "^6.3.3"
  ,
  "devDependencies": 
    "@nestjs/testing": "^7.4.2",
    "@types/express": "^4.16.0",
    "@types/jest": "^26.0.9",
    "@types/node": "^10.12.18",
    "@types/supertest": "^2.0.7",
    "concurrently": "^4.1.0",
    "jest": "^26.3.0",
    "nodemon": "^1.18.9",
    "prettier": "^1.15.3",
    "supertest": "^3.4.1",
    "ts-jest": "^26.2.0",
    "ts-node": "8.1.0",
    "tsconfig-paths": "3.8.0",
    "tslint": "5.16.0",
    "typescript": "~4.0.5",
    "wait-on": "^3.2.0"
  ,
  "jest": 
    "moduleFileExtensions": [
      "js",
      "json",
      "ts"
    ],
    "rootDir": "src",
    "testRegex": ".spec.ts$",
    "transform": 
      "^.+\\.(t|j)s$": "ts-jest"
    ,
    "coverageDirectory": "../coverage",
    "testEnvironment": "node"
  

还有这个 tsconfig:

  "compilerOptions": 
      "module": "commonjs",
      "declaration": true,
      "removeComments": true,
      "emitDecoratorMetadata": true,
      "experimentalDecorators": true,
      "allowSyntheticDefaultImports": true,
      "target": "es2019",
      "sourceMap": true,
      "outDir": "./dist",
      "baseUrl": "./",
      "incremental": true
  ,
  "exclude": ["node_modules"]

我的节点是 14.15.0 版本,我的 npm 是 6.14.8,全局嵌套是 7.5.4。 我已将 typescript 版本从 ~4.5.0 更改为 4.4.2 再到 4.0.5,但在 RUN npm run build 上仍然出现故障。

 #16 2.145 sh: 1: nest: not found

不用说 npm run build 和 run start:prod 在 docker 之外工作正常.....

【问题讨论】:

【参考方案1】:

不用说 npm run build 和 run start:prod 在 docker 之外工作正常

这里有几点需要注意:

    nestjs 未在您的package.json 中定义,因此未安装。我假设您在主机上全局安装了 nestjs(在 docker 之外) 即使你的 package.json 中定义了 nestjs,npm 也不会将其安装为全局包

您可以通过以下几种方式解决它:

    如果您将nestjs 添加到您的package.json,它将可用于您的项目。如果您希望使用 package.json 并使软件包在全球范围内可用,则将 /node-app/node_modules 添加到您的路径(在您的主机或 docker 映像上)
    RUN npm install
    ENV PATH="/node-app/node_modules:$PATH"
    
    在你的 docker 镜像上全局安装 nestjs
    RUN npm install -g nestjs
    
    利用捆绑您的代码及其依赖项的工具,例如esbuild,将您的所有依赖项捆绑到一个文件中。那么您可以分发单个文件而无需安装任何依赖项

【讨论】:

"nestjs 未在您的 package.json 中定义,因此未安装。"我对这个评论感到困惑...也许您没有向上滚动查看完整的 package.json?.....请查看您的回复。 nestjs/cli 从 devDependencies 中丢失,如果这是“nestjs 未定义...”的意思,那么您的答案并不清楚。【参考方案2】:

问题是缺少 @nestjs/cli 来构建您的项目。根据项目的维护方式,您可以通过 2 种方式解决问题。

1- 如果您使用自动化工具来获取项目,请编辑您的dockerfile,以便在RUN npm run build 之前出现以下行中的“之一”。第一个全局安装,因此您可以在 shell 中将其用作免费命令,第二个只能在 npm 脚本中使用。构建镜像将被自动删除,因此在容器内使用哪个并不重要,但如果您在没有容器的情况下共享,则会有所不同。

> RUN npm install -g @nestjs/cli@7.5
> RUN npm i -D @nestjs/cli@7.5

2- 如果您拥有该项目,请使用npm i -D @nestjs/cli@7.5 或编辑packages.json 并在创建容器之前手动添加

"devDependencies": 
        "@nestjs/cli": "7.5",
        "@nestjs/testing": "^7.4.2",

从您的packages.json 中使用的版本可以追溯到一年前,version 7.5 似乎是合适的版本。目前这将安装version 7.5.7。如果您仍然有相同的设置,请使用nest --version 看看要使用什么。

【讨论】:

以上是关于docker build 在nestjs微服务构建上失败的主要内容,如果未能解决你的问题,请参考以下文章

基于事件驱动架构构建微服务第10部分:在docker容器内运行单元测试

NestJS MQTT 微服务的有效@MessagePattern 是啥?

无法容器化 NestJS 微服务

NestJS - 文件上传到微服务

nestjs为啥不火

基于事件驱动架构构建微服务第11部分:持续集成