What does it mean to 'move this variable directly inside useEffect' in this error message?
Asked Answered
C

3

55

I am attempting to pass an object through props to a child component. The value is set in the useEffect hook and lost when passed to my child component.

I have tried setting the value of the object outside the useEffect hook in a separate function but the value is still lost.

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

function SetValue(props){

    let users = {};

    useEffect(() => {
          users = { user: 'bob' };
    })        

    return <NewComponent users={users} />
}

export default SetValue;

I expected props.users to be { user: 'bob' } and not an empty object {}.

The error message is:

"Assignments to the 'users' variable from inside React Hook useEffect will be lost after each render. To preserve the value over time, store it in a useRef Hook and keep the mutable value in the '.current' property. Otherwise, you can move this variable directly inside useEffect react-hooks/exhaustive-deps"

Curtice answered 15/5, 2019 at 18:53 Comment(0)
D
70

About useEffect hook:

By using this Hook, you tell React that your component needs to do something after render. React will remember the function you passed (we’ll refer to it as our “effect”), and call it later after performing the DOM updates. more

This means that function inside useEffect will be called after rendering of the component. That's why you have an empty object.

About the error. You have it because React doesn't remember your users variable - it will be recreated on each render of SetValue component. It will be better to use useState hook to set value in useEffect and remember it on the next render.

And one more note. Don't forget about passing the second argument in useEffect with an array of dependencies. Now your hook will be called after each render of SetValue component.

Here's how to use useState hook:

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

function SetValue(props){

    const [users, setUsers] = useState({});

    useEffect(() => {
          setUsers({ user: 'bob' });
    }, [
       //here you could pass dependencies, or leave it empty to call this effect only on first render
    ]);        

    return <NewComponent users={users} />
}

export default SetValue;
Dwanadwane answered 15/5, 2019 at 19:27 Comment(0)
Q
6

This warning --"Assignments to the 'users' variable from inside React Hook useEffect will be lost after each render-- is the reason why state concept exists in React. React component doesn't preserve the value of normal javascript variables throughout successive re-renders(component lifecycle).Thats where react state helps so that changes to the state can be reflected in DOM if component re-renders.

Quincy answered 4/6, 2019 at 13:5 Comment(0)
B
0

A simple solution that I found to this problem was to declare the variable used in useEffect hook outside the function declaration i.e.,

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

let users = {};  // variable declaration outside of the component declaration

function SetValue(props) {
    useEffect(() => {
          users = { user: 'bob' };
    })        

    return <NewComponent users={users} />
}

export default SetValue;

Try it, since it solved the problem for me.

Butterbur answered 23/11, 2023 at 17:40 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.