Follow

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use
Contact

My API is returning undefined instead of response value

I’m consuming an API using Axios in React, but when i come to set the response in a State so I may use the data, it is undefined. The funny thing is, if I put console.log inside Get.js I see the array perfectly. Am I returning the value the wrong way ?

PS: When I use console.log inside the Get.js,inside the 2nd .then, it prints two times the array. Why ?

MainPage.jsx

MEDevel.com: Open-source for Healthcare and Education

Collecting and validating open-source software for healthcare, education, enterprise, development, medical imaging, medical records, and digital pathology.

Visit Medevel

import { useEffect, useState } from 'react';
import { axiosGet } from '../../services/Get';
import { Header } from '../../components/Header/';
import { Welcome } from '../../components/Welcome/';

export const MainPage = () => {
  const [data, setData] = useState([]);
  useEffect(() => {
    console.log(axiosGet());
    setData(axiosGet());
  }, []);

  return (
    <>
      <Header />
      <Welcome />
      {data.length &&
        data.map(obj => {
        <p key={obj.id}>obj.name</p>;
    })}
    </>
  );

Get.js

import axios from 'axios';

export function axiosGet() {
  axios
    .get(
      `https://api.rawg.io/api/games?key=a6a08e14b07f41d09e846ec3c01e5db0&dates=2019-10-10,2022-03-01&page=2`
    )
    .then(res => {
      return res.data.results;
    })
    .then(arr => {
      return arr;
    })
    .catch(err => {
      console.error('oops! error: ' + err);
    });
}

if I change the Get.js code at this piece of code:

.then(res => {
          return res.data.results;
        })
        .then(arr => {
          console.log(arr)
          return arr;
        })

I got this:

Array(20) [ {…}, {…}, {…}, {…}, {…}, {…}, {…}, {…}, {…}, {…}, … ]
​
0: Object { slug: "forza-horizon-5", name: "Forza Horizon 5", playtime: 11, … }
​
1: Object { slug: "call-of-duty-modern-warfare", name: "Call of Duty: Modern Warfare (2019)", playtime: 0, … }
​
2: Object { slug: "resident-evil-village", name: "Resident Evil: Village", playtime: 16, … }
​
3: Object { slug: "assassins-creed-valhalla", name: "Assassin's Creed Valhalla", playtime: 0, … }
​
4: Object { slug: "genshin-impact", name: "Genshin Impact", playtime: 0, … }
​
5: Object { slug: "mafia", name: "Mafia: Definitive Edition", playtime: 9, … }
​
6: Object { slug: "superhot-mind-control-delete", name: "SUPERHOT: MIND CONTROL DELETE", playtime: 2, … }
​
7: Object { slug: "valheim", name: "Valheim", playtime: 11, … }
​
8: Object { slug: "it-takes-two-2", name: "It Takes Two", playtime: 11, … }
​
9: Object { slug: "deep-rock-galactic", name: "Deep Rock Galactic", playtime: 6, … }
​
10: Object { slug: "risk-of-rain-2", name: "Risk of Rain 2", playtime: 7, … }
​
11: Object { slug: "tell-me-why", name: "Tell Me Why", playtime: 2, … }
​
12: Object { slug: "factorio", name: "Factorio", playtime: 17, … }
​
13: Object { slug: "ghostrunner", name: "Ghostrunner", playtime: 4, … }
​
14: Object { slug: "marvels-avengers", name: "Marvel’s Avengers", playtime: 14, … }
​
15: Object { slug: "mafia-iii-definitive-edition", name: "Mafia III: Definitive Edition", playtime: 0, … }
​
16: Object { slug: "guardians-of-the-galaxy", name: "Marvel's Guardians of the Galaxy", playtime: 8, … }
​
17: Object { slug: "need-for-speed-heat", name: "Need for Speed Heat", playtime: 3, … }
​
18: Object { slug: "marvels-spider-man-miles-morales", name: "Marvel's Spider-Man: Miles Morales", playtime: 0, … }
​
19: Object { slug: "streets-of-rage-4", name: "Streets of Rage 4", playtime: 4, … }
​
length: 20
​
<prototype>: Array []
Get.js:12:15

>Solution :

The problem is that axiosGet doesn’t actually return anything.

You can’t though get it to directly return the API data, since that is only retrieved asynchronously. See this question for lots of discussion as to how to get the response from asynchronous requests and use it in your code.

In your case probably the easiest solution is to have axiosGet return the promise that axios.get (and your subsequent .then calls from it) gives you, and then await that in your useEffect so that you can set the state in your component to it.

So I would make the following changes:

First add the return statement to axiosGet:

export function axiosGet() {
  return axios
    .get(
      `https://api.rawg.io/api/games?key=a6a08e14b07f41d09e846ec3c01e5db0&dates=2019-10-10,2022-03-01&page=2`
    )
    .then(res => {
      return res.data.results;
    })
    .then(arr => {
      return arr;
    })
    .catch(err => {
      console.error('oops! error: ' + err);
    });
}

and adjust the useEffect in your component as follows:

useEffect(async () => {
  const apiData = await axiosGet();
  setData(apiData);
}, []);
Add a comment

Leave a Reply

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use

Discover more from Dev solutions

Subscribe now to keep reading and get access to the full archive.

Continue reading