Проверяет понимание связи между параметрами фильтра, queryKey и поведением кэша в React Query, что важно для корректной инвалидации и рефетча данных.
В React Query (TanStack Query) queryKey — это уникальный идентификатор кэша. Если параметр фильтра не входит в ключ, библиотека считает все запросы с этим ключом одним и тем же кэшем, независимо от фактических аргументов внутри queryFn. Это приводит к тому, что данные для разных фильтров перезаписывают друг друга, а инвалидация затрагивает не тот набор данных, который ожидается.
Рассмотрим пример, где фильтр не включён в ключ:
function useItems(filter) {
return useQuery({
queryKey: ['items'], // фильтр отсутствует
queryFn: () => fetchItems(filter),
});
}
Если пользователь меняет filter, React Query не увидит изменения ключа и не выполнит новый запрос автоматически. Кэш останется прежним, а queryFn при следующем рефетче будет вызван с тем значением filter, которое замкнуто в текущем рендере компонента.
queryClient.invalidateQueries(['items'])) помечает кэш как устаревший и запускает рефетч. Рефетч вызовет queryFn из последнего активного наблюдателя (компонента), то есть с актуальным на тот момент значением filter, если компонент перерендерился с новым значением.Однако есть подвох: если компонент не перерендерился после смены фильтра (например, значение хранится в ref или внешнем сторе без подписки), queryFn продолжит использовать старое значение. Кроме того, при переключении фильтра туда-обратно вы получите данные из кэша, которые могут не соответствовать текущему фильтру, потому что ключ один и тот же.
Параметры, влияющие на результат запроса, должны быть частью queryKey:
useQuery({
queryKey: ['items', { filter }],
queryFn: () => fetchItems(filter),
});
Тогда каждый фильтр получит свой кэш, инвалидация будет точной, а рефетч всегда будет соответствовать актуальному значению фильтра.
Итог: если фильтр не входит в queryKey, актуальное значение попадёт в новый запрос только при условии, что компонент перерендерился и queryFn замкнул свежую переменную. Но кэш при этом будет общим и потенциально несогласованным, поэтому параметры фильтрации всегда следует включать в queryKey.
Frontend developer
Ментор по Frontend
Полное сопровождение до оффера — без дорогих курсов, с оплатой после трудоустройства
Записаться на консультацию