问题
I'm having issues trying to work with api "pagination", I need to merge multiple objects into one. However, I can't seem to figure out how to do this with promises and I'm not sure how to work with async/await to get the best results.
I have a class called selly, which works with the Selly API.
getAllProducts(page = 1) {
return this.makeRequest('products', { page: page });
}
makeRequest(endpoint, params = {}) {
return axios
.get(`https://selly.gg/api/v2/${endpoint}`, {
headers: {
Authorization: `Basic ${this.genApiToken(this.apiKey, this.apiEmail)}`,
'User-Agent': `username - localhost`,
},
params: params,
})
.catch((err) => {
console.log(err);
});
}
Which worked great, until I realized I need to fetch multiple pages and combine all of the results into a single object. Here's my attempt:
app.get('/api/products', (req, res) => {
res.setHeader('Content-Type', 'application/json');
selly.getAllProducts().then((request) => {
const pages = request.headers['x-total-pages'];
let products = request.data;
if (pages > 1) {
let i = 2;
while (pages >= i) {
selly.getAllProducts(i).then((nextPageRequest) => {
nextPageRequest.data.forEach((item) => {
products.push(item);
});
});
i++;
}
}
res.send(JSON.stringify(products));
});
});
I can't seem to push nextPageRequest to products object. Obviously because res.send runs before the promise selly.getAllProducts(i) is finished.
I understand that the best optimization for this is using async and await, however I just can't get the basic concept of it, or well, at-least how would I refactor my code into using async and await.
How can I get this working?
回答1:
You can make the whole app.get handler async, then await the inital request to figure out how many pages there are, then use a for loop and await additional calls of selly.getAllProducts, pushing the result to the products array. Make sure to try/catch so you can handle errors:
app.get('/api/products', async (req, res) => {
res.setHeader('Content-Type', 'application/json');
try {
const request = await selly.getAllProducts();
const pages = request.headers['x-total-pages'];
const products = request.data;
for (let i = 2; i <= pages; i++) {
const { data } = await selly.getAllProducts(i);
products.push(...data);
}
res.send(JSON.stringify(products));
} catch(e) {
// handle errors
}
});
来源:https://stackoverflow.com/questions/53992630/cant-push-object-into-another-object-how-can-i-change-my-code-to-work-with-asy