Rek*_*kha 22 java spring caching spring-boot spring-cache
我希望在我的Web应用程序中配置多个Spring缓存管理器,并且我可以在项目的不同位置使用不同的缓存管理器.有没有办法做到这一点.
Ste*_*oll 35
有几种方法可以做到这一点,正确的答案取决于您对缓存的使用.
如果你使用CacheManager A 90%的用例而B使用10%我建议CacheManager
为A 创建一个默认值(你需要通过CacheConfigurerSupport
扩展名指定它),例如:
@Configuration
@EnableCaching
public class CacheConfig extends CachingConfigurerSupport {
@Override
@Bean // not strictly necessary
public CacheManager cacheManager() { ... CacheManager A }
@Bean
public CacheManager bCacheManager() { ... CacheManager B }
}
Run Code Online (Sandbox Code Playgroud)
然后,对于10%的用例,您CacheConfig
需要在需要使用其他缓存管理器的类的顶部添加a
@CacheConfig(cacheManager="bCacheManager")
public class MyService { /*...*/ }
Run Code Online (Sandbox Code Playgroud)
如果只需要对一个方法使用其他缓存管理器,则也可以在方法级别指定
@Cacheable(cacheNames = "books", cacheManager = "bCacheManager")
public Book findById(long id) { /*...*/ }
Run Code Online (Sandbox Code Playgroud)
如果您不是这种情况,则需要一种方法来了解需要根据具体情况使用哪个缓存管理器.您可以根据目标类型(MyService
)或缓存(books
)的名称来执行此操作.你需要实现一个CacheResolver
为你做翻译的工具.
@Configuration
@EnableCaching
public class CacheConfig extends CachingConfigurerSupport {
@Override
public CacheResolver cacheResolver() { ... }
}
Run Code Online (Sandbox Code Playgroud)
查看javadoc以CacheResolver
获取更多详细信息.在实现中,您可能有几个CacheManager
实例(无论是否为bean),您将根据您的逻辑在内部调用,以确定应使用哪个管理器.
我在评论中看到你指的是"模块".缓存实际上是一个基础架构问题,因此我强烈建议您在应用程序级别上移动该决策.您可以将缓存标记为"本地",将其他标记为"群集".但你应该对名称有一些命名,以使其更容易.不要在模块级别选择缓存管理器.
这篇博客文章通过其他示例说明了这一点
正如@Stephane Nicoll解释的那样,您有几种选择。我将尝试提供有关custom的一些信息CacheResolver
。CacheResolver
有一种方法:
Collection<? extends Cache> resolveCaches(CacheOperationInvocationContext<?> context);
Run Code Online (Sandbox Code Playgroud)
这为可缓存操作的类,方法,参数等提供了上下文。
基本形式:
public class CustomCacheResolver implements CacheResolver {
private final CacheManager cacheManager;
public CustomCacheResolver(CacheManager cacheManager){
this.cacheManager = cacheManager;
}
@Override
public Collection<? extends Cache> resolveCaches(CacheOperationInvocationContext<?> context) {
Collection<Cache> caches = getCaches(cacheManager, context);
return caches;
}
private Collection<Cache> getCaches(CacheManager cacheManager, CacheOperationInvocationContext<?> context) {
return context.getOperation().getCacheNames().stream()
.map(cacheName -> cacheManager.getCache(cacheName))
.filter(cache -> cache != null)
.collect(Collectors.toList());
}
}
Run Code Online (Sandbox Code Playgroud)
CacheManager
为了简洁起见,我在这里使用一个。但是您可以将不同的CacheManager
s 绑定到CacheResolver
并进行更精细的选择:如果类名是X
,则使用GuavaCacheManager
,否则使用EhCacheCacheManager
。
完成此步骤后,您应该注册CacheResolver
,(再次可以CacheManagers
在此处绑定更多内容):
@Configuration
@EnableCaching
public class CacheConfiguration extends CachingConfigurerSupport {
@Bean
@Override
public CacheManager cacheManager() {
// Desired CacheManager
}
@Bean
@Override
public CacheResolver cacheResolver() {
return new CustomCacheResolver(cacheManager());
}
}
Run Code Online (Sandbox Code Playgroud)
而作为最后一步,你应该指定CustomCacheResolver
于一体@Cacheable
,@CachePut
,@CacheConfig
等注释。
@Cacheable(cacheResolver="cacheResolver")
Run Code Online (Sandbox Code Playgroud)
您可以在此处查找代码示例。
归档时间: |
|
查看次数: |
20064 次 |
最近记录: |