]> gerrit.simantics Code Review - simantics/district.git/blob - org.simantics.maps.server/node/node-v4.8.0-win-x64/node_modules/npm/lib/utils/correct-mkdir.js
Adding integrated tile server
[simantics/district.git] / org.simantics.maps.server / node / node-v4.8.0-win-x64 / node_modules / npm / lib / utils / correct-mkdir.js
1 var chownr = require('chownr')
2 var dezalgo = require('dezalgo')
3 var fs = require('graceful-fs')
4 var inflight = require('inflight')
5 var log = require('npmlog')
6 var mkdirp = require('mkdirp')
7
8 // memoize the directories created by this step
9 var stats = {}
10 var effectiveOwner
11 module.exports = function correctMkdir (path, cb) {
12   cb = dezalgo(cb)
13   cb = inflight('correctMkdir:' + path, cb)
14   if (!cb) {
15     return log.verbose('correctMkdir', path, 'correctMkdir already in flight; waiting')
16   } else {
17     log.verbose('correctMkdir', path, 'correctMkdir not in flight; initializing')
18   }
19
20   if (stats[path]) return cb(null, stats[path])
21
22   fs.stat(path, function (er, st) {
23     if (er) return makeDirectory(path, cb)
24
25     if (!st.isDirectory()) {
26       log.error('correctMkdir', 'invalid dir %s', path)
27       return cb(er)
28     }
29
30     var ownerStats = calculateOwner()
31     // there's always a chance the permissions could have been frobbed, so fix
32     if (st.uid !== ownerStats.uid) {
33       stats[path] = ownerStats
34       setPermissions(path, ownerStats, cb)
35     } else {
36       stats[path] = st
37       cb(null, stats[path])
38     }
39   })
40 }
41
42 function calculateOwner () {
43   if (!effectiveOwner) {
44     effectiveOwner = { uid: 0, gid: 0 }
45
46     // Pretty much only on windows
47     if (!process.getuid) {
48       return effectiveOwner
49     }
50
51     effectiveOwner.uid = +process.getuid()
52     effectiveOwner.gid = +process.getgid()
53
54     if (effectiveOwner.uid === 0) {
55       if (process.env.SUDO_UID) effectiveOwner.uid = +process.env.SUDO_UID
56       if (process.env.SUDO_GID) effectiveOwner.gid = +process.env.SUDO_GID
57     }
58   }
59
60   return effectiveOwner
61 }
62
63 function makeDirectory (path, cb) {
64   cb = inflight('makeDirectory:' + path, cb)
65   if (!cb) {
66     return log.verbose('makeDirectory', path, 'creation already in flight; waiting')
67   } else {
68     log.verbose('makeDirectory', path, 'creation not in flight; initializing')
69   }
70
71   var owner = calculateOwner()
72
73   if (!process.getuid) {
74     return mkdirp(path, function (er) {
75       log.verbose('makeCacheDir', 'UID & GID are irrelevant on', process.platform)
76
77       stats[path] = owner
78       return cb(er, stats[path])
79     })
80   }
81
82   if (owner.uid !== 0 || !process.env.HOME) {
83     log.silly(
84       'makeDirectory', path,
85       'uid:', owner.uid,
86       'gid:', owner.gid
87     )
88     stats[path] = owner
89     mkdirp(path, afterMkdir)
90   } else {
91     fs.stat(process.env.HOME, function (er, st) {
92       if (er) {
93         log.error('makeDirectory', 'homeless?')
94         return cb(er)
95       }
96
97       log.silly(
98         'makeDirectory', path,
99         'uid:', st.uid,
100         'gid:', st.gid
101       )
102       stats[path] = st
103       mkdirp(path, afterMkdir)
104     })
105   }
106
107   function afterMkdir (er, made) {
108     if (er || !stats[path] || isNaN(stats[path].uid) || isNaN(stats[path].gid)) {
109       return cb(er, stats[path])
110     }
111
112     if (!made) return cb(er, stats[path])
113
114     setPermissions(made, stats[path], cb)
115   }
116 }
117
118 function setPermissions (path, st, cb) {
119   chownr(path, st.uid, st.gid, function (er) {
120     if (er && er.code === 'ENOENT') return cb(null, st)
121     return cb(er, st)
122   })
123 }