loading...

State and Variable in React Hooks

ghost profile image Ghost ・1 min read

I am pretty new to react-hooks and I have yet to discover its real super powers. I want to ask if I am breaking anything if I do the sample code below.


let somevariable= [];

const SomeComponent = () => {
  const [state, setState] = useState({});

  useEffect(()=>{
   fetch('http://insert-api/state')
      .then(response => response.json())
      .then(data => setState({ data }));
  },[])


  useEffect(()=>{
   //update `somevariable` whenever the state changes
   somevariable = state.something
  },[state])


 const clickMe = () => {
   console.log(somevariable)
   //do something to somevariable
 }

  return (
    <button onClick={clickMe}>Click Me </button>
  )
}

Instead of putting somevariablein the state I put it outside to make it kind of global. I did this because when I put somevariable in its own state and set its value in the useEffect it results to endless loop but this one does not, so this is like my workaround. A lot of my functions rely on somevariable that's why it's important for me to know if this approach is alright or not.

PS. I don't know if it's alright to ask this here so please tell me if it's not and I will take it down. Thanks.

Posted on by:

ghost profile

Ghost

@ghost

I'm the ghost of Developers Past...

Discussion

markdown guide
 

When you put the somevariable outside of React's control, changing the value of somevariable would not trigger components depending on that value to re-render.

e.g.)

You can fork and try it yourself

Edit Doesn't re-render with global variable

let somevariable;

const Child = ({ somevariable }) => {
  useEffect(() => {
    console.log(`Child rendering with somevariable=>`, somevariable);
  });

  return <h1>{somevariable}</h1>;
};

async function fetchData() {
  return "some data";
}

const SomeComponent = () => {
  const [state, setState] = useState({});

  useEffect(() => {
    fetchData().then(data => setState({ data }));
  }, []);

  useEffect(() => {
    //update `somevariable` whenever the state changes
    somevariable = state.data;
  }, [state]);

  const clickMe = () => {
    console.log(somevariable, state);
    //do something to somevariable
  };

  return (
    <>
      <button onClick={clickMe}>Click Me </button>
      <Child somevariable={somevariable} />
    </>
  );
};

You can see that Child that depends on the change of somevariable does NOT render, as somevariable is not a state tracked by React.

The demo below doesn't render the Child component (with <h1>{somevariable}</h1> element)

does not rerender

Can you post a runnable code (possibly forking the sandbox) that causes the infinite loop?