|
| 1 | +/* eslint no-irregular-whitespace: 0 */ |
| 2 | +'use strict'; |
| 3 | +// Refs: https://github.com/nodejs/node/pull/5950 |
| 4 | + |
| 5 | +// This test illustrates the problem that symlinked modules are unable |
| 6 | +// to find their peer dependencies. This was fixed in #5950 but that is |
| 7 | +// reverted because that particular way of fixing it causes too much |
| 8 | +// breakage (breakage that was not caught by either CI or CITGM on multiple |
| 9 | +// runs. |
| 10 | + |
| 11 | +// This test passes in v6 with https://github.com/nodejs/node/pull/5950 but |
| 12 | +// fails with https://github.com/nodejs/node/pull/5950 reverted. This test |
| 13 | +// will fail in Node.js v4 and v5. |
| 14 | + |
| 15 | +const common = require('../common'); |
| 16 | +const fs = require('fs'); |
| 17 | +const path = require('path'); |
| 18 | +const assert = require('assert'); |
| 19 | + |
| 20 | +common.refreshTmpDir(); |
| 21 | + |
| 22 | +const tmpDir = common.tmpDir; |
| 23 | + |
| 24 | +// Creates the following structure |
| 25 | +// {tmpDir} |
| 26 | +// ├── app |
| 27 | +// │ ├── index.js |
| 28 | +// │ └── node_modules |
| 29 | +// │ ├── moduleA -> {tmpDir}/moduleA |
| 30 | +// │ └── moduleB |
| 31 | +// │ ├── index.js |
| 32 | +// │ └── package.json |
| 33 | +// └── moduleA |
| 34 | +// ├── index.js |
| 35 | +// └── package.json |
| 36 | + |
| 37 | +const moduleA = path.join(tmpDir, 'moduleA'); |
| 38 | +const app = path.join(tmpDir, 'app'); |
| 39 | +const moduleB = path.join(app, 'node_modules', 'moduleB'); |
| 40 | +const moduleA_link = path.join(app, 'node_modules', 'moduleA'); |
| 41 | +fs.mkdirSync(moduleA); |
| 42 | +fs.mkdirSync(app); |
| 43 | +fs.mkdirSync(path.join(app, 'node_modules')); |
| 44 | +fs.mkdirSync(moduleB); |
| 45 | + |
| 46 | +// Attempt to make the symlink. If this fails due to lack of sufficient |
| 47 | +// permissions, the test will bail out and be skipped. |
| 48 | +try { |
| 49 | + fs.symlinkSync(moduleA, moduleA_link); |
| 50 | +} catch (err) { |
| 51 | + if (err.code !== 'EPERM') throw err; |
| 52 | + console.log('1..0 # Skipped: insufficient privileges for symlinks'); |
| 53 | + return; |
| 54 | +} |
| 55 | + |
| 56 | +fs.writeFileSync(path.join(moduleA, 'package.json'), |
| 57 | + JSON.stringify({name: 'moduleA', main: 'index.js'}), 'utf8'); |
| 58 | +fs.writeFileSync(path.join(moduleA, 'index.js'), |
| 59 | + 'module.exports = require(\'moduleB\');', 'utf8'); |
| 60 | +fs.writeFileSync(path.join(app, 'index.js'), |
| 61 | + '\'use strict\'; require(\'moduleA\');', 'utf8'); |
| 62 | +fs.writeFileSync(path.join(moduleB, 'package.json'), |
| 63 | + JSON.stringify({name: 'moduleB', main: 'index.js'}), 'utf8'); |
| 64 | +fs.writeFileSync(path.join(moduleB, 'index.js'), |
| 65 | + 'module.exports = 1;', 'utf8'); |
| 66 | + |
| 67 | +// TODO(@jasnell): Update this comment with this issue is fixed and |
| 68 | +// this test is moved out of the known_issues directory. |
| 69 | +// |
| 70 | +// Ideally, this should not throw but it does because moduleA is not |
| 71 | +// able to find it's peer dependency moduleB. The reason it cannot find |
| 72 | +// it's peer is because moduleA is cached at it's realpath and when it's |
| 73 | +// require goes to find moduleA, it can't (because moduleB does not exist |
| 74 | +// within it's lookup path). |
| 75 | +assert.doesNotThrow(() => { |
| 76 | + require(path.join(app, 'index')); |
| 77 | +}); |
0 commit comments