Hi community!
I’m trying to complete the last step (43) of the last project ‘Wanderlust’ of the JavaScript course. In particular this:
For a real challenge, try fetching venue photos! This will require an additional request for venue details for each venue, as the photo information is not returned in the initial request.
So I have 2 async functions:
Async function: getVenues
const getVenues = async () => {
const city = $input.val();
const urlToFetch = `${url}?${near}${city}&${limit}&client_id=${clientId}&client_secret=${clientSecret}&${version}`;
try{
const response = await fetch(urlToFetch);
if(response.ok){
const jsonResponse = await response.json();
const venues = jsonResponse.response.groups[0].items.map(e => e.venue); //extract venues out of response
return venues;
}
} catch(error){console.log(error.message);}
};
This function gets a certain amount of venues using the inserted city name from the Foursquare API. These venue objects don’t have much details (API response): id, name, location.
To get a photo of the venue I used the ‘details’ response from the API. This response has the property ‘bestPhoto’ with the prefix & suffix to the photo I want to use.
To get the details I made this function:
Async function: getVenueDetails
const getVenueDetails = async id => {
const urlToFetch = `${url2}${id}?client_id=${clientId}&client_secret=${clientSecret}&${version}`;
try{
const response = await fetch(urlToFetch);
if(response.ok){
const jsonResponse = await response.json();
const details = jsonResponse.response.venue;
return details;
}
} catch(error){console.log(error.message);}
};
This gets the details of a specified venue (with the id).
Now I need to accomplish this:
- Get the venues of the inserted city
- Get the ID’s of the venues
- Get the details of the ID’s of the venues
- Pass the details to a render function to show the wanted info on the website (unfinished, but added on the bottom)
I’m stuck at passing the details to the render function:
getVenues()
.then(async venues => {
const details = [];
for(let i = 0; i <venues.length; i++){ //Can't use forEach
await details.push(getVenueDetails(venues[i].id));
}
return renderVenues(details);
});
If I log the ‘details’ after the loop this contains 3 pending Promise-objects.
So it looks like the for-loop doesn’t wait on the getVenueDetails().
So here’s my question: How can I loop through the result of a async-function and pass that result to another async function?
Googling got me more confused about looping & async/await. Some say it’s impossible, others say you can’t use .forEach.
I have to feeling I’m making this more complex than it is. So all help is appreciated &
thank you in advance!
renderVenues(data)
const renderVenues = (venues) => {
console.log('Render');
console.log(venues);
console.log(venues.forEach(v => v.value.bestPhoto));
$venueDivs.forEach(($venue, index) => {
// Add your code here:
const ven = venues[0];
console.log(ven);
const venueIcon = ven.categories[0].icon;
const venueImgSrc = `${venueIcon.prefix}bg_64${venueIcon.suffix}`;
console.log('RENDER');
console.log(venue);
let venueContent = createVenueHTML(ven.name, ven.location, venueImgSrc);
$venue.append(venueContent);
});
$destination.append(`<h2>${venues[0].location.city}</h2>`);
};