Other options are omiited for brevity.
{
"compilerOptions": {
"baseUrl": "./src"
"paths": {
"#/*": ["./*"]
}
}
}
ts-node-dev --respawn --transpileOnly src/index.ts
import { foo } from '#/foo'
console.log(`index.ts uses ${foo}`)
When I edit foo.ts, which index.ts depends on, ts-node-dev does not respawn. I guess it's because ts-node-dev does not consider the paths option in tsconfig.json.
Here is a workaround for folks with the same problem.
Install concurrently (or another preferred alternative) and node-dev (or maybe another like nodemon).
npm uninstall ts-node-dev
npm install concurrently node-dev --save-dev
Then run
concurrently 'tsc -w' 'node-dev --respawn dist/index.js'
This would incrementally compile editted .ts files(tsc -w), and node-dev would respawn by detecting compiled .js files. Obviously, this is logically identical to what ts-node-env does, but now tsc respects the "paths" option.
This is strange "workaround" =)
Should this even work with node.js without special plugins?
TS compiler doesn't transform require paths like '#/foo', so it should just give the error Cannot find module '#/foo'
There is a module https://github.com/dividab/tsconfig-paths allows to handle tsconfig's paths option with node.js
@whitecolor
Thank you for the recommendation :)
I've been using link-module-alias, which automatically creates symlinks in _node_modules_ (And by this aspect, it has some other benefits, especially on plain node project, by the way). Whereas tsconfig-paths works on runtime, link-module-alias should be executed (only once) before running node.
TS compiler doesn't transform require paths like '#/foo', so it should just give the error
Cannot find module '#/foo'
The compiler doesn't transform but compiles it "as-is"
(import foo from '#/foo' -> const foo = require('#/foo')),
without an error or warning.
Should this even work with node.js without special plugins?
For example, I set a symlink node_modules/# -> dist through link-module-alias. So #/foo is valid on compiled js.
So, I let ts compiler check types by looking "paths", and node find modules by symlinks. Maybe you can read https://dev.to/larswaechter/path-aliases-with-typescript-in-nodejs-4353 if you want.
What I suggest is, of course, different from tsc's behavior. Though ts compiler compiles modules aliases as-is, ts-node-dev should dynamically stitch ts files by looking "baseUrl" and "paths". This only requires reading tsconfig.json and doing some regex, so I guess It'd be not a big deal.
Sometimes, project structure gets deeper and wider, so using absolute path provides significant benefit. If ts-node-dev doesn't care them, people using aliases have to find other ways like the "workaround" I suggested. And what we should consider is, people negatively feel to fragmented setting. They prefer setting as consistent as possible through projects, no matter big or small. If ts-node-dev doesn't support, then they might just avoid using it at all even on projects without aliases.
P.S.
This is strange "workaround" =)
"strange"..? Hmm, why?
Well, I personally think it's also a quite good approach. There would be pros and cons.
pros
tsc --watch is stable, so straight-forward and beginner-friendly. tsc --watch --incremental supports both ones.)cons
tsc -w) is completed, which would cause an initial error message printed. (However, it's actually not a problem as it would be restarted automatically just after .ts modules are all compiled.) It works smoothly. jjangga0214/ts-boilerplate is a working example. You can clone it, run yarn/npm dev, and then edit .ts files. Then it would automatically restart the node process seamlessly.
tsc --watch creates *.js files, which ts-node (not ts-node-dev, but ts-node) was created to avoid.
If you ok with this *.js filles all around while dev, it is just another approach.
Also I prefer to use yarn workspaces instead of tsconfig paths and other "workarounds" like mentioned link-module-alias.
@whitecolor Thanks for the recommendation again.
The main point of this issue is asking if ts-node-dev would repect paths. I think it's cool and necessary. How do you think?
This is a task for another package, as I said you may use https://github.com/dividab/tsconfig-paths to achieve that if needed, setup is quite transparent.
Closing this issue. Thanks for the suggestion anyway :)
If anyone has issues with this, try the module-alias plugin. So far it's the cleanest solution I've found and it is working all right!
Given a directory structure like the following:
- build/ // Here is the typescript outDir folder
- src/ // Here is where we have all the app files
- src/index.ts
- src/app.ts
- package.json
Create a src/aliases.ts file like this:
import moduleAlias from 'module-alias';
import path from 'path';
const IS_DEV = process.env.NODE_ENV === 'development';
const rootPath = path.resolve(__dirname, '..', '..');
const rootPathDev = path.resolve(rootPath, 'src');
const rootPathProd = path.resolve(rootPath, 'build');
moduleAlias.addAliases({
'@src': IS_DEV ? rootPathDev : rootPathProd,
});
Then, in the src/index.ts file, or in whatever is your entry file, add this as first import:
import './aliases'; // MUST BE FIRST!!
// Now you can use the `@src` for absolute imports
import { app } from '@src/app';
Finally, set tsconfig.json like this (mostly to make typescript and your IDE recognise the path):
{
"compilerOptions": {
"outDir": "./build/",
"baseUrl": ".",
"paths": {
/* IMPORTANT: this must be the same of 'src/aliases.ts' */
"@src/*": ["src/*"]
},
}
@whitecolor I would recommend to add a note about this (also mentioning baseUrl, since one really doesn't have to use paths for things to break) in points of notice in the README.
Because while I love ts-node-dev for the reason you mentioned in this issue, I almost just threw in the towel until I stumbled across your recommendation to use tsconfig-paths. Which is so simple to set up but... why would one even think about looking for it in the first place? At least all I perceived was an inconsistency between tsc and ts-node-dev and assumed it was a bug (hence then looking for it here).
@whitecolor tsconfig paths does not seem to work with ts-node-dev. It worked well previously with nodemon and ts-node.
Running via npx ts-node-dev --project tsconfig.json -r tsconfig-paths/register src/server/server.ts
My aliased paths do not resolve.
Not sure why it may not work, when I used it, it worked ok.
Please disregard. I was a bit confused when running a nextjs customer server, that first passed through ts-node for the server and than passed through webpack for the react code. Think I have it figured out now.
For anyone finding this and want a two-liner here it is:
npm i -D tsconfig-paths
then in your package.json add a script like this:
"dev": "tsnd --respawn -r tsconfig-paths/register *pathtoyourmainfile* "
Most helpful comment
For anyone finding this and want a two-liner here it is:
npm i -D tsconfig-pathsthen in your package.json add a script like this:
"dev": "tsnd --respawn -r tsconfig-paths/register *pathtoyourmainfile* "