Search code examples
javascripttypescripttsctsconfig

How to compile two projects that reference each other


I am having issues building a project (@red5/middleware) that references another project (@red5/router) and in return that project references this project (@red5/middleware).

So, when I run the command:

rm -rf types && tsc -p .

I get an error that says it cannot find the .d.ts file(s) because I removed them with rm.

../router/types/Route.d.ts:4:28 - error TS7016: Could not find a declaration file for module '@red5/middleware'. 'C:/Users/rnaddy/Documents/vscode/projects/red5/framework/middleware/lib/index.js' implicitly has an 'any' type. Try npm install @types/red5__middleware if it exists or add a new declaration (.d.ts) file containing declare module '@red5/middleware';

@red5/router -> route.ts

import { Middleware } from '@red5/middleware';

If I remove the rm -rf types command, I get errors saying that it cannot overwrite the input file, but I no longer get the above error.

What can I do to get rid of this error and still use rm -rf types in my command?

middleware/tsconfig.json

{
  "compilerOptions": {
    "outDir": "lib",
    "declarationDir": "types"
  },
  "extends": "../tsconfig.json",
  "include": [
    "src/**/*.ts"
  ]
}

tsconfig.json

{
  "compilerOptions": {
    "target": "es2017",
    "module": "commonjs",
    "moduleResolution": "node",
    "declaration": true,
    "strict": true,
    "removeComments": false,
    "inlineSourceMap": true
  },
  "exclude": [
    "lib",
    "types"
  ]
}

Solution

  • To solve this issue, was basically just a modification of the tsconfig.json file.

    Two items are needed:

    1. compilerOptions.baseUrl - Base directory to resolve non-relative module names.
    2. compilerOptions.paths - List of path mapping entries for module names to locations relative to the baseUrl.

    So, in the @red5/middleware module we reference the router like this:

    {
      "compilerOptions": {
        "baseUrl": ".",
        "paths": {
          "@red5/router": [ "../router" ]
        }
      }
    }
    

    Then in the @red5/router module we reference the middleware like this:

    {
      "compilerOptions": {
        "baseUrl": ".",
        "paths": {
          "@red5/middleware": [ "../middleware" ]
        }
      }
    }
    

    Everything then resolves to the proper locations.