0

I have a Caffeine AsyncLoadingCache created with a refreshAfterWrite configured. For a given key, if a value is already loaded into the cache and there is an error during refresh, the key/value gets removed. Instead of this, I would like to retain the old value and update the expiration timestamp so it doesn't immediately get refreshed again. Is there a way to configure this behavior?

user3380364
  • 65
  • 1
  • 5

1 Answers1

1

You can implement either CacheLoader.reload(key, oldValue) or AsyncCacheLoader.asyncReload(key, oldValue). When an error occurs it shouldn't remove the old value but can be triggered again on the next call. If the result resolves to null then it should be removed. Since the old value is provided, if returned then it would reset the timestamps as desired.

Ben Manes
  • 9,178
  • 3
  • 35
  • 39
  • Thanks for the quick response Ben! One thing I neglected to mention is that we are using cache.get(key, mappingFunction) because our loading process needs some data that isn't available during the cache construction. I don't see a flavor of that which provides access to the oldValue. Did I miss it? – user3380364 Jan 09 '22 at 15:01
  • @user3380364 Unfortunately it would make the api very messy to provide it explicitly. Instead consider fetching that data on-demand, e.g. through a supplier. In [Guice](https://xvik.github.io/dropwizard-guicey/5.0.0/guide/guice/scopes) or [Spring](https://www.logicbig.com/tutorials/spring-framework/spring-core/using-jsr-330-provider.html) this would be a scoped provider, e.g. to query the user's id from a request-scoped supplier. In non-DI code this is often done via a thread-local. – Ben Manes Jan 09 '22 at 17:54
  • fwiw, you can also use asMap().compute if you need the old value for an explicit atomic change. That has nothing to do with refreshing though. – Ben Manes Jan 09 '22 at 19:38
  • Thanks again Ben for the followup. One last question - is there any way to get the current value for a key without the cache checking the timestamps and possibly initiating a refresh? – user3380364 Jan 10 '22 at 15:46
  • @user3380364 Take a look at `cache.policy().getIfPresentQuietly(key)` – Ben Manes Jan 10 '22 at 16:36