【问题标题】:Monorepo – Yarn workspaces Typescript Node.JS project – cannot find module when running nodemonMonorepo – Yarn 工作区 Typescript Node.JS 项目 – 运行 nodemon 时找不到模块
【发布时间】:2021-05-17 00:00:11
【问题描述】:

我已经为 typescript Node.JS 项目使用 yarn 工作区设置了一个 monorepo。构建项目工作正常,但是,我在本地开发过程中遇到了问题。

在运行yarn dev 之前,我需要手动运行yarn build。否则我会收到以下错误:

错误:找不到模块“/Users/benedikt/code/monorepo-build/node_modules/@bhirmer/utils/dist/index.js”。请验证 package.json 是否有有效的“main”条目

这里是重现问题的sample repo

或者,重要文件。

项目结构

packages/
  utils
services/
  api

根包.json

{
  "name": "@bhirmer/monorepo",
  "description": "Workspace",
  "private": true,
  "workspaces": [
    "packages/*",
    "services/*"
  ],
  "scripts": {},
  "devDependencies": {
    "eslint": "~7.14.0",
    "typescript": "^4.0.5"
  }
}

根 tsconfig.json

{
  "compilerOptions": {
    "module": "commonjs",
    "target": "ES2015",
    "lib": ["ES2019", "dom"],
    "types": ["node"],
    "esModuleInterop": true,
    "skipLibCheck": true,
    "sourceMap": true,
    "noEmitOnError": true,
    "allowUmdGlobalAccess": true,
    "allowJs": false,
    "strict": true,
    "forceConsistentCasingInFileNames": true,
    "noEmit": false,
    "moduleResolution": "node",
    "resolveJsonModule": true,
    "allowSyntheticDefaultImports": true,
    "noImplicitAny": true,
    "noUnusedLocals": true,
    "noImplicitThis": true,
    "strictNullChecks": true,
    "noImplicitReturns": true,
    "preserveConstEnums": true,
    "suppressImplicitAnyIndexErrors": true,
    "composite": true,
    "baseUrl": "../..",
    "paths": {
      "@bhirmer/*": ["packages/*/src"]
    }
  },
  "include": ["src/**/*"],
  "exclude": ["node_modules", "dist"]
}

实用程序包.json

{
  "name": "@bhirmer/utils",
  "version": "1.0.0",
  "main": "dist/index.js",
  "types": "dist/index.d.ts",
    "files": [
        "dist"
    ],
  "scripts": {
    "build": "yarn run clean && yarn run compile",
    "clean": "rimraf ./dist && rimraf ./tsconfig.buildinfo",
    "compile": "tsc --build",
    "test": "yarn run build"
  },
  "dependencies": {
    "@types/node": "^14.14.12"
  },
  "devDependencies": {},
  "sideEffects": false
}

实用程序 tsconfig.json

{
  "extends": "../../tsconfig.json",
  "compilerOptions": {
    "baseUrl": "../../",
    "rootDir": "./src",
    "outDir": "./dist",
    "composite": true
  },
  "include": ["src/**/*"],
  "exclude": ["node_modules", "dist"]
}

API 包.json

{
  "name": "@bhirmer/api",
  "description": "api",
  "author": "Benedikt Hirmer <benedikt@hirmer.me",
  "license": "UNLICENSED",
  "private": true,
  "version": "1.0.0",
  "main": "server/index",
  "scripts": {
    "dev": "PROJECT_ID=test-dev PORT=3010 nodemon src/server/index.ts",
    "clean": "rimraf ./dist",
    "compile": "NODE_ENV=production tsc --build",
    "build": "yarn run compile",
    "start": "PROJECT_ID=test-prod NODE_ENV=production node dist/server/index.js",
  },
  "dependencies": {
    "@bhirmer/utils": "^1.0.0",
    "@types/compression": "^1.7.0",
    "@types/express": "^4.17.11",
    "@types/node": "^14.14.12",
    "compression": "^1.7.4",
    "express": "^4.17.1",
    "typescript": "^4.2.4"
  },
  "devDependencies": {
    "nodemon": "^2.0.7",
    "ts-node": "^9.1.1"
  }
}

API tsconfig.json

{
  "extends": "../../tsconfig.json",
  "compilerOptions": {
    "outDir": "dist",
    "baseUrl": "../../",
    // "rootDir": "src", // Getting `TypeError: src/server/index.ts: Emit skipped` if not commented out
    "composite": true
  },
  "include": ["src/**/*"],
  "types": ["typePatches"],
  "references": [{ "path": "../../packages/utils" }]
}

services/api中packages/utils的使用示例

import { getProjectID } from '@bhirmer/utils';

...

const projectID = getProjectID();

...

还有一点需要注意的是,一旦我在services/api/tsconfig.json 中设置了"rootDir": "src",就会遇到以下错误:

TypeError: src/server/index.ts: Emit skipped 如果没有被注释掉

【问题讨论】:

    标签: node.js typescript monorepo yarn-workspaces


    【解决方案1】:

    NPM 工作空间仍然需要您在根目录(带有工作空间定义/位置的 package.json 所在的位置)内运行 npm install,以便与本地包建立相关的符号链接。

    当你这样做时,你应该得到:

    node_modules/
        @bhirmer/
            utils/ <-- symlink to /packages/utils/
            api/ <-- symlink to /services/api/
    packages/
        utils/
            ...
    services/
        api/
            ...
    package.json <-- root package.json with "workspaces"
    

    每次你创建一个包含 package.json 的新本地包文件夹时,你都必须重新运行它,你想从其他地方访问它。

    【讨论】:

      猜你喜欢
      • 2019-08-10
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2019-01-16
      • 1970-01-01
      • 2016-06-05
      • 2015-06-30
      相关资源
      最近更新 更多