1. Overview
In this quick tutorial, we’re going to illustrate how to create a custom key generator with Spring Cache.
For an introduction to the above module, please refer to this article.
2. KeyGenerator
This is responsible for generating every key for each data item in the cache, which would be used to lookup the data item on retrieval.
The default implementation here is the SimpleKeyGenerator – which uses the method parameters provided to generate a key. This means that if we have two methods that use the same cache name and set of parameter types, then there’s a high probability that it will result in a collision.
It also implies that the cache data can be overwritten by another method.
3. Custom KeyGenerator
A KeyGeneratorneeds to implement just one single method:
Object generate(Object object, Method method, Object... params)
If it isn’t implemented or used correctly, it can lead to overwriting cache data.
Let’s look at the implementation:
public class CustomKeyGenerator implements KeyGenerator {
public Object generate(Object target, Method method, Object... params) {
return target.getClass().getSimpleName() + "_"
+ method.getName() + "_"
+ StringUtils.arrayToDelimitedString(params, "_");
}
}
After that, we have two possible ways of using it; the first is declaring a bean in the ApplicationConfig.
It’s important to remark that the class has to extend from CachingConfigurerSupport or implement CacheConfigurer:
@EnableCaching
@Configuration
public class ApplicationConfig extends CachingConfigurerSupport {
@Bean
public CacheManager cacheManager() {
SimpleCacheManager cacheManager = new SimpleCacheManager();
Cache booksCache = new ConcurrentMapCache("books");
cacheManager.setCaches(Arrays.asList(booksCache));
return cacheManager;
}
@Bean("customKeyGenerator")
public KeyGenerator keyGenerator() {
return new CustomKeyGenerator();
}
}
The second way is using it just for a particular method:
@Component
public class BookService {
@Cacheable(value = "books", keyGenerator = "customKeyGenerator")
public List<Book> getBooks() {
List<Book> books = new ArrayList<>();
books.add(new Book("The Counterfeiters", "André Gide"));
books.add(new Book("Peer Gynt and Hedda Gabler", "Henrik Ibsen"));
return books;
}
}
4. Conclusion
In this article, we’ve explored a way of implementing a custom Spring Cache’s KeyGenerator.
As always, the full source code of the examples is available over on GitHub.