Assigning a return value from two chained promises to an outside variable

Viewed 29

I have two functions that, through promises, asynchronously return values from HTTP GET requests.

One needs to be called after the other because it depends on the result of the first one.

I trained to chain them using then but, although both GET requests are happening and bringing the expected JSON responses, I can't figure out how to assign the final return value to a variable that I can use outside both functions.

function getPageInfo(config, lastPageId) {

    axios.get('http://localhost:8000/page/'+lastPageId, config)
         .then(res => {
             return res.data;
         })
         .catch(err => console.log(err));

}

function getUserPages(config) {

    const userId = localStorage.getItem('userId');

    axios.get('http://localhost:8000/user/'+userId, config)
         .then(res => {
             const pageInfo = getPageInfo(config, res.data.pages[res.data.pages.length - 1]);
             console.log(pageInfo);
                return pageInfo;
         })
         .catch(err => console.log(err));

}
2 Answers

Adjust your code to something like this:

// note the returns
function getPageInfo(config, lastPageId) {
    return axios.get('http:.....')
}

function getUserPages(config) {
    const userId = localStorage.getItem('userId');
    return axios.get('http://lo....')
}

let res1;
let res2;
getPageInfo(...).then(result => {
  // assign the result somewhere
  res1 = result;
   // return the next promese
  return getUserPages(...);
}).then(result => {
  res2 = result;
}).catch(error => {
  console.log(error)
})

Must you use .then() and .catch()?

It's more modern to use async/await:

(async function () {
    try {
        const userId = localStorage.getItem('userId');
        let res = await axios.get('http://localhost:8000/user/'+userId, config);
        let lastPageId = res.data.pages[res.data.pages.length - 1]);
        let pageInfo = await axios.get(http://localhost:8000/page/'+lastPageId, config);
        console.log(pageInfo);
    } catch (err) {
        console.log(err);
    }
})();

Below is a runnable example of Promise chaining using async/await:

function fetch(method, url) {
  return new Promise(function (resolve, reject) {
    var xhr = new XMLHttpRequest();
    xhr.open(method, url);
    xhr.onload = function () {
      if (xhr.status < 200 && xhr.status >= 300) {
        reject(new Error(`HTTP Error ${xhr.status}: ${xhr.statusText}`));
        return;
      }
      resolve(xhr.response);
    };
    xhr.onerror = function () {
      reject(new Error(`HTTP Error ${xhr.status}: ${xhr.statusText}`));
    };
    xhr.send();
  });
}

(async function () {
    try {
        let q = "webmap owner:Esri";
        let searchText = await fetch("GET", `https://www.arcgis.com/sharing/rest/search?q=${encodeURIComponent(q)}&f=json`);
        let search = JSON.parse(searchText);
        let itemId = search.results[0].id;
        console.log(`itemId: ${itemId}`);
        let itemText = await fetch("GET", `https://www.arcgis.com/sharing/rest/content/items/${itemId}?f=json`);
        let item = JSON.parse(itemText);
        console.log(`title: ${item.title}`);
        console.log(`snippet: ${item.snippet}`);
    } catch (err) {
        console.error(err.message);
    }
})();

Related