Persist Apollo Cache to local storage

Hi,
I was wondering if it is possible to use apollo-cache-persist with RedwoodApolloProvider.

This would be the necessary code roughly:

import { InMemoryCache } from '@apollo/client/core';
import { persistCache, LocalStorageWrapper } from 'apollo3-cache-persist';

const cache = new InMemoryCache({...});

// await before instantiating ApolloClient, else queries might run before the cache is persisted
await persistCache({
  cache,
  storage: new LocalStorageWrapper(window.localStorage),
});

// Continue setting up Apollo as usual.

const client = new ApolloClient({
  cache,
  ...
});

Unfortunately the persistCache needs to wrap InMemoryCache before the client is created. Otherwise queries will run before cache is persisted.
Therefore useApolloClient won´t suit us.

I could pass a custom cache to RedwoodApolloClient, but too be honest I do not dare to do this, since there seems to be quite some custom logic in the normal client with fragments, suspense and stuff. (redwood/packages/web/src/apollo/index.tsx at e94dbf5ff52bc33b364e183bba47985f683c915f · redwoodjs/redwood · GitHub)

Any idea how I could accomplish this easily?

1 Like

Have you tried the method shown to customize the cache config here: GraphQL | RedwoodJS Docs ?

Ah… going to have a look at it! Hope it will work.

Unfortunately cacheConfig goes into InMemoryCache (redwood/packages/web/src/apollo/index.tsx at e26395f46e0bd131890680b7a6b6e72b6330fa97 · redwoodjs/redwood · GitHub)
And I would need the output of InMemoryCache to wrap it with persiststCache.

It is a bit a hen and egg case. Unfortunately the linked file also says InMemoryCache should be used within RedwoodApolloProvider.

Now we could consider another prop for the Provider, like beforeAssignCache: (cache: InMemoryCache): InMemoryCache => void. But this one would need to be async. Because the data from local storage is loaded async.
Alternatively we could add another RedwoodApolloPersistProvider. Would this make sense?

If we find a preferred way, I could go forward and try to implement it.

1 Like

Or perhaps make a PR to add an option to persist the cache in redwood/packages/web/src/apollo/index.tsx at e1e3f35e657743eac545e7592f1a6cb774f27b05 · redwoodjs/redwood · GitHub

1 Like

Hi @dennemark I completely forgot about this idea with v7.

Somehow the docs for the new useCache hook didn’t make it in the release and I am including them now.

I think there is a way:

First: yarn workspace web add apollo3-cache-persist

Then … somewhere :slight_smile: this is a page, but might be better in in App.tsx maybe?

import { persistCache, LocalStorageWrapper } from 'apollo3-cache-persist'

import { useCache } from '@redwoodjs/web/apollo'

const CachePage = async () => {
  const { cache } = useCache()

  await persistCache({
    cache,
    storage: new LocalStorageWrapper(window.localStorage),
  })

//.. do stuff :slight_smile: 

I then looked in Web Dev Storage settings and saw the key and my cached data.

And as I used my app, and navigated to the pages that made additional queries,I did see local storage being updated with new info.

Could you try that and let me know if it works?

If so, I’ll definitely include it in these updated caching docs,

1 Like

i am going to try as soon as i am on v7!
thanks a lot! also did not find time yet to figure out solution…