正如Andrews S所指出的,这听起来确实像是自动配置中的缓存冲突。
@EnableCaching
's javadoc
有一些关于
cacheManager
是被选中的,特别是一个关于如何继续的想法。在这种情况下,你要做的是建立一个
CachingConfigurer
选择缓存-也许您可以扩展
CachingConfigurerSupport
(如下面的例子)并完成。
类型的豆子
CacheManager
必须注册,因为框架没有合理的默认值可以用作约定。鉴于
<cache:annotation-driven>
按类型搜索缓存管理器bean。因此,缓存管理器bean方法的命名并不重要。
对于那些希望在
@启用缓存
以及要使用的缓存管理器bean
@Override
-注释方法如下:
@Configuration
@EnableCaching
public class AppConfig extends CachingConfigurerSupport {
@Bean
public MyService myService() {
// configure and return a class having @Cacheable methods
return new MyService();
}
@Bean
@Override
public CacheManager cacheManager() {
// configure and return an implementation of Spring's CacheManager SPI
SimpleCacheManager cacheManager = new SimpleCacheManager();
cacheManager.setCaches(Arrays.asList(new ConcurrentMapCache("default")));
return cacheManager;
}
@Bean
@Override
public KeyGenerator keyGenerator() {
// configure and return an implementation of Spring's KeyGenerator SPI
return new MyKeyGenerator();
}
}
这种方法可能仅仅是因为更为明确而可取,也可能是区分两者所必需的
缓存管理器
同一容器中的豆子。
keyGenerator
KeyGenerator
SPI公司。正常情况下,
@启用缓存
将配置Spring的
SimpleKeyGenerator
大笑配置器
,必须显式提供密钥生成器。返回
null
或
new SimpleKeyGenerator()
如果不需要自定义,则使用此方法。
大笑配置器
cachingconfigurers支持
它为所有方法提供了一个默认实现,如果您不需要自定义所有方法,那么这些方法将非常有用。看到了吗
CachingConfigurer
Javadoc
更多细节。
How to have multiple cache manager configuration in spring cache java
编辑:
@Bean
@Override
public CacheResolver cacheResolver() {
return new SimpleCacheResolver(cacheManager()) {
@Override
protected Collection<String> getCacheNames(CacheOperationInvocationContext<?> context) {
Collection<String> toReturn = super.getCacheNames(context);
toReturn.forEach(System.out::println);
return toReturn;
}
@Override
public Collection<? extends Cache> resolveCaches(CacheOperationInvocationContext<?> context) {
System.out.println(Arrays.toString(context.getArgs()));
System.out.println(context.getClass());
System.out.println(context.getMethod());
System.out.println(context.getOperation());
return super.resolveCaches(context);
}
};
}
除了看到已建立的缓存名称弹出外,我注意到上下文正在输出:
[]
公共摘要…transferobjects.CacheContainer…service.LookupService.getCacheSelections()
生成器[public…transferobjects.CacheContainer…dao.LookupFacade.getCacheSelections()]缓存=[cacheselections]| key=“”| keyGenerator=“”| cacheManager=“”| cacheResolver=“”| condition=“”|除非=“”| sync=“”true'
这个
context.getClass()
考虑到您的方面问题,输出是有意义的。也就是说,我在自己的代码中有一个非常类似的日志记录/计时方面,这不会对缓存的其余部分造成任何混乱。试试我的解析器,看看输出是否对缓存代码发出的调用有指导意义。
编辑#2:
@Cacheable
在它不能工作的地方工作——主要是因为这个框架还没有完全建立起来。您正在使用
InitializingBean
我试着用
@PostConstruct
两者都失败了。
Spring cache using @Cacheable during @PostConstruct does not work
我拿到你的github代码了。我最初遇到了您在另一个线程中报告的阻塞问题,但是为了一次处理一件事情,我只是注释掉了阻塞代码并调用了
service.cachedMethod()
直接。
RuntimeException
. 我注意到你的
NOT CACHED
System.out.println(service.toString());
在控制器的afterPropertiesSet()方法中
com.company.client.api.domain.CachedServiceImpl@2bbfb8b
因此,一般来说,您需要重新考虑如何启用此功能。