Add support for --preserve-symlinks
See original GitHub issueThis is a thorny issue but I believe I’m beginning to understand it.
Basically there’s two ways to treat symlinks:
- “Expand” their paths during resolution (aka “not preserving symlinks”)
- Don’t “expand” their paths during resolution (aka “preserving symlinks”)
There are downsides to both (if my understanding is right).
Node by default does not preserve symlinks. They tried to change this behavior in Node 6 (https://github.com/nodejs/node/pull/5950) but that backfired with non-trivial breakages and they reverted it soon and put behind a --preserve-symlinks
flag (https://github.com/nodejs/node/pull/6537). There is also an argument that the behavior isn’t a bug or needs a different fix (https://github.com/isaacs/node6-module-system-change).
Regardless, it seems like some people prefer one behavior (with its set of tradeoffs) and other people prefer the other behavior (with another set of tradeoffs). Node currently supports both. Webpack does too (https://webpack.js.org/configuration/resolve/#resolve-symlinks).
Jest currently seems to support a mixture of both behaviors (?). I fixed at least some of it to match Node in https://github.com/facebook/jest/pull/4761 (ironically despite “preserve” in the PR name the change aligned with Node’s default behavior of not preserving them). I still think that PR was a good idea. However, apparently there are places where Jest still doesn’t match node: https://github.com/facebook/jest/issues/5228, https://github.com/facebook/jest/pull/5085.
Assuming those get fixed, and Jest always does not preserve symlinks by default (just like Node), what do you think about allowing the “preserve symlinks” behavior as an opt-in, just like Node and webpack already offer?
Issue Analytics
- State:
- Created 6 years ago
- Reactions:100
- Comments:25 (1 by maintainers)
Top GitHub Comments
We use Jest at Dropbox and we are also in need of the ability to preserve symlinks when Jest resolves file paths.
All of our automated test runs and frontend asset build steps are performed using Bazel. Notably, Bazel runs build tools and binaries inside sandboxes, temporary directories inside which every file is actually a read-only symlink that points outside of the sandbox. Bazel expects the test binary to treat the symlinks opaquely — as normal files relative to the sandbox root.
This has a couple consequences for Jest:
When Jest performs test discovery, we need it to discover tests inside files that are actually symlinks. Unfortunately, the filesystem walk (
find
) used to discover test files will not return symlinks at all.Jest uses
fs.realpath
(or similar) to resolve symlinks in the default resolver and the script transformer — when these are resolved to paths outside the Bazel sandbox (i.e. outside of Jest’s current working directory), code coverage reports will contain duplicated paths: one set of paths from inside the sandbox and another from outside.We’ve started an internal fork of Jest at Dropbox, in which we’ve removed the
realpath
calls and changed thefind
call to also pick up symlinks — these changes were sufficient for us to get Jest playing nicely with Bazel. However, I assume symlink-preserving behavior would be useful not only to us or anyone hoping to integrate Jest with Bazel, but also anyone using Jest in any other kind of test or build environment in which source files and test files may actually be symlinks.We’d be happy to contribute these changes back upstream behind a
--preserve-symlinks
flag (or perhaps two distinct flags if changes for thefind
call and therealpath
calls are considered orthogonal). Are there any other concerns or details we should be aware of or take into account when implementing a PR for this?So… is this on the roadmap?