I am writing a site with information about films. I need to get my hands on genres. But the problem is this. In the request, where all the main information is located, the genres are indicated by id. I need to make another request where there are these id and genre names. In a Vue component, I made a for loop. With it, I show basic information besides genres. How can I combine the two queries?
My Code:
movies.js
export default { actions: { async getPopularFilms({ commit }) { const res_movies = await fetch( 'https://api.themoviedb.org/3/movie/popular?api_key=d502a3d84eb533756ec099ef127a2acd&language=en-US&page=1' ); const { results } = await res_movies.json(); commit('updateFilms', results); // Fetch genres const res_genres = await fetch( 'https://api.themoviedb.org/3/genre/movie/list?api_key=d502a3d84eb533756ec099ef127a2acd&language=en-US' ); const { genres } = await res_genres.json(); let ids = []; let genres_ids = []; for (let id = 0; id < results.length; id++) { ids.push(results[id].genre_ids); } for (let id = 0; id < genres.length; id++) { genres_ids.push(genres[id]); } console.log(ids); console.log(genres_ids); }, }, mutations: { updateFilms(state, films) { state.popular = films; }, updateGenres(state, genres) { state.genres = genres; }, }, state: { popular: [], genres: [], }, getters: { returnFilms(state) { return state.popular; }, returnGenres(state) { return state.genres; }, }, };
PopularMovies.vue
<template> <div class="container mx-auto px-4 pt-8"> <div class="popular-movies"> <h2 class="uppercase tracking-wider text-lg text-orange-500 font-semibold" > Popular movies </h2> <div class="grid grid-cols-1 sm:grid-cols-2 md:grid-cols-3 lg:grid-cols-5 gap-4" > <div v-for="movies in returnFilms" :key="movies.id" class="mt-8"> <img :src="'https://image.tmdb.org/t/p/w200' + movies.poster_path" alt="poster" class="hover:opacity-75 transition ease-in-out duration-150" /> <div class="mt-2"> <p class="text-lg mt-2 hover:text-gray-300">{{ movies.title }}</p> <div class="flex items-center mt1 text-sm text-gray-400"> <svg class="fill-current text-orange-500 w-4" viewBox="0 0 24 24"> <g data-name="Layer 2"> <path d="M17.56 21a1 1 0 01-.46-.11L12 18.22l-5.1 2.67a1 1 0 01-1.45-1.06l1-5.63-4.12-4a1 1 0 01-.25-1 1 1 0 01.81-.68l5.7-.83 2.51-5.13a1 1 0 011.8 0l2.54 5.12 5.7.83a1 1 0 01.81.68 1 1 0 01-.25 1l-4.12 4 1 5.63a1 1 0 01-.4 1 1 1 0 01-.62.18z" data-name="star" ></path> </g> </svg> <span class="ml-1">{{ movies.vote_average * 10 }}%</span> <span class="mx-2">|</span> <span>{{ movies.release_date }}</span> </div> <div class="text-gray-300 text-sm">aaa</div> </div> </div> </div> </div> </div> </template> <script> import { mapGetters, mapActions } from 'vuex'; export default { name: 'Popular Movies', computed: { ...mapGetters(['returnFilms']), }, methods: { ...mapActions(['getPopularFilms']), }, async mounted() { this.getPopularFilms(); }, }; </script> <style lang="scss"> .text-orange-500 { color: #ed8936; } </style>
My gets requests: https://api.themoviedb.org/3/movie/popular?api_key=d502a3d84eb533756ec099ef127a2acd&language=en-US&page=1
Advertisement
Answer
Assuming you want the genreIds transformed to their name, within results.
Try this. I cannot test it unfortunately. I am on mobile.
async getPopularFilms({ commit }) { const res_movies = await fetch( 'https://api.themoviedb.org/3/movie/popular?api_key=d502a3d84eb533756ec099ef127a2acd&language=en-US&page=1' ); const { results } = await res_movies.json(); commit('updateFilms', results); // Fetch genres const res_genres = await fetch( 'https://api.themoviedb.org/3/genre/movie/list?api_key=d502a3d84eb533756ec099ef127a2acd&language=en-US' ); const { genres } = await res_genres.json(); const filmsWithGenres = results.map( ({genre_ids, ...rest}) => ({...rest, genre_ids: genre_ids.map(id => genres.find(genre => genre.id === id).name )}) ) console.log(filmsWithGenres); },