1. Overview
1.概述
In this short tutorial, we’ll look at how to configure Redis as the data store for Spring Boot cache.
在这个简短的教程中,我们将了解如何配置Redis作为Spring Boot缓存的数据存储。
2. Dependencies
2.依赖性
To get started, let’s add the spring-boot-starter-cache and spring-boot-starter-data-redis artifacts:
为了开始,让我们添加spring-boot-starter-cache和spring-boot-starter-data-redis构件。
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-cache</artifactId>
<version>2.4.3</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-redis</artifactId>
<version>2.4.3</version>
</dependency>
These add caching support and bring in all the required dependencies.
这些都增加了缓存支持,并带来了所有需要的依赖。
3. Configuration
3.配置
By adding the above dependencies and the @EnableCaching annotation, Spring Boot will auto-configure a RedisCacheManager with default cache configuration. However, we can modify this configuration prior to cache manager initialization in a couple of useful ways.
通过添加上述依赖关系和@EnableCaching注解,Spring Boot将自动配置一个具有默认缓存配置的RedisCacheManager。不过,我们可以在缓存管理器初始化之前,以几种有用的方式修改这个配置。
First, let’s create a RedisCacheConfiguration bean:
首先,让我们创建一个RedisCacheConfiguration bean。
@Bean
public RedisCacheConfiguration cacheConfiguration() {
return RedisCacheConfiguration.defaultCacheConfig()
.entryTtl(Duration.ofMinutes(60))
.disableCachingNullValues()
.serializeValuesWith(SerializationPair.fromSerializer(new GenericJackson2JsonRedisSerializer()));
}
This gives us more control over the default configuration. For example, we can set the desired time-to-live (TTL) values and customize the default serialization strategy for in-flight cache creation.
这给了我们对默认配置的更多控制。例如,我们可以设置所需的生存时间(TTL)值,并定制默认的序列化策略来创建飞行中的缓冲区。
In order to have full control over the caching setup, let’s register our own RedisCacheManagerBuilderCustomizer bean:
为了完全控制缓存设置,让我们注册我们自己的RedisCacheManagerBuilderCustomizerBean。
@Bean
public RedisCacheManagerBuilderCustomizer redisCacheManagerBuilderCustomizer() {
return (builder) -> builder
.withCacheConfiguration("itemCache",
RedisCacheConfiguration.defaultCacheConfig().entryTtl(Duration.ofMinutes(10)))
.withCacheConfiguration("customerCache",
RedisCacheConfiguration.defaultCacheConfig().entryTtl(Duration.ofMinutes(5)));
}
Here we’ve used RedisCacheManagerBuilder along with RedisCacheConfiguration to configure TTL values of 10 and 5 minutes for itemCache and customerCache, respectively. This helps to further fine-tune the caching behavior on a per-cache basis including null values, key prefixes and binary serialization.
这里我们使用RedisCacheManagerBuilder和RedisCacheConfiguration分别为itemCache和customerCache配置了10分钟和5分钟的TTL值。这有助于进一步在每个缓存的基础上微调缓存行为,包括null值、键前缀和二进制序列化。
It’s worth mentioning that the default connection details for the Redis instance are localhost:6379. Redis configuration can be used to further tweak the low-level connection details along with the host and port.
值得一提的是,Redis实例的默认连接细节是localhost:6379。Redis 配置可用于进一步调整低级别连接细节以及主机和端口。
4. Example
4.例子
In our example, we have an ItemService component that retrieves item information from the database. In effect, this represents a potentially costly operation and a good candidate for caching.
在我们的例子中,我们有一个ItemService组件,从数据库检索项目信息。实际上,这代表了一个潜在的昂贵的操作,是一个很好的缓存候选者。
First, let’s create the integration test for this component using an embedded Redis server:
首先,让我们使用嵌入式Redis服务器为该组件创建集成测试。
@Import({ CacheConfig.class, ItemService.class})
@ExtendWith(SpringExtension.class)
@EnableCaching
@ImportAutoConfiguration(classes = {
CacheAutoConfiguration.class,
RedisAutoConfiguration.class
})
class ItemServiceCachingIntegrationTest {
@MockBean
private ItemRepository mockItemRepository;
@Autowired
private ItemService itemService;
@Autowired
private CacheManager cacheManager;
@Test
void givenRedisCaching_whenFindItemById_thenItemReturnedFromCache() {
Item anItem = new Item(AN_ID, A_DESCRIPTION);
given(mockItemRepository.findById(AN_ID))
.willReturn(Optional.of(anItem));
Item itemCacheMiss = itemService.getItemForId(AN_ID);
Item itemCacheHit = itemService.getItemForId(AN_ID);
assertThat(itemCacheMiss).isEqualTo(anItem);
assertThat(itemCacheHit).isEqualTo(anItem);
verify(mockItemRepository, times(1)).findById(AN_ID);
assertThat(itemFromCache()).isEqualTo(anItem);
}
}
Here we create a test slice for the caching behavior and invoke the getItemForId twice. The first invocation should obtain the item from the repository, but the second invocation should return the item from the cache without invoking the repository.
这里我们为缓存行为创建一个测试片,并调用getItemForId两次。第一次调用应该从存储库中获取项目,但第二次调用应该从缓存中返回项目而不调用存储库。
Finally, let’s enable the caching behavior using Spring’s @Cacheable annotation:
最后,让我们使用Spring的@Cacheable注解来启用缓存行为。
@Cacheable(value = "itemCache")
public Item getItemForId(String id) {
return itemRepository.findById(id)
.orElseThrow(RuntimeException::new);
}
This applies the caching logic while relying on the Redis cache infrastructure that we’ve configured earlier. Further details about controlling properties and behaviors of the Spring caching abstraction, including data update and eviction, are covered in our Guide to Caching in Spring.
这将应用缓存逻辑,同时依靠我们之前配置的Redis缓存基础设施。关于控制 Spring 缓存抽象的属性和行为(包括数据更新和驱逐)的更多细节,将在我们的Guide to Caching in Spring中介绍。
5. Conclusion
5.总结
In this article, we’ve seen how to use Redis for Spring caching.
在这篇文章中,我们已经看到了如何使用Redis进行Spring缓存。
We first described how to auto-configure Redis caching with minimal configuration. Then we looked at how to further customize the caching behavior by registering configuration beans.
我们首先描述了如何用最小的配置来自动配置Redis缓存。然后我们研究了如何通过注册配置Bean来进一步定制缓存行为。
Finally, we created a sample use case to demonstrate this caching in practice.
最后,我们创建了一个用例,以证明这种缓存在实践中的作用。
As always, the full source code is available over on GitHub.
一如既往,完整的源代码可在GitHub上获得,。