React - useEffect hook
In this article, we would like to show you how to use React useEffect
hook.
React useEffect
hook is equivalent to the class components lifecycle methods:
componentDidMount
,componentDidUpdate
,componentWillUnmount
.
The function inside useEffect
runs when the component is first rendered and on every array of dependencies update (which is the second, optional argument).
Below examples present:
- how to import
useEffect
hook, - solution with one argument only (arrow function),
- solution with two arguments:
- array of dependencies that is monitored for changes,
- empty array of dependencies.
- how to mix
useEffect
The first thing you need to do is import useEffect
hook the following way:
xxxxxxxxxx
import React, { useEffect } from 'react';
The arrow function inside useEffect
is always executed after:
- the rendering cycle,
- props, state or context change,
- the parent component is rendered.
Runnable example:
xxxxxxxxxx
// Note: Uncomment import lines while working with JSX Compiler.
// import React, { useEffect } from 'react';
// import ReactDOM from 'react-dom';
const App = () => {
const [counter, setCounter] = React.useState(0);
React.useEffect(() => {
console.log(`useEffect: counter: ${counter}`);
});
return (
<div>
<p>
<b>Counter: </b>{counter}
</p>
<button onClick={() => setCounter(counter + 1)}>Change counter</button>
</div>
);
};
const root = document.querySelector('#root');
ReactDOM.render(<App />, root );
The function inside useEffect
is executed in two cases:
- after the component is mounted,
- after any change of the monitored array of dependencies (in our case on the
user
change).
Note:
In one
useEffect
array of dependencies we can put many variables.
Runnable example:
xxxxxxxxxx
// Note: Uncomment import lines while working with JSX Compiler.
// import React, { useEffect } from 'react';
// import ReactDOM from 'react-dom';
const App = () => {
const [user, setUser] = React.useState('Tom');
const [counter, setCounter] = React.useState(0);
React.useEffect(() => {
console.log(`useEffect: Hello ${user}!`);
}, [user]);
return (
<div>
<p>
<b>User: </b> {user},<b>Counter: </b> {counter}
</p>
<button onClick={() => setCounter(counter + 1)}>Change counter</button>
<button onClick={() => setUser(user === 'Tom' ? 'Kate' : 'Tom')}>
Change user
</button>
</div>
);
};
const root = document.querySelector('#root');
ReactDOM.render(<App />, root );
In this example, we create useEffect
hook with an empty array of dependencies. That tells React to execute the effect only once (at component mount).
Runnable example:
xxxxxxxxxx
// Note: Uncomment import lines while working with JSX Compiler.
// import React, { useEffect } from 'react';
// import ReactDOM from 'react-dom';
const App = () => {
const [counter, setCounter] = React.useState(0);
React.useEffect(() => {
console.log('Setting counter...');
}, []);
return (
<div>
<p>
<b>Counter: </b> {counter}
</p>
<button onClick={() => setCounter(counter + 1)}>Increment</button>
</div>
);
};
const root = document.querySelector('#root');
ReactDOM.render(<App />, root );
We can also use many useEffect
hooks and mix them as we want.
Runnable example:
xxxxxxxxxx
// Note: Uncomment import lines while working with JSX Compiler.
// import React, { useEffect } from 'react';
// import ReactDOM from 'react-dom';
const App = () => {
const [counter1, setCounter1] = React.useState(0);
const [counter2, setCounter2] = React.useState(0);
React.useEffect(() => {
console.log('Setting counters...');
}, []);
React.useEffect(() => {
console.log(`Counter 1 value is now ${counter1}`);
}, [counter1]);
React.useEffect(() => {
console.log(`Counter 2 value is now ${counter2}`);
}, [counter2]);
return (
<div>
<p>
<b>Counter 1: </b> {counter1}, <b>Counter 2: </b> {counter2}
</p>
<button onClick={() => setCounter1(counter1 + 1)}>Increment 1</button>
<button onClick={() => setCounter2(counter2 + 1)}>Increment 2</button>
</div>
);
};
const root = document.querySelector('#root');
ReactDOM.render(<App />, root );