【问题标题】:How to have multiple cache manager configuration in multiple modules/projects spring cache java如何在多个模块/项目中配置多个缓存管理器spring cache java
【发布时间】:2018-02-13 15:10:12
【问题描述】:

目前有两个不同的模块假设项目 A 和项目 B。项目 B 导入/使用到项目 A 中。目前项目 B 已经有 CacheManager。

项目B

  public class CacheConfig {

  @Bean 
  public CacheManager cacheManager() {

  // using SimpleCacheManager()

  }
 }

但现在计划在项目 A 中实现 CacheManager 用于其他目的。

class SomeCacheConfig{

@Bean 
public CacheManager someCacheManager(){
 // using SimpleCacheManager() 
}

}

加载应用程序时抛出以下异常。

 java.lang.IllegalStateException: No CacheResolver specified, and no unique bean of type CacheManager found. Mark one as primary (or give it the name 'cacheManager') or declare a specific CacheManager to use, that serves as the default one.

你能帮我如何在多个模块/项目中实现多个缓存管理器吗?

【问题讨论】:

  • 为什么必须是唯一的?重用你拥有的缓存管理器。
  • @duffymo,可能以后项目B可以把它拿出来。所以我们在项目 A 中需要新的 cacheManager
  • 您想同时使用这两个不同的缓存管理器吗?还是只用一个?
  • @javvano,我想使用两个缓存管理器

标签: java spring-boot caching guava


【解决方案1】:

那好吧。 将 @Primary 放在将用作默认值的 CacheManager bean 上。

@Primary
@Bean(name = "primaryCacheManager")
public CacheManager primaryCacheManager() {
    return new SimpleCacheManager();
}


@Bean(name = "myCacheManager")
public CacheManager myCacheManager() {
    return new SimpleCacheManager();
}

当您想使用另一个(即不是默认值)时,请使用 @Qualifier 注释明确定义 CacheManager bean 的名称。

@Autowired
@Qualifier("myCacheManager")
private CacheManager myCacheManager;

或者如果你使用annotation base Spring Cache implementation,你也可以定义一个CacheManager名字作为这些注解的属性

@Cacheable(value = "some",cacheManager = "myCacheManager")
public String getSome(){
    return "";
}

【讨论】:

  • 感谢您的帮助。但是在这种情况下,我们不能使用二级缓存管理器。但在我的用例中,我需要同时使用两个缓存管理器。
【解决方案2】:

可以使用Spring提供的CompositeCacheManager实现(https://docs.spring.io/spring-framework/docs/current/javadoc-api/org/springframework/cache/support/CompositeCacheManager.html)

这允许您编写缓存管理器列表。复合管理器将遍历列表并在它存在的第一个管理器中获取缓存。请注意“注意:此复合管理器委托给的常规 CacheManagers 需要从 getCache(String) 返回 null 如果他们不知道指定的“

【讨论】:

    【解决方案3】:

    Erik Ahlswede 建议的最终对我有用的方法

    @Bean
    public CacheManager cacheManager() {
        return new CompositeCacheManager(
                new ConcurrentMapCacheManager("cacheA") {
                    @Override
                    protected Cache createConcurrentMapCache(final String name) {
                        return new ConcurrentMapCache(name,
                                CacheBuilder.newBuilder()
                                        .expireAfterWrite(CACHE_TTL_IN_SECONDS, TimeUnit.SECONDS)
                                        .maximumSize(MAX_ENTRIES_IN_CACHE)
                                        .build().asMap(), false);
                    }
                },
                new ConcurrentMapCacheManager("cacheB") {
    
                    @Override
                    protected Cache createConcurrentMapCache(final String name) {
                        return new ConcurrentMapCache(name,
                                CacheBuilder.newBuilder()
                                        .expireAfterWrite(CACHE_TTL_IN_SECONDS, TimeUnit.SECONDS)
                                        .maximumSize(MAX_ENTRIES_IN_CACHE)
                                        .build().asMap(), false);
                    }
                }
        );
    }
    

    然后和它一起使用

    @Cacheable(cacheNames = "someComplicatedAction", cacheManager = "cacheA")
    public String someComplicatedAction() {
    
    }
    

    【讨论】:

      猜你喜欢
      • 2016-11-28
      • 2018-02-10
      • 2014-10-12
      • 2012-02-14
      • 1970-01-01
      • 2021-10-10
      • 2017-02-02
      • 1970-01-01
      • 2017-03-20
      相关资源
      最近更新 更多