copy-dir.js 3.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130
  1. /**
  2. * Module dependencies.
  3. */
  4. var fs = require('fs');
  5. var path = require('path');
  6. var util = require('util');
  7. var EventEmitter = require('events').EventEmitter;
  8. var rl = require("readline").createInterface(process.stdin, process.stdout);
  9. var ndir = require('../');
  10. if (process.argv.length < 4) {
  11. console.log('Usage: node copy-dir.js <fromdir> <todir>');
  12. process.exit(1);
  13. }
  14. function CopyDir(fromdir, todir) {
  15. this.tasks = [];
  16. this.walkEnd = false;
  17. this.copyfileCount = 0;
  18. };
  19. util.inherits(CopyDir, EventEmitter);
  20. CopyDir.prototype.start = function() {
  21. var self = this;
  22. self.emit('start');
  23. var walker = ndir.walk(fromdir);
  24. walker.on('dir', function(dirpath, files) {
  25. var doNext = self.tasks.length === 0;
  26. self.tasks.push([dirpath, true]);
  27. for (var i = 0, l = files.length; i < l; i++) {
  28. var info = files[i];
  29. self.tasks.push([info[0], info[1].isDirectory()]);
  30. }
  31. if (doNext) {
  32. process.nextTick(function() {
  33. self.next();
  34. });
  35. }
  36. });
  37. walker.on('end', function() {
  38. self.walkEnd = true;
  39. });
  40. };
  41. CopyDir.prototype.next = function() {
  42. var task = this.tasks.shift();
  43. if (!task) {
  44. if (this.walkEnd) {
  45. this.emit('end');
  46. }
  47. return;
  48. }
  49. var self = this;
  50. var f = task[0];
  51. var t = f.replace(fromdir, '');
  52. if (t[0] === '/') {
  53. t = t.substring(1);
  54. }
  55. t = path.join(todir, t);
  56. var isdir = task[1];
  57. if (isdir) {
  58. ndir.mkdir(t, function(err) {
  59. self.next();
  60. });
  61. return;
  62. }
  63. self.copyfile(f, t, function() {
  64. self.next();
  65. });
  66. };
  67. CopyDir.prototype._copyfile = function _copyfile(fromfile, tofile, callback) {
  68. var self = this;
  69. self.emit('startCopyfile', fromfile, tofile);
  70. ndir.copyfile(fromfile, tofile, function(err) {
  71. self.emit('endCopyfile', err, fromfile, tofile);
  72. if (!err) {
  73. self.copyfileCount++;
  74. }
  75. callback(err);
  76. });
  77. }
  78. CopyDir.prototype.copyfile = function copyfile(fromfile, tofile, callback) {
  79. var needCopy = true;
  80. var self = this;
  81. path.exists(tofile, function(exists) {
  82. if (exists) {
  83. self.emit('fileExists', tofile, function(confirm) {
  84. if (confirm) {
  85. return self._copyfile(fromfile, tofile, callback);
  86. }
  87. callback();
  88. })
  89. return;
  90. }
  91. self._copyfile(fromfile, tofile, callback);
  92. });
  93. };
  94. var fromdir = path.resolve(process.argv[2]);
  95. var todir = path.resolve(process.argv[3]);
  96. var copyworker = new CopyDir(fromdir, todir);
  97. copyworker.on('start', function() {
  98. console.log('Start copy %s to %s', fromdir, todir);
  99. });
  100. copyworker.on('fileExists', function(tofile, confirmCallback) {
  101. rl.question('File "' + tofile + '" exists, overwrite? > ', function (answer) {
  102. confirmCallback(answer === 'yes' || answer === 'y');
  103. });
  104. });
  105. copyworker.on('startCopyfile', function(fromfile, tofile) {
  106. util.print(util.format('Copying "%s" to "%s" ... ', fromfile, tofile));
  107. });
  108. copyworker.on('endCopyfile', function(err, fromfile, tofile) {
  109. util.print((err ? 'Error!!!' : 'done.') + '\n');
  110. });
  111. function exit() {
  112. console.log('\nTotal copy %d files.', copyworker.copyfileCount);
  113. process.exit(0);
  114. };
  115. copyworker.on('end', exit);
  116. rl.on('close', exit);
  117. copyworker.start();