fs.js
1 const parseJson = require('parse-json'); 2 const os = require('os'); 3 let path = require('path'); 4 let fs = require('fs-extra'); 5 let utils = require('../utils/utils.js'); 6 require('colors'); 7 8 const pathConfigs = { 9 DAPP_PATH: process.env.DAPP_PATH, 10 EMBARK_PATH: process.env.EMBARK_PATH 11 }; 12 13 function restrictPath(receiver, binding, count, args) { 14 const dapp = dappPath(); 15 const embark = embarkPath(); 16 17 const allowedRoots = [ 18 dapp, 19 embark, 20 os.tmpdir() 21 ]; 22 23 let allInsideRestricted = true; 24 25 for(let i = 0; i < count; i++) { 26 let resolved = path.resolve(dapp, args[i]); 27 allInsideRestricted = allowedRoots.some(p => { return resolved.indexOf(p) === 0; }); 28 if(!allInsideRestricted) break; 29 } 30 31 if(allInsideRestricted) return receiver.apply(binding, args); 32 throw new Error('EPERM: Operation not permitted'); 33 } 34 35 function mkdirpSync() { 36 return restrictPath(fs.mkdirpSync, fs.mkdirpSync, 1, arguments); 37 } 38 39 function mkdirp() { 40 return restrictPath(fs.mkdirp, fs.mkdirp, 1, arguments); 41 } 42 43 function readdir() { 44 return restrictPath(fs.readdir, fs.readdir, 1, arguments); 45 } 46 47 function stat() { 48 return restrictPath(fs.stat, fs.stat, 1, arguments); 49 } 50 51 function remove() { 52 return restrictPath(fs.remove, fs.remove, 1, arguments); 53 } 54 55 function copy() { 56 return restrictPath(fs.copy, fs.copy, 2, arguments); 57 } 58 59 function copySync() { 60 return restrictPath(fs.copySync, fs.copySync, 2, arguments); 61 } 62 63 function move(){ 64 return restrictPath(fs.move, fs.move, 2, arguments); 65 } 66 67 function moveSync() { 68 return restrictPath(fs.moveSync, fs.moveSync, 2, arguments); 69 } 70 71 function appendFileSync() { 72 return restrictPath(fs.appendFileSync, fs.writeFileSync, 1, arguments); 73 } 74 75 function writeFile() { 76 return restrictPath(fs.writeFile, fs.writeFileSync, 1, arguments); 77 } 78 79 function writeFileSync() { 80 return restrictPath(fs.writeFileSync, fs.writeFileSync, 1, arguments); 81 } 82 83 function readFile() { 84 return restrictPath(fs.readFile, fs.readFile, 1, arguments); 85 } 86 87 function readFileSync() { 88 return restrictPath(fs.readFileSync, fs.readFileSync, 1, arguments); 89 } 90 91 function readdirSync() { 92 return restrictPath(fs.readdirSync, fs.readdirSync, 1, arguments); 93 } 94 95 function statSync() { 96 return restrictPath(fs.statSync, fs.statSync, 1, arguments); 97 } 98 99 function readJSONSync() { 100 let content = readFileSync.apply(readFileSync, arguments); 101 try { 102 return parseJson(content); 103 } catch(e) { 104 console.error("error: ".red + arguments[0].green.underline + " " + e.message.green); 105 process.exit(0); 106 } 107 } 108 109 function writeJSONSync() { 110 return restrictPath(fs.writeJSONSync, fs.writeJSONSync, 1, arguments); 111 } 112 113 function writeJson() { 114 return restrictPath(fs.writeJson, fs.writeJson, 1, arguments); 115 } 116 117 function existsSync() { 118 return restrictPath(fs.existsSync, fs.existsSync, 1, arguments); 119 } 120 121 function access() { 122 return restrictPath(fs.access, fs.access, 1, arguments); 123 } 124 125 function removeSync() { 126 return restrictPath(fs.removeSync, fs.removeSync, 1, arguments); 127 } 128 129 function anchoredPath(envAnchor, ...args) { 130 let anchor = pathConfigs[envAnchor]; 131 if (!pathConfigs[envAnchor]) { 132 console.error(`process.env.${envAnchor} was not set`.bold.red); 133 process.exit(1); 134 } 135 return utils.joinPath(anchor, ...args); 136 } 137 138 function embarkPath() { 139 return anchoredPath('EMBARK_PATH', ...arguments); 140 } 141 142 function dappPath() { 143 return anchoredPath('DAPP_PATH', ...arguments); 144 } 145 146 function pkgPath() { 147 return anchoredPath('PKG_PATH', ...arguments); 148 } 149 150 function createWriteStream() { 151 return restrictPath(fs.createWriteStream, fs.createWriteStream, 1, arguments); 152 } 153 154 function tmpDir() { 155 let os = require('os'); 156 return utils.joinPath(os.tmpdir(), ...arguments); 157 } 158 159 function copyPreserve(sourceFilePath, targetFilePath) { 160 const path = require('path'); 161 let ext = 1; 162 let preserved = targetFilePath; 163 while (fs.existsSync(preserved)) { 164 let extname = path.extname(targetFilePath); 165 preserved = utils.joinPath( 166 path.dirname(targetFilePath), 167 `${path.basename(targetFilePath, extname)}.${ext}${extname}` 168 ); 169 ext++; 170 } 171 if (preserved !== targetFilePath) { 172 fs.copySync(targetFilePath, preserved); 173 } 174 fs.copySync(sourceFilePath, targetFilePath); 175 } 176 177 function outputFileSync(){ 178 return fs.outputFileSync.apply(fs.outputFile, arguments); 179 } 180 181 module.exports = { 182 access, 183 appendFileSync, 184 copy, 185 copySync, 186 createWriteStream, 187 embarkPath, 188 existsSync, 189 mkdirp, 190 mkdirpSync, 191 move, 192 moveSync, 193 outputFileSync, 194 readFile, 195 readFileSync, 196 readJSONSync, 197 readdir, 198 readdirSync, 199 remove, 200 removeSync, 201 stat, 202 statSync, 203 tmpDir, 204 writeFile, 205 writeFileSync, 206 writeJSONSync, 207 copyPreserve, 208 dappPath, 209 pkgPath, 210 outputFileSync, 211 writeJson 212 };