get and useRecoilState do very similar thing.
Not sure how realistic it would be to useRecoilState inside selector
const filteredTodoListState = selector({
key: 'filteredTodoListState',
get: ({get}) => {
// const filter = useRecoilState(todoListFilterState)
const filter = get(todoListFilterState);
return filter;
}
})
Hi @alexandrzavalii
The Rules Of Hooks say that a hook can only be called from either React function components or as part of a custom hook. This means they can't be called inside a function like a Recoil selector.
Hi @acutmore , thanks for reply.
I know about this rule, but get function looks to me like a body of a custom hook, it will rerender if the value changes.
Agreed @alexandrzavalii they do look like the body of a custom hook.
The difference is when the function gets called. Hooks need to be called when React is 'rendering' a Function component. This is how React knows which part of the component tree 'owns' that hook.
The problem with putting the hook inside the selector is that Recoil (EDIT: an async selector ) may call the get function at a different point in time, after the component has rendered. This means that the hook calls inside the implementation of useRecoilState like useCallback will throw an exception.
@acutmore Cool thanks! I thought it has the same behavior as hooks, and “get” is always immediately called on render.
Thanks for explanation!
@alexandrzavalii You are correct, I was not very clear. The get function passed to the selector is called during render. Though that function could be async, so the internal get could be after the render.
const delayNumberState = selector({
key: "delayNumberState",
get: async ({ get }) => {
const delay = get(delayState);
await new Promise(resolve => setTimeout(resolve, delay));
const number = get(numberState); // get called outside of React render
return number;
}
});
Even if calling the hook was safe in practice the rules-of-hooks eslint rule would not know that and would display an error/warning.
oh yeah, I definitely forgot about the async use-case. And also get does not have to be at the top level.
yeah there is no way you could use hooks in that case.