Skip to content

Commit

Permalink
Update node_modules_path to resolve symlinks to real paths (#5085)
Browse files Browse the repository at this point in the history
* Update node_modules_path to follow symlinks

* Update whitespace to make prettier happy

* Update CHANGELOG.md

* Update CHANGELOG.md

* Update node_modules_paths.js

* Code Review feedback

* Use `realpath()` in `jest-util`
* Fix a lint error

* Add missing dependency in jest-resolve

* Fix import statement

* Fix a lint warning

* Fix lint issues caused by editor

* Add test

* passing tests

* Make lint happy

* Make lint happy

* Make lint happy

* AppVeyor should keep symlinks

* Update appveyor.yml

* Fix imports

* fixed the rel/abs path test suite that was failing with realpath

* Update CHANGELOG.md

* Update package.json
  • Loading branch information
Nicholas Pape authored and cpojer committed Feb 23, 2018
1 parent 83a51cc commit a6aa304
Show file tree
Hide file tree
Showing 10 changed files with 87 additions and 5 deletions.
5 changes: 5 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,10 @@
## master

### Fixes

* `[jest-resolve]` Update node module resolution algorithm to correctly handle
symlinked paths ([#5085](https://github.com/facebook/jest/pull/5085))

## 22.4.2

### Fixes
Expand Down
1 change: 1 addition & 0 deletions appveyor.yml
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ init:
# debugging Appveyor build. More info:
# https://www.appveyor.com/docs/how-to/rdp-to-build-worker/
- ps: iex ((new-object net.webclient).DownloadString('https://raw.githubusercontent.com/appveyor/ci/master/scripts/enable-rdp.ps1'))
- git config --global core.symlinks true

install:
- ps: Install-Product node $env:nodejs_version x64
Expand Down
3 changes: 2 additions & 1 deletion packages/jest-resolve/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,8 @@
"main": "build/index.js",
"dependencies": {
"browser-resolve": "^1.11.2",
"chalk": "^2.0.1"
"chalk": "^2.0.1",
"realpath-native": "^1.0.0"
},
"devDependencies": {
"jest-haste-map": "^22.4.2"
Expand Down
Empty file.
1 change: 1 addition & 0 deletions packages/jest-resolve/src/__mocks__/bar/node_modules/foo

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Empty file.
Empty file.
23 changes: 23 additions & 0 deletions packages/jest-resolve/src/__tests__/resolve.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -129,6 +129,19 @@ describe('resolveModule', () => {
require.resolve('../__mocks__/mockJsxDependency.native.jsx'),
);
});

it('is possible to resolve node modules by resolving their realpath', () => {
const resolver = new Resolver(moduleMap, {
extensions: ['.js'],
});
const src = require.resolve(
'../../src/__mocks__/bar/node_modules/foo/index.js',
);
const resolved = resolver.resolveModule(src, 'dep');
expect(resolved).toBe(
require.resolve('../../src/__mocks__/foo/node_modules/dep/index.js'),
);
});
});

describe('getMockModule', () => {
Expand Down Expand Up @@ -203,6 +216,16 @@ describe('Resolver.getModulePaths() -> nodeModulesPaths()', () => {
map: [],
mocks: [],
});

// Mocking realpath to function the old way, where it just looks at
// pathstrings instead of actually trying to access the physical directory.
// This test suite won't work otherwise, since we cannot make assumptions
// about the test environment when it comes to absolute paths.
jest.doMock('realpath-native', () => {
return {
sync: dirInput => dirInput,
};
});
});

afterAll(() => {
Expand Down
15 changes: 11 additions & 4 deletions packages/jest-resolve/src/node_modules_paths.js
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@

import type {Path} from 'types/Config';
import path from 'path';
import {sync as realpath} from 'realpath-native';

type NodeModulesPathsOptions = {|
moduleDirectory?: Array<string>,
Expand All @@ -37,11 +38,17 @@ export default function nodeModulesPaths(
prefix = '\\\\';
}

const paths = [basedirAbs];
let parsed = path.parse(basedirAbs);
// The node resolution algorithm (as implemented by NodeJS
// and TypeScript) traverses parents of the physical path,
// not the symlinked path
const physicalBasedir = realpath(basedirAbs);

const paths = [physicalBasedir];
let parsed = path.parse(physicalBasedir);
while (parsed.dir !== paths[paths.length - 1]) {
paths.push(parsed.dir);
parsed = path.parse(parsed.dir);
const realParsedDir = realpath(parsed.dir);
paths.push(realParsedDir);
parsed = path.parse(realParsedDir);
}

const dirs = paths
Expand Down
44 changes: 44 additions & 0 deletions yarn.lock
Original file line number Diff line number Diff line change
Expand Up @@ -4534,6 +4534,10 @@ jest-docblock@^21, jest-docblock@^21.0.0, jest-docblock@^21.2.0:
version "21.2.0"
resolved "https://registry.yarnpkg.com/jest-docblock/-/jest-docblock-21.2.0.tgz#51529c3b30d5fd159da60c27ceedc195faf8d414"

jest-get-type@^21.2.0:
version "21.2.0"
resolved "https://onedrive.pkgs.visualstudio.com/_packaging/odsp-npm/npm/registry/jest-get-type/-/jest-get-type-21.2.0.tgz#f6376ab9db4b60d81e39f30749c6c466f40d4a23"

jest-haste-map@^21:
version "21.2.0"
resolved "https://registry.yarnpkg.com/jest-haste-map/-/jest-haste-map-21.2.0.tgz#1363f0a8bb4338f24f001806571eff7a4b2ff3d8"
Expand All @@ -4545,6 +4549,39 @@ jest-haste-map@^21:
sane "^2.0.0"
worker-farm "^1.3.1"

jest-message-util@^21.2.1:
version "21.2.1"
resolved "https://onedrive.pkgs.visualstudio.com/_packaging/odsp-npm/npm/registry/jest-message-util/-/jest-message-util-21.2.1.tgz#bfe5d4692c84c827d1dcf41823795558f0a1acbe"
dependencies:
chalk "^2.0.1"
micromatch "^2.3.11"
slash "^1.0.0"

jest-mock@^21.2.0:
version "21.2.0"
resolved "https://onedrive.pkgs.visualstudio.com/_packaging/odsp-npm/npm/registry/jest-mock/-/jest-mock-21.2.0.tgz#7eb0770e7317968165f61ea2a7281131534b3c0f"

jest-util@^21.2.1:
version "21.2.1"
resolved "https://onedrive.pkgs.visualstudio.com/_packaging/odsp-npm/npm/registry/jest-util/-/jest-util-21.2.1.tgz#a274b2f726b0897494d694a6c3d6a61ab819bb78"
dependencies:
callsites "^2.0.0"
chalk "^2.0.1"
graceful-fs "^4.1.11"
jest-message-util "^21.2.1"
jest-mock "^21.2.0"
jest-validate "^21.2.1"
mkdirp "^0.5.1"

jest-validate@^21.2.1:
version "21.2.1"
resolved "https://onedrive.pkgs.visualstudio.com/_packaging/odsp-npm/npm/registry/jest-validate/-/jest-validate-21.2.1.tgz#cc0cbca653cd54937ba4f2a111796774530dd3c7"
dependencies:
chalk "^2.0.1"
jest-get-type "^21.2.0"
leven "^2.1.0"
pretty-format "^21.2.1"

jquery@^3.2.1:
version "3.2.1"
resolved "https://registry.yarnpkg.com/jquery/-/jquery-3.2.1.tgz#5c4d9de652af6cd0a770154a631bba12b015c787"
Expand Down Expand Up @@ -6200,6 +6237,13 @@ prettier@^1.10.1:
version "1.10.1"
resolved "https://registry.yarnpkg.com/prettier/-/prettier-1.10.1.tgz#01423fea6957ea23618d37d339ef0e7f7c967fc6"

pretty-format@^21.2.1:
version "21.2.1"
resolved "https://onedrive.pkgs.visualstudio.com/_packaging/odsp-npm/npm/registry/pretty-format/-/pretty-format-21.2.1.tgz#ae5407f3cf21066cd011aa1ba5fce7b6a2eddb36"
dependencies:
ansi-regex "^3.0.0"
ansi-styles "^3.2.0"

pretty-format@^4.2.1:
version "4.3.1"
resolved "https://registry.yarnpkg.com/pretty-format/-/pretty-format-4.3.1.tgz#530be5c42b3c05b36414a7a2a4337aa80acd0e8d"
Expand Down

0 comments on commit a6aa304

Please sign in to comment.