FTP-клиент с асинхронным JavaScript
Я пишу в node.js и использую клиентские модули async.js и ftp.
Я использую async.series, и это функция в async.series:
var client = new ftp();
client.on('ready', function () {
for ( var i = 0 ; i < stage._sub_directories.length ; i++ ) {
var path = get_absolute_path() + DIRECTORY_NAME_LESSONS + stage._name + "/" + DIRECTORY_NAME_STAGE + stage._sub_directories[i];
var file = 'copy.' + stage._sub_directories[i] + get_xml_file_name();
client.get(path + "/" + get_xml_file_name(), function (err, stream) {
console.log('done');
if (err) throw err;
stream.once('close', function () {client.end();});
stream.pipe(fs.createWriteStream(file));
callback(null, true);
});
}
});
client.connect(config);
callback(null, true);
для асинхронного модуля. Когда он запускается, его вставить в for
петля stage._sub_directories.length
раз, а затем вставить в client.get()
только один раз (в последний раз).
создано один файл, а не больше.
в чем моя проблема? Я должен использовать другой поток асинхронного управления? или что-то другое?
2 ответа
То, как написан ваш код, не будет работать, потому что вы вызываете асинхронную функцию, client.get
внутри правильной петли.
Вы должны заменить свой обычный for
петля для async.eachSeries
метод, так как вы уже используете async.js
, Попробуй это:
client.on('ready', function () {
async.eachSeries(stage._sub_directories, function (subDir, done) {
var path = get_absolute_path() + DIRECTORY_NAME_LESSONS + stage._name + "/" + DIRECTORY_NAME_STAGE + subDir;
var file = 'copy.' + subDir + get_xml_file_name();
client.get(path + "/" + get_xml_file_name(), function (err, stream) {
if (err) return done(err);
console.log('done');
stream.once('close', function () {client.end();});
stream.pipe(fs.createWriteStream(file));
done();
});
}, function (err) {
if (err) return callback(err);
callback(null, true);
});
});
Честно говоря, разочаровывает, сколько разметки и обнаружения необходимо, чтобы "обойти" эти современные популярные модули FTP... Я автор FTPimp, который я написал специально для решения этой проблемы. Например, вы можете сделать то же самое, используя только модуль ftpimp:
ftp.connect(function () {
stage._sub_directories.forEach(function (subDir) {
var path = get_absolute_path() + DIRECTORY_NAME_LESSONS + stage._name + "/" + DIRECTORY_NAME_STAGE + subDir;
var file = 'copy.' + subDir + get_xml_file_name();
//save from -> to
ftp.save([path + "/" + get_xml_file_name(), file], function (err, name) {
console.log(err, name);
});
});
//@see http://ftpimp.net/FTP.html#event:queueEmpty
ftp.once('queueEmpty', function () {
console.log('files saved');
//do more stuff ...
ftp.quit();
});
});