I cannot understand, why do I keep getting "Objects are not valid as a React child (found: [object Promise]). If you meant to render a collection of children, use an array instead." error.
export async function LobbyPage(props) {
let fetched;
const [data, setState] = useState(null);
axios.get("http://127.0.0.1:8000/api_shop/")
.then(res => {
fetched = res.data;
setState(fetched);
})
return (
<>
<CatNav />
<main>
{data.map((current) => (
<div className="card">
<img src={current.photo} alt="Nothing"/>
<div className="card-body">
<h5 className="card-title">{current.name}</h5>
<p className="card-text">
{current.desc}
</p>
<a href="#" className="btn btn-primary"></a>
</div>
</div>
))}
</main>
</>
)}
It must fetch json data from my DRF backend and just render it via data.map state attribute. Can somebody help with it?
EDIT:
Data is being fetched as well, just something wrong with state and map()
2
Answers
This component isn’t necessarily producing the error. But the component that uses it is. That’s because this component doesn’t return JSX, it returns a
Promise
:async
functions always return aPromise
. The component shouldn’t beasync
:Aside from that… Don’t make AJAX calls directly in the component’s rendering. That will invoke the AJAX operation every time it renders. And if the operation updates state, that will trigger a re-render and an infinite render loop.
You can use
useEffect
with an empty dependency array to invoke the AJAX operation once when the component first loads:You also don’t need the
fetched
variable, it’s not doing anything meaningful.Additionally, if you’re mapping over
data
in the rendering then don’t initialize it tonull
, since you can’t call.map()
onnull
. Initialize it to an empty array:Since your function is
async
, the whole function will now return aPromise
. All you have to do is to use theawait
keyword to "wait" for the promise to get resolved, and then return the response. So the modified function would be: