0

I'm making a simple API call from a react component to my Mongo database, which returns a list of items. Inside useEffect, I'm making a GET request to return an arrays of reviews. When I log the resulting to the data, I'm seeing the correct information:

useEffect(() => {
    axios.get('http://localhost:3000/all-reviews')
  .then((allReviews) => {
    console.log(allReviews)
  })
  })

However, when I try to set state inside the useEffect method, my program breaks. I know that setState is async, so how do I configure it so it works inside useEffect?

Here's the entire component used to control API calls:

App.jsx

import React, {useState, useEffect} from 'react'
import axios from 'axios'

const App = () => {
  const [reviews, setReviews] = useState([])

  useEffect(() => {
    axios.get('http://localhost:3000/all-reviews')
  .then((allReviews) => {
    setReviews(allReviews)
  })
  })

  return (
    <>
    <h1>React development has begun!</h1>
    {
      reviews.map((item, index) => {
        <h1>item.title</h1>
      })
    }
    </>
  )
}

export default App

Not that relevant, but here's the route this component invokes:

server.get('/all-reviews', (req,res) => {
    Review.find()
    .then((result) => {
        res.send(result)
    })
    .catch(err => {
        console.log(err)
    })
})
Josh Simon
  • 159
  • 1
  • 10
  • 27

1 Answers1

-1

I think firstly, your useEffect doesn't have a depedency, which mean it will run every time, it needs an empty array at least, like the one below.

useEffect(() => {

  },[])

And when you are expecting a JSON data in React, you have to check if the data is available first before populating it, if not react will freak out.

You could do this.

  return (
    <>
    <h1>React development has begun!</h1>
    {
      reviews?.map((item, index) => {
        <h1>item.title</h1>
      })
    }
    </>
  )
}

or this

  return (
    <>
    <h1>React development has begun!</h1>
    {
      reviews && (reviews.map((item, index) => {
        <h1>item.title</h1>
      }))
    }
    </>
  )
}

and thirdly you are not returning anything in your dom. it should be this way.

  reviews && (reviews.map((item, index) => 
        <h1>item.title</h1>
      ))

or if you wanna do it your way, you could just do this.

  reviews && (reviews.map((item, index) => {
return (
        <h1>item.title</h1>
)
      }))