Skip to content
New issue

Have a question about this project? # for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “#”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? # to your account

invalidateTags only seems to work with a setTimeout #4706

Open
wmonecke-oss opened this issue Nov 12, 2024 · 3 comments
Open

invalidateTags only seems to work with a setTimeout #4706

wmonecke-oss opened this issue Nov 12, 2024 · 3 comments

Comments

@wmonecke-oss
Copy link

wmonecke-oss commented Nov 12, 2024

Hey there!

When I get a web socket update I want to refetch data.

This setup is working (notice setTimeout):

  useEffect(() => {
    if (!enabled) {
      return;
    }

    prettyLog('FETCHING WEATHER');

    dispatch(Api.util.invalidateTags([ApiCacheTags.FetchWeather]));

    // wait for cache invalidation
    setTimeout(() => {
      dispatch(syncWeatherForCurrentLocation());
    }, 1000);
  }, [
    dispatch,
    enabled,
    realTimeChanges.update,
  ]);

This is NOT working:

  useEffect(() => {
    if (!enabled) {
      return;
    }

    prettyLog('FETCHING ALERTS FOR LOCATIONS');

    dispatch(Api.util.invalidateTags([ApiCacheTags.FetchWeather]));

    dispatch(syncWeatherForCurrentLocation());
  }, [
    dispatch,
    enabled,
    realTimeChanges.update,
  ]);

I thought invalidateTags was a synchronous call. How would I await it here? Or what else am I missing?

@markerikson
Copy link
Collaborator

What are you trying to accomplish? Are you trying to wait for all the invalidated cache entry requests to complete?

invalidateTags itself is a synchronous action that tells the RTKQ middleware to start the fetching process. It doesn't have any knowledge of what requests got kicked off or how they completed.

If you need to know when the requests are done, you'd probably need:

@wmonecke-oss
Copy link
Author

wmonecke-oss commented Nov 13, 2024

@markerikson ah i see thanks!

this is what i was trying to accomplish:

  1. invalidate cache
  2. next time i call that endpoint it wont return cached data

so here is my problem, (see first message):

inside dispatch(syncWeatherForCurrentLocation());

i have an api call that returns cached data:

   // fetch weather for current position
    const promiseromise = thunkApi
      .dispatch(
        Weather.endpoints.fetchWeatherByCoordinate.initiate(
          currentLocation.position.coordinate,
        ),
      )
      .unwrap();

even when before that i called dispatch(Api.util.invalidateTags([ApiCacheTags.FetchWeather]));

After the invalidateTags call, I expected all cached data would have been invalidated and the next API call would have been fresh data.

EDIT:

I followed your recommendation but it still did not work:

const fetchAlerts = async () => {
      prettyLog('Fetching alerts for locations');

      dispatch(Weather.util.invalidateTags([ApiCacheTags.FetchWeather]));
      
      // only works w this delay, if i remove this delay then the call in 
      // syncWeatherForCurrentLocation returns cached data
      await new Promise(resolve => setTimeout(resolve, 1000)); 

      // this return empty array always, with or without the delay above
      const queries = await Promise.all(
        dispatch(Weather.util.getRunningQueriesThunk()),
      );

      prettyLog('Cache invalidation complete', { queries });


        dispatch(syncWeatherForCurrentLocation()),
    };

@markerikson
Copy link
Collaborator

Invalidation kicks off a new request, but it doesn't remove the existing cache entry.

# for free to join this conversation on GitHub. Already have an account? # to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants