我要进行一组相当复杂的API调用,并且我尝试尽可能地做到优雅和高效。我了解如何使用服务的promise api $http来链接请求,以及如何使用$q服务并行进行请求。但是对于此特定的API工作流程,我需要同时进行。
$http
$q
这是高级API流程的示例:
/dog/<dog_id>
/breed/<breed_id>
/food/<food_id>
/cat/<cat_id>
/turkey/<turkey_id>
/fish/<fish_id>
第一层请求均具有已知ID。然而,<breed_id>需要使/breed呼叫必须从解析/dog响应,并<food_id>作出必要的/food呼叫必须从解析/breed响应。因此/dog,/breed和/food都需要链接起来。但是/cat,/turkey和/fish可以与整个/dog链条平行。
<breed_id>
/breed
/dog
<food_id>
/food
/cat
/turkey
/fish
我现在所拥有的(并且工作正常)是两组独立的请求。我如何改善这一流程?有没有一种方法可以将两个堆栈组合在一起,从而导致一个单次执行Promise .then()?
.then()
var dogId = '472053', catId = '840385', turkeyId = '240987', fishId = '510412'; var myData = {}; var firstSetComplete = false, secondSetComplete = false, returnData = function() { if (firstSetComplete && secondSetComplete) { console.log("myData.dog", myData.dog); console.log("myData.dog.breed", myData.dog.breed); console.log("myData.dog.food", myData.dog.food); console.log("myData.cat", myData.cat); console.log("myData.turkey", myData.turkey); console.log("myData.fish", myData.fish); } }; // first call set $http.get('http://example.com/dog/' + dogId) .then(function(response) { myData.dog = response.data; return $http.get('http://example.com/breed/' + response.data.breed_id); }) .then(function(response) { myData.dog.breed = response.data; return $http.get('http://example.com/food/' + response.data.food_id); }) .then(function(response) { myData.dog.food = response.data; firstSetComplete = true; returnData(); }); // second call set $q.all([ $http.get('http://example.com/cat/' + catId), $http.get('http://example.com/turkey/' + turkeyId), $http.get('http://example.com/fish/' + fishId) ]) .then(function(responses) { myData.cat = responses[0].data; myData.turkey = responses[1].data; myData.fish = responses[2].data; secondSetComplete = true; returnData(); });
您可以像这样传递第一个链:
$q.all([ $http.get('http://example.com/cat/' + catId), $http.get('http://example.com/turkey/' + turkeyId), $http.get('http://example.com/fish/' + fishId), $http.get('http://example.com/dog/' + dogId) .then(function(response) { myData.dog = response.data; return $http.get('http://example.com/breed/' + response.data.breed_id); }) .then(function(response) { myData.dog.breed = response.data; return $http.get('http://example.com/food/' + response.data.food_id); }) .then(function(response) { myData.dog.food = response.data; return myData; }) ]) .then(function(responses) { myData.cat = responses[0].data; myData.turkey = responses[1].data; myData.fish = responses[2].data; secondSetComplete = true; returnData(); });
对狗的那条大保证书最终会返回一个单独的保证书,当最后一个then被调用时,它会被解决,并由最终功能的结果来解决。因此,没有理由不能将其嵌套在$q.all()呼叫中。
then
$q.all()