`__dirname` + relative path (`../`) returns unexpected path after build
phanect opened this issue · comments
Environment
Environment of repro (Stackblitz)
~/projects/stackblitz-starters-hebbrj 4s
❯ node --version
v18.18.0
~/projects/stackblitz-starters-hebbrj
❯ npx unbuild --version
2.0.0
Environment of my local PC
$ node --version
v20.10.0
$ npx unbuild --version
2.0.0
$ lsb_release -a
No LSB modules are available.
Distributor ID: Neon
Description: KDE neon 5.27
Release: 22.04
Codename: jammy
# KDE neon is a Linux distro and currently based on Ubuntu 22.04
Reproduction
https://stackblitz.com/edit/stackblitz-starters-hebbrj
Run npm start
to build and run the compiled mjs.
Describe the bug
When you build a path with Node.js's path.join()
in a different deepness from the build path (e.g. the generated file is $PROJECT_ROOT/build/main.mjs and the source file is in $PROJECT_ROOT/foo/bar/library.ts), path.join()
returns unexpected path when you join __dirname
and relative path like path.join(__dirname, '../../../..')
.
In the repro, I created a TS file path/to/deep/folder/lib.ts and declare a variable projectRoot
as follows: const projectRoot = join(__dirname, '../../../..');
The project root is /home/projects/stackblitz-starters-hebbrj, so projectRoot
should be "/home/projects/stackblitz-starters-hebbrj".
I call this projectRoot
variable from main.ts in the project root and build it with unbuild.
However, when I build it and run the generated mjs, projectRoot
points "/".
This happened because all the source files are compiled to dist/main.mjs and join(__dirname, '../../../..')
runs on it.
In the built mjs, __dirname
is /home/projects/stackblitz-starters-hebbrj/dist while I expected __dirname
is /home/projects/stackblitz-starters-hebbrj/path/to/deep/folder.
I understand it is hard to handle this issue (and I'm not sure if it should be considered as a bug), but I believe it should make a better developer experience if this issue is resolved.
Sorry if this is not an issue caused by unbuild but by the bundlers (esbuild or mkdist?).
Additional context
No response
Logs
Log of `npm start`:
~/projects/stackblitz-starters-hebbrj 5s
❯ npm start
> unbuild-issue-relative-path@1.0.0 start
> npm run build && node ./dist/main.mjs
> unbuild-issue-relative-path@1.0.0 build
> unbuild
# ...Build logs...
----------
Project root given by path/to/deep/folder/lib.js (wrong): /
Project root given by process.cwd() (correct): /home/projects/stackblitz-starters-hebbrj
Hi, @phanect, I also meet the same problem. I think this is expected behavior. As you said. It's hard to handle this problem by bundlers
This is my two methods to get expected path:
- Use mkdist: keep original file structure
- Set project root path as global variable
// src/main.ts
import { finup } from 'find-up'
process.env.ROOT_PATH = findUpSync('package.json')
// src/template/build.ejs
// Some Content
// src/other/file/foo.ts
const path = resolve(process.env.ROOT_PATH, 'template/build.ejs')
Hi @peterroe, thanks for your reply :)
I understand it is hard to handle this by unbuild (and maybe esbuild).
I will try mkdist. Thanks for the workaround.
I'm closing this Issue.