Joniverse
Joniverse

Reputation: 45

useEffect with only one dependency / React Hook useEffect has a missing dependency: 'props'

I want to be able to reuse my input form as an edit form, so in the form component I check if there is an id in the url with { useParams }, and if there is, set state of the input fields with the data i get from a function getContact that is passed down with props.

In UseEffect I want to track id but not props, so I just put [id] as a dependency at the end of useEffect. If I add [id, props] I'm not able to set the state of the input fields because it instantly sets it back to the values i get back from getContact() (since there IS an id if I'm editing).

I'm very new to React so I just wonder if there is a better way to do this, or if I should just put // eslint-disable-next-line in my code and get on with my life :-)

    const Form = (props) => {
      const { id } = useParams();
    
      const [input, setInput] = useState({});
    
      useEffect(() => {
        setInput(id ? props.getContact(id) : {});
      }, [id]);
    
      const handleChange = (event) => {
        let value = event.target.value;
        let name = event.target.name;
    
        setInput((prev) => {
          return { ...prev, [name]: value };
        });
      };

... A few more functions and then a return that spits out som JSX

Upvotes: 0

Views: 587

Answers (1)

Domino987
Domino987

Reputation: 8774

Anything that is used within the useEffect should be added to the dependency array. Why not extract the id you want to set instead like this?

const contectId = id ? props.getContact(id) : {};
useEffect(() => {
    setInput(contectId);
  }, [contectId]);

This only works if you store the {} somewhere where it does not change on render: Either like this:

const emptyArray = React.useMemo(() => {}, [])
const contectId = id ? props.getContact(id) : emptyArray;
useEffect(() => {
    setInput(contectId);
  }, [contectId]);

or

const emtyArray = {};
const Form = (props) => {
  const { id } = useParams();

  const [input, setInput] = useState({});

 const contectId = id ? props.getContact(id) : emtyArray;
  useEffect(() => {
    setInput(contectId);
  }, [contectId]);

  const handleChange = (event) => {
    let value = event.target.value;
    let name = event.target.name;

    setInput((prev) => {
      return { ...prev, [name]: value };
    });
    console.log(input);
   };

Upvotes: 1

Related Questions