I encountered the following code in a project, where a custom string is created as a dependency for a useEffect hook:
Defined refreshKey
const refreshKey = [
pageIndex,
filterActive,
viewSetting,
itemType,
sortingValue,
userLanguage,
sortOrder,
window.location.href,
searchQuery
].join("_")
The usage then:
useEffect(() => {
// Fetch or update data when any of the dependencies change
fetchData();
// The effect depends on the custom `refreshKey`
}, [refreshKey]);
My concerns are:
-
Is this the correct way to use a custom string as a dependency in useEffect?
-
Would it be safer or more reliable to list each state variable individually in the dependency array instead of combining them into a single string?
-
Could this cause unexpected behaviour of the component?
2
Answers
It’s not recommended to do so.
refreshKey
will be new on every render, it means theuseEffect
runs on every render, which is somtimes unnecessary.And yes, to list each state variable individually in the dependency array is always a better choice.
It’s also a correct usage.
Regarding whether you should do that or not:
It matters if ‘refreshKey’ will be passed in the multiple hooks. (It’s more about performance, but in my opinion, I don’t see any reason to do it because it would provide only a small advantage in cases where the number of hooks including this is not very large. )
Dependencies are checked this way, so the for loop will be completed when all items are checked. Also, for every item in the dependencies, Object.is will be called.
We can also consider it as following the ‘DRY’ principle, but in my opinion, in this case, we don’t need to use
join
. We can create an array and pass it as a second argument instead.