2016-08-29 12 views
-1

ファイルを非同期でアップロードする方法を実装しようとしています。 私の配列のすべての項目に適用したいプロセスがあります。 私は各項目の名前をとってAPIを呼び出してそれに関する補足情報を取得してから、それをテキスト・ツー・スピーチ・ユーティリティーに送信し、その結果のwavファイルをS3インスタンスにアップロードします。ノードjs - 配列内の各アイテムに対するマルチタスク処理

私はこれを非同期的に行い、それらのすべてが終了するのを待つ方法が見つかりません。

私はセリでもできますが、時間がかかります(30ファイル(各ファイル2MB)に対して12分)。

私は非同期の方法を実装しようとしましたが、これは約5分(7分少なくなります)ですが、ネット回線に問題があることを恐れていますか?各項目に適用する

機能:

function doAll(c, lan, country, fileName, callback){ 
    getNews(c, lan) 
    .then(function(newsResults){ 
     getWavFile(newsResults, lan, fileName) 
     .then(function(wavResults){ 
      uploadToS3(country,lan,fileName) 
      .then(function(s3Results){ 
       return callback("done"); 
      }, function(s3err){ 
       console.log('s3 error: ',s3err); 
       return callback("done"); 
      }) 
     }, function(waverr){ 
      console.log('wav error: ',waverr); 
     }) 
    }, function(newserr){ 
     console.log('news error: ',newserr); 
    }) 
} 

アレイの例:

var arr = [ 
    { 
    _id: '5769369ba2d42fd82ca4d851', 
    Name: 'Sports', 
    Order: 1, 
    Color: 'White', 
    Description: 'ספורט', 
    UpdatedDate: '2016-07-28T07:44:47.906Z', 
    CreatedDate: '2016-06-21T12:44:11.468Z', 
    Country: 'IL', 
    Langs: [ 
     { 
     Name: 'Sports', 
     IsoCode: 'en', 
     Url: 'SportsJSON', 
     _id: '576b93486c7a9ff025275836' 
     }, 
     { 
     Name: 'ספורט', 
     IsoCode: 'iw', 
     Url: 'HebrewSportsJSON', 
     _id: '576be6ad56126ccc25852613' 
     } 
    ] 
    }, 
    { 
    _id: '576bf4eb28176a3e5ce15afa', 
    Name: 'Top Stories', 
    Description: 'הכותרות', 
    Color: 'ww', 
    Order: 1, 
    UpdatedDate: '2016-07-10T12:01:26.713Z', 
    CreatedDate: '2016-06-23T14:40:43.435Z', 
    Country: 'IL', 
    Langs: [ 
     { 
     Name: 'כותרות', 
     Url: 'HebrewTopStoriesJSON', 
     IsoCode: 'iw', 
     _id: '576bf52228176a3e5ce15afb' 
     }, 
     { 
     Name: 'Top Stories', 
     IsoCode: 'en', 
     Url: 'TopStoriesJSON', 
     _id: '576bf94d28176a3e5ce15afd' 
     } 
    ] 
    }, 
    { 
    _id: '5756d5d6c4a3dfe478b16aa2', 
    Description: 'Nation Channel', 
    Order: 1, 
    Color: 'blue', 
    Code: 'Nation', 
    Name: 'Nation', 
    UpdatedDate: '2016-06-24T22:23:07.198Z', 
    CreatedDate: '2016-06-07T14:10:30.699Z', 
    Country: 'US', 
    Langs: [ 
     { 
     Name: 'Nation', 
     IsoCode: 'en', 
     Url: 'NationJson', 
     _id: '576db2cb28176a3e5ce15b02' 
     } 
    ] 
    } 
] 

マイ非同期方法:

var array = [] // see the example how array look like 
var newArray= []; 
console.log('start uploading files time:', new Date()); 
for (var i = 0; i < array.length; i++) { 
    var list = array[i].Langs; 
    for (var j= 0; j < list.length; j++) { 
     var c = list[j]; 
     var lan = convertIsoCode(c.IsoCode); 
     var fileName = array[i].Name + "_" + lan; 
     var country = array[i].Country; 
     doAll(c,lan,country,fileName, function(){ 
      newArray.push(array[i]); 
      if (array.length == newArray.length) { 
       console.log('done'); 
       defer.resolve('done'); 
      } 
     }) 
    } 

} 

はEDIT:

私はasync.eachasync.parallelでそれをやろうとしましたが、成功しませんでした。

+0

私は約束についてはよく分かりませんが、「Promise.all」はあなたが探しているものです。 ['async.each'](http://caolan.github.io/async/docs.html#.each)も必要な作業を行います。 – DrakaSAN

+0

async.eachはそれぞれの機能を理解しているので、同じ時間にいくつかの機能を実行できますが、同時に各項目に対して同時にいくつかの機能を実行し、すべての完了を待って、すべてを約束しますか?私は次のものを待つ必要がありますか? – Erez

+0

'async.each'はコールバックをサポートしています。すべての関数が終了するたびに呼び出されるか、関数のいずれかのコールバックにエラーが渡されます。また、@DrakaSANを使って彼に答えたときに誰かに知らせることができます。私はあなたのポストを運だけで見ました。 – DrakaSAN

答えて

1

newArrayを削除したので、何も役に立たないので、CPU時間が浪費され、何が行われたのかをたどる恐ろしい方法でした。シンプルなカウンターがそのトリックを実行したでしょう。

それが2016年になってからES6が終了しました。あなたはそれらを不変的に使用していたので、セミコロンも追加されました。

また、doAllは意味のある名前ではありません。

'use strict'; 

const async = require('async'); 

let array = [/*data*/]; 

console.log('START ' + (new Date())); 
//Asynchronously iterate throught the array 
async.each(array, (item, callback) => { 
    //item is your array[i] 
    async.each(item.Langs, (lang, callback) => { 
     //lang is your array[i].Langs[j] 
     let lan = convertIsoCode(item.IsoCode), 
      fileName = item.Name + '_' + lan, 
      country = item.Country; 

     //Apply your functions 
     getNews(c, lan).then((newsResults) => { 
      getWavFile(newsResults, lan, fileName).then((wavResults) => { 
       uploadToS3(country,lan,fileName).then((s3Results) => { 
        //Everything is OK, callback without error 
        callback(); 
       }, (s3err) => { 
        //Raise the error 
        callback(s3err); 
       }); 
      }, (waverr) => { 
       console.log('wav error: ',waverr); 
       //Raise the error 
       callback(waverr); 
      }); 
     }, (newserr) => { 
      console.log('news error: ',newserr); 
      //Raise the error 
      callback(newserr); 
     }); 
    }, (error) => { 
     callback(error); 
    }); 
}, (error) => { 
    //If a error was raised, everything pending will be aborted and the error will be displayed 
    if(error) { 
     console.log(error); 
    //Else, just report it did fine 
    } else { 
     console.log('OK'); 
    } 
}); 
+0

魔法のように動作します!ありがとう – Erez

+0

私はES5のコードを書き直すか、ES6のコードの残りの部分を書き直して、あなたが一貫したスタイルを保つために 'eslint'のようなツールを使って助言したいと思います。あなたのコード月ラウンドを見直してください。 – DrakaSAN

+0

私は非常にありがとう – Erez

関連する問題