• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1'use strict'
2
3const promisify = require('./util.js').promisify
4
5const path = require('path')
6const statAsync = promisify(require('fs').stat)
7
8module.exports = getPrefix
9function getPrefix (root) {
10  const original = root = path.resolve(root)
11  while (path.basename(root) === 'node_modules') {
12    root = path.dirname(root)
13  }
14  if (original !== root) {
15    return Promise.resolve(root)
16  } else {
17    return Promise.resolve(getPrefixFromTree(root))
18  }
19}
20
21function getPrefixFromTree (current) {
22  if (isRootPath(current, process.platform)) {
23    return false
24  } else {
25    return Promise.all([
26      fileExists(path.join(current, 'package.json')),
27      fileExists(path.join(current, 'node_modules'))
28    ]).then(args => {
29      const hasPkg = args[0]
30      const hasModules = args[1]
31      if (hasPkg || hasModules) {
32        return current
33      } else {
34        return getPrefixFromTree(path.dirname(current))
35      }
36    })
37  }
38}
39
40module.exports._fileExists = fileExists
41function fileExists (f) {
42  return statAsync(f).catch(err => {
43    if (err.code !== 'ENOENT') {
44      throw err
45    }
46  })
47}
48
49module.exports._isRootPath = isRootPath
50function isRootPath (p, platform) {
51  return platform === 'win32'
52    ? p.match(/^[a-z]+:[/\\]?$/i)
53    : p === '/'
54}
55