I wanna render a table after fetching data from an API, I use the Context API and a custom hook to update the context. I know that my hook is working because of the second useEffect that logs the data. I'm aware that state updates in React are asynchronous, but I thought a change in the context would trigger a rerender.
import React, { useEffect, useContext } from "react";
import { titleCase } from "title-case";
import dataContext from "../../context/dataContext";
const fetchUsers = async (url:string) => {
const response = await fetch(url);
return response.json();
};
const Table = () => {
const {data, setData } = useContext(dataContext);
useEffect(() => {
fetchUsers(`https://randomuser.me/api/?results=50`).then(
(res) => {setData([...data, res.results]) ;
}
)
}, [])
useEffect(() => {
console.log(data)
}, [data])
return (
<table>
<thead>
<tr>
<th>
Name
</th>
<th>
Gender
</th>
<th>
Birth
</th>
<th>
Actions
</th>
</tr>
</thead>
<tbody>
{data.length >0 && data.map((user: Record<string, any>, index: number) => {
const dob = new Date(user.dob.date);
return (
<tr>
<td>
{`${titleCase(user.name.first)} ${titleCase(user.name.last)}`}
</td>
<td>
{titleCase(user.gender)}
</td>
<td>
{dob.toLocaleDateString()}
</td>
<td>
<button>View</button>
</td>
</tr>
);
})}
</tbody>
</table>
);
};
export default Table;
There are multiple issues with the code that you have posted.
res.results
inside setData. If you don't do it, the array of user will be stored as a single object instead of storing all the multiple user objects. setData([...data, ...res.results)
login.uuid
field for each user as the key. <tr key={user.login.uuid}>
data
as a dependency for the useEffect
hook.I made a simple demo, which follows the above points. In the demo, I'm not using context. I'm fetching 2 new users every 10 seconds and then updating a table with their emails. link for demo .
I know this is a late post but I have spent some time looking into this and thought this might help you. Hopefully you have solved your issue by now.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.