Skip to content

Commit 3a95205

Browse files
committed
What happens when useEffect contains a async method with multiple setState?
1 parent e53c81e commit 3a95205

File tree

1 file changed

+19
-2
lines changed

1 file changed

+19
-2
lines changed

src/Todo/TodoList.js

+19-2
Original file line numberDiff line numberDiff line change
@@ -18,18 +18,35 @@ const fetchTodosFromApi = async () => {
1818
const TodoList = () => {
1919
const [todos, setTodoList] = useState([]);
2020
useEffect(function callApi() {
21+
//1. Imagine that we are calling an api to get todos
2122
fetchTodosFromApi().then(list => setTodoList(list));
2223
}, []);
2324

25+
//2. And we have a state for 2 counter
2426
const [ongoingCount, setOngoingCount] = useState(0);
2527
const [doneCount, setDoneCount] = useState(0);
2628

29+
// 3. But what if the setter are in a async method ?
2730
useEffect(function refreshCounters() {
28-
setDoneCount(todos.filter(t => t.done).length);
29-
setOngoingCount(todos.filter(t => !t.done).length);
31+
(async () => {
32+
new Promise(resolve => setTimeout(() => {
33+
setDoneCount(todos.filter(t => t.done).length);
34+
setOngoingCount(todos.filter(t => !t.done).length);
35+
resolve();
36+
}, 1));
37+
})();
3038
}, [todos]);
3139

40+
//4. See how many render ?
3241
console.log('render with', {total: todos.length, ongoingCount, doneCount});
42+
// When I set one of the todos as "done", it re-renders 3 times
43+
// render with { total: 5, ongoingCount: 5, doneCount: 0 } ==> when setTodoList is called
44+
// render with { total: 5, ongoingCount: 5, doneCount: 1 } ==> when setDoneCount is called
45+
// render with { total: 5, ongoingCount: 4, doneCount: 1 } ==> when setOngoingCount is called
46+
47+
//2 conclusions:
48+
// - We still have too many render!
49+
// - Once you are outside the "useEffect" thread, you have as many render as "setter"
3350

3451
const addEmptyTodo = () => setTodoList([createTodo('Relax! Edition will come...', false), ...todos]);
3552
const markAsDone = (index) => setTodoList([...todos.slice(0, index), {

0 commit comments

Comments
 (0)