0

I can't figure out why this code does not work. The movies function returns undefined when called in the App function, but the data is present in the function. I am learning React and playing with different ways to do things, so I'm a bit confused on this one.

The main App function:

import getMovies from './api/get';

const App = () => {
    var movies = getMovies('popular');
    console.log(movies); // returns undefined
    
  return (
    <div>
        <header>
            
        </header>
    </div>
  );
}

export default App;

and the getMovies function:

import $ from 'jquery'

export default function getMovies(type) {
    const apiString = 'https://api.themoviedb.org/3/movie/';
    const apiKey = MY_API_KEY;
    var urlString = '';
    switch (type) {
        case 'popular':
            urlString = apiString + 'popular?api_key=' + apiKey + '&language=en-US';
            break;
        case 'top_rated':
            urlString = apiString + 'top_rated?api_key=' + apiKey + '&language=en-US';
            break;
        case 'upcoming':
            urlString = apiString + 'upcoming?api_key=' + apiKey + '&language=en-US';
            break;
        case 'now_playing':
            urlString = apiString + 'now_playing?api_key=' + apiKey + '&language=en-US';
            break;
        default:
            urlString = apiString + 'popular?api_key=' + apiKey + '&language=en-US';
    }
    $.ajax({
        url: urlString,
        success: (latestResults) => {
            const results = latestResults.results;
            console.log(results); // returns arrays
            return results;
        },
        error: (xhr, status, err) => {
            console.error("Failed to fetch data")
          }
    });
}

Apologies if this is a stupid question, and thanks for any help.

  • 1
    getMovies function does not contain any return statement at the top level, and as the above comment says, it must return a promise which resolves to your API response – Sudhanshu Kumar Jan 13 '21 at 13:21

1 Answers1

1

getMovies should return a promise, since you are making an API call within it, otherwise you are returning from the getMovies function before the API call has finished. Have a look at w3schools.com/js/js_promise.asp

try

export default function getMovies(type) {
    return new Promise((resolve, reject) => {
       const apiString = 'https://api.themoviedb.org/3/movie/';
    const apiKey = MY_API_KEY;
    var urlString = '';
    switch (type) {
        case 'popular':
            urlString = apiString + 'popular?api_key=' + apiKey + '&language=en-US';
            break;
        case 'top_rated':
            urlString = apiString + 'top_rated?api_key=' + apiKey + '&language=en-US';
            break;
        case 'upcoming':
            urlString = apiString + 'upcoming?api_key=' + apiKey + '&language=en-US';
            break;
        case 'now_playing':
            urlString = apiString + 'now_playing?api_key=' + apiKey + '&language=en-US';
            break;
        default:
            urlString = apiString + 'popular?api_key=' + apiKey + '&language=en-US';
    }
    $.ajax({
        url: urlString,
        success: (latestResults) => {
            const results = latestResults.results;
            console.log(results); // returns arrays
            resolve(results) 
        },
        error: (xhr, status, err) => {
            console.error("Failed to fetch data")
            reject(err)
          }
    });
    })
    
}

then call to get the movies from within an effect, not in the body of the component -

const [movies, setMovies] = useState([])
useEffect(() => {
   getMovies().then((movies) => {
      setMovies(movies)
   })
}, [])

or using async/await

andy mccullough
  • 9,070
  • 6
  • 32
  • 55