index.js 2.6 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798
  1. var path = require('path');
  2. var fs = require('fs');
  3. var _0777 = parseInt('0777', 8);
  4. module.exports = mkdirP.mkdirp = mkdirP.mkdirP = mkdirP;
  5. function mkdirP (p, opts, f, made) {
  6. if (typeof opts === 'function') {
  7. f = opts;
  8. opts = {};
  9. }
  10. else if (!opts || typeof opts !== 'object') {
  11. opts = { mode: opts };
  12. }
  13. var mode = opts.mode;
  14. var xfs = opts.fs || fs;
  15. if (mode === undefined) {
  16. mode = _0777 & (~process.umask());
  17. }
  18. if (!made) made = null;
  19. var cb = f || function () {};
  20. p = path.resolve(p);
  21. xfs.mkdir(p, mode, function (er) {
  22. if (!er) {
  23. made = made || p;
  24. return cb(null, made);
  25. }
  26. switch (er.code) {
  27. case 'ENOENT':
  28. mkdirP(path.dirname(p), opts, function (er, made) {
  29. if (er) cb(er, made);
  30. else mkdirP(p, opts, cb, made);
  31. });
  32. break;
  33. // In the case of any other error, just see if there's a dir
  34. // there already. If so, then hooray! If not, then something
  35. // is borked.
  36. default:
  37. xfs.stat(p, function (er2, stat) {
  38. // if the stat fails, then that's super weird.
  39. // let the original error be the failure reason.
  40. if (er2 || !stat.isDirectory()) cb(er, made)
  41. else cb(null, made);
  42. });
  43. break;
  44. }
  45. });
  46. }
  47. mkdirP.sync = function sync (p, opts, made) {
  48. if (!opts || typeof opts !== 'object') {
  49. opts = { mode: opts };
  50. }
  51. var mode = opts.mode;
  52. var xfs = opts.fs || fs;
  53. if (mode === undefined) {
  54. mode = _0777 & (~process.umask());
  55. }
  56. if (!made) made = null;
  57. p = path.resolve(p);
  58. try {
  59. xfs.mkdirSync(p, mode);
  60. made = made || p;
  61. }
  62. catch (err0) {
  63. switch (err0.code) {
  64. case 'ENOENT' :
  65. made = sync(path.dirname(p), opts, made);
  66. sync(p, opts, made);
  67. break;
  68. // In the case of any other error, just see if there's a dir
  69. // there already. If so, then hooray! If not, then something
  70. // is borked.
  71. default:
  72. var stat;
  73. try {
  74. stat = xfs.statSync(p);
  75. }
  76. catch (err1) {
  77. throw err0;
  78. }
  79. if (!stat.isDirectory()) throw err0;
  80. break;
  81. }
  82. }
  83. return made;
  84. };