$.ajax で直列処理を行う
2016年もjQuery を使ってます。
ふと、以下のようなことがしたくなりました。
非同期ではなく一つの処理が終わったら次の処理を実行するようにして、処理の順番を保証したい
戻ってきたdata を処理してViewに描画したい
でいろいろと悩んだのですが以下のように実装しました。
// number_list は可変リストという想定 var number_list = [ 'number1', 'number2', 'number3', 'number4', ]; var html_data = []; var number_list_length = number_list.length; var loadDataRecursive = function(){ if(!number_list ) { return; } var number = number_list.shift(); var url = '//cdn.hogehoge.jp/json/' + number + '.json'; $.ajax({ type: 'GET', url: url, dataType: 'jsonp', jsonpCallback: 'callback_' + model_code, }).done(function(data) { // dataをつかって描画処理する html_data.push('<p class="title">' + data.productName + '</p>'); html_data.push('<p class="title">' + data.productNumber + '</p>'); // 最後まで処理を行ったらappend する if(number === number_list_length) { $('#model-list').append(html_data.join('')); } // 再帰的にコール if (number) { loadDataRecursive(); } }).fail(function() { console.log("loadDataRecursive is failed: " + number ); }); }; loadDataRecursive();
ポイントは
var number = number_list.shift();
と
if (number) { loadDataRecursive(); }
です。
shift()
メソッドは、配列から最初の要素を取り除き、その要素を返します。このメソッドは配列の長さを変えます。
いわゆる破壊的なメソッドです。
返された要素をもとに非同期通信を行い、number_list
が空になるまでloadDataRecursive()
を実行し再帰的に繰り返します。
loadDataRecursive()
自体はひとつのjson しか処理を行いません。
number_list
の要素数だけ、処理を繰り返すことで処理の順番が保証されます。
描画処理以下のように行います。
配列にDOMデータをプッシュしておいて最後にそいつを表示したいDOMにappend()
します。
// dataをつかって描画処理する html_data.push('<p class="title">' + data.productName + '</p>'); html_data.push('<p class="title">' + data.productNumber + '</p>'); // 最後まで処理を行ったらappend する if(number === number_list_length) { $('#model-list').append(html_data.join('')); }
これを実現するために丸一日つぶれました。