using a fetch inside another fetch in javascript

孤人 提交于 2019-11-27 00:04:14

问题


I want to get an api and after that call another one. Is it wisely using a code like this in javascript?

fetch(url, {
 method: 'get',
 }).then(function(response) {  
  response.json().then(function(data) {  
    fetch(anotherUrl).then(function(response) {
      return response.json();
    }).catch(function() {
      console.log("Booo");
    });
  });  
}) 
.catch(function(error) {  
  console.log('Request failed', error)  
});

回答1:


Fetch returns a promise, and you can chain multiple promises, and use the result of the 1st request in the 2nd request:

The example uses the SpaceX API to get the info of the latest launch, find the rocket's id, and fetch the rocket's info.

var url = 'https://api.spacexdata.com/v2/launches/latest';

var result = fetch(url, {
    method: 'get',
  }).then(function(response) {
    return response.json(); // pass the data as promise to next then block
  }).then(function(data) {
    var rocketId = data.rocket.rocket_id;

    console.log(rocketId, '\n');
  
    return fetch('https://api.spacexdata.com/v2/rockets/' + rocketId); // make a 2nd request and return a promise
  })
  .then(function(response) {
    return response.json();
  })
  .catch(function(error) {
    console.log('Request failed', error)
  })

// I'm using the result variable to show that you can continue to extend the chain from the returned promise
result.then(function(r) {
  console.log(r); // 2nd request result
});
.as-console-wrapper { max-height: 100% !important; top: 0; }



回答2:


There is not an issue with nesting fetch() calls. It depends on what you are trying to achieve by nesting the calls.

You can alternatively use .then() to chain the calls. See also How to structure nested Promises

fetch(url)
.then(function(response) { 
  return response.json()
})
.then(function(data) {   
  // do stuff with `data`, call second `fetch`
  return fetch(data.anotherUrl)
})
.then(function(response) { 
  return response.json(); 
})
.then(function(data) {
  // do stuff with `data`
})
.catch(function(error) { 
  console.log('Requestfailed', error) 
});



回答3:


This is a common question people get tripped up by when starting with Promises, myself included when I began. However, first...

It's great you're trying to use the new Fetch API, but if I were you I would use a XMLHttpRequest implementation for now, like jQuery AJAX or Backbone's overridden implementation of jQuery's .ajax(), if you're already using these libraries. The reason is because the Fetch API is still so new, and therefore experimental at this stage.

With that said, people definitely do use it, but I won't in my own production code until it's out of "experimental" status.

If you decide to continue using fetch, there is a polyfill available. NOTE: you have to jump through extra hoops to get error handling to work properly, and to receive cookies from the server. If you're already loading jQuery, or using Backbone, just stick with those for now; not completely dreadful, anyway.

Now onto code:

You want a flat structure, else you're missing the point of Promises. It's not wise to nest promises, necessarily, because Promises solve what nested async callbacks (callback hell) could not.

You will save yourself time and energy, and produce less buggy code by simply using a more readable code structure. It's not everything, but it's part of the game, so to speak.

Promises are about making asynchronous code retain most of the lost properties of synchronous code such as flat indentation and one exception channel.

-- Petka Antonov (Bluebird Promise Library)

// run async #1
asyncGetFn()
// first 'then' - execute more async code as an arg, or just accept results
// and do some other ops
.then(response => {
    // ...operate on response data...or pass data onto next promise, if needed
})
// run async #2
.then(asyncGetAnotherFn)
.then(response => {
    // ...operate on response data...or pass data onto next promise, if needed
})
// flat promise chain, followed by 'catch'
// this is sexy error handling for every 'then' above
.catch(err => {  
  console.error('Request failed', err) 
  // ...raise exeption...
  // ... or, retry promise... 
})


来源:https://stackoverflow.com/questions/40981040/using-a-fetch-inside-another-fetch-in-javascript

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!