2017-02-01 2 views
-1

すべてのAjax呼び出しが完了したら関数を1回呼び出そうとしています。以下の$.whenは、空の配列の約束をもってすぐに呼び出されていません。 searchRecommendations()は、数回前の$.ajaxコールの成功から数回呼び出されています。それはどういうわけか責任がありますか?

var MAX = 2; //Maximum levels queried 
var ARTISTS = []; //Multidimensional array with the number of potential 'artists' i.e. compare Madonna, to Beethoven to Eminem to nth-artist 
var RELEVENT_ARTISTS = 2; //Number of relevent artists added to the list for each new artist 
var promises = []; 

$(function(){ 
    init(0); 
}) 


    function init(i){ 
    for(var i; i<1; i++){ 

     console.log('searchArtists for relevant artist '+$('input')[i].value) 
     var artist = $('input')[i].value; 
     $.ajax({ 
      url: 'https://api.spotify.com/v1/search', 
      data: { 
       q: artist, 
       type: 'artist' 
      }, 
       success: function (response) { 
        console.log(response.artists.href); 
        searchRecommendations(response.artists.items[0].id, 0) 
        //nextLevel(0) 
      } 
     }); 


    } 
    //console.log(ARTISTS) 
    //getMatches(ARTISTS) 
} 



function searchRecommendations(artist, depth) { 
      console.log(' ')     
      console.log('searchRecommendations '+artist+ ' '+ depth) 
      if(depth == MAX){ return console.log('max reached '+depth) } else { 
        promises.push(
         $.ajax({ 
          url: 'https://api.spotify.com/v1/artists/' + artist + '/related-artists', 
          data: { 
           type: 'artist', 
          }, 
          success: function (response) { 

           console.log('RESPONSE'); 
           console.log(response) 
           for(var r=0; r<RELEVENT_ARTISTS; r++){ 
            console.log(response.artists[r].name) 
            var obj = { 'artist' : response.artists[r].name, 'level':(depth+1)*5 } 

            ARTISTS.push(obj) 

            searchRecommendations(response.artists[r].id, depth+1) //Recursion 
           } 
          }  
         }) 
        ) 
      } 
} 





$.when.apply(undefined, promises).done(function() { 
    convert_artists_to_nodes_and_links(ARTISTS) 
    console.log('this is being called too soon') 
    console.log(promises) 
}) 

How to wait until jQuery ajax request finishes in a loop?

+0

「searchRecommendations」はどこにありますか? 'MAX'と' ARTISTS'はどこに定義されていますか?なぜあなたは 'searchRecommendations'から' setTimeout'を '返す 'ようにしようとしていますか? – guest271314

+0

'.ajaxStop()'を試すと、すべてのAjax呼び出しが完了するのを待ちます。ここにドキュメントがあります:http://api.jquery.com/ajaxStop/ – Girisha

+3

あなたが空の 'promises'配列で待つコードは、後で何らかの手段で関数が呼び出されると、' $ .when'魔法のように "再実行"しない...約束はイベント駆動コードの代わりではない –

答えて

1

あなたのコードの[OK]を、大きなリファクタリングが、私は、これはあなたがやりたいだろうと思います - 申し訳ありませんが、私はそれをテストすることはできません - 私は、コードを説明するために、ゆっくりと、コメントを追加しようとします

function init(i) { 
    // $('input.artist') - as I can't see your HTML, I would recommend adding cclass='artist' to inputs that you want to process 
    // [].map.call($('input.artist'), function(artist, i) { - iterate through the inputs, calling the function which returns a promise 
    // artistP will be an array of Promises 
    var artistsP = [].map.call($('input.artist'), function(artist, i) { 
     console.log('searchArtists for relevant artist ' + $('input')[i].value) 
     var artist = $('input')[i].value; 
     // return the promise returned by $.ajax 
     return $.ajax({ 
      url: 'https://api.spotify.com/v1/search', 
      data: { 
       q: artist, 
       type: 'artist' 
      } 
     }) 
     // the returned promise needs to wait for the promise returned by searchRecommendations 
     .then(function(response) { 
      console.log(response.artists.href); 
      return searchRecommendations(response.artists.items[0].id, 0); 
     }); 
    }); 
    // wait for the promises to complete and we're done 
    $.when.apply($, artistsP).done(function() { 
     convert_artists_to_nodes_and_links(ARTISTS) 
    }); 
} 

function searchRecommendations(artist, depth) { 
    console.log('searchRecommendations ' + artist + ' ' + depth) 
    if (depth == MAX) { 
     // just return undefined to stop the recursion 
     return console.log('max reached ' + depth); 
    } else { 
     // return a promise 
     return $.ajax({ 
      url: 'https://api.spotify.com/v1/artists/' + artist + '/related-artists', 
      data: { 
       type: 'artist', 
      } 
     }) 
     // the promise needs to wait for the recursed artists 
     .then(function(response) { 
      // create an array of promises to wait on 
      var promises = response.artists.map(function(artist) { 
       console.log(artist.name) 
       var obj = { 
        'artist': artist.name, 
        'level': (depth + 1) * 5 
       } 
       ARTISTS.push(obj) 
       return searchRecommendations(response.artists[r].id, depth + 1) //Recursion 
      }); 
      // return a promise that waits for all the "sub" requests 
      return $.when.apply($, promises); 
     }); 
    } 
} 
+0

私は 'jQuery.Deferred例外を取得しています:#は関数ではありませんTypeError:#は関数ではありません。 – Squirrl

+0

ええ、フィックスアップのビットが必要です - 少しうんざりしました –

+0

私はそれを学習体験ありがとう。 – Squirrl

関連する問題