1

In my below React component I am fetching more items using Apollo Client fetchMore function.

What is exactly the purpose of using React useCallback hook here? And is it good idea to use that in this case?

const Carousel = ({ data: blockData, metadata }: Props) => {

  const { data, fetchMore, networkStatus } = useQuery<
   GqlRes,
  >(GET_NODES, {
    variables: {
      offset
      limit
    },
    errorPolicy: 'all',
    notifyOnNetworkStatusChange: true,
    ssr: false,
  });


  const fetchNextPage = useCallback(() => {
    return fetchMore({
      variables: {
        offset: data?.getNodes.nodes.length,
      },
    });
  }, [data, fetchMore]);

  const items =
    data?.getNodes.nodes
      .map((node) => {
        return {
          id: node.id,
          title: node.title,
        };
      }) || [];

  return (
    <Carousel
      items={items}
        onEnd={() => {
         if (data?.getNodes.pager?.hasNextPage) {
           fetchNextPage();
         }
      }}
    />
  )
};

export default Carousel;
meez
  • 3,783
  • 5
  • 37
  • 91
  • The useCallback hook is used when you have a component in which the child is rerendering again and again without need. Pass an inline callback and an array of dependencies. useCallback will return a memoized version of the callback that only changes if one of the dependencies has changed. – iLuvLogix Dec 17 '21 at 10:16
  • 2
    There is no point in using `useCallback` here because you are passing a new function to `Carousel` on every render anyways. `useCallback` is useful if you are passing a function to a child component and you only want to pass a new function object when any of the data that the function uses changes. This allows the child component to do optimizations. – Felix Kling Dec 17 '21 at 10:17
  • @Felix Kling and inside `Carousel` there is another `` where `onEnd` is passed through. Does that make any difference? Ans sorry can you give a clear use case when to use it? – meez Dec 17 '21 at 10:28

1 Answers1

1

IMHO:

  1. if your inner 'Carousel' component is cached (memoized by React.memo or extends PureComponent) it's could to do not provide new properties on each parent (outer 'Carousel') re-render (just to mention - on each re-render you not memoized objects and function will be created again as new instances and will be passed further as new properties and cause new re-renders of children) it's to use useCallback
  2. even more, I would like to use useMemo for your 'items' data variable to avoid that logic re-handling. Yes for it's logically will be new on each update of 'data' or other properties from a parent, BUT when someone will extend the logic of the component and it will be re-rendered, then data handling could be not changed and that logic will be redundant - you safe time of component logic handling
kosiakMD
  • 923
  • 7
  • 22