标签: spring-cache

Spring Boot 2 - 使用 Mockito 测试 @Cacheable 不带参数的方法不起作用

我有一个使用 Spring Boot 2 的应用程序。我想测试一个带有@Cacheable (Spring Cache) 的方法。我做了一个简单的例子来展示这个想法:

@Service
public class KeyService {

    @Cacheable("keyCache")
    public String getKey() {
        return "fakeKey";
    }
}
Run Code Online (Sandbox Code Playgroud)

和测试类:

@RunWith(SpringRunner.class)
@SpringBootTest
public class KeyServiceTest {

    @Autowired
    private KeyService keyService;

    @Test
    public void shouldReturnTheSameKey() {

        Mockito.when(keyService.getKey()).thenReturn("key1", "key2");

        String firstCall = keyService.getKey();
        assertEquals("key1", firstCall);

        String secondCall = keyService.getKey();
        assertEquals("key1", secondCall);
    }

    @EnableCaching
    @Configuration
    static class KeyServiceConfig {

        @Bean
        KeyService keyService() {
            return Mockito.mock(KeyService.class);
        }

        @Bean
        CacheManager cacheManager() {
            return new ConcurrentMapCacheManager("keyCache");
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

上面的例子不起作用。但是,如果我更改getKey()接收参数的方法: …

java spring mockito spring-boot spring-cache

5
推荐指数
1
解决办法
9741
查看次数

如何在 Spring 中缓存对象列表?

我有一个名为 getUserById 的方法

@Cacheable(value = "Account", key = "#accountId")
public Account getUserById(Long accountId) {
Run Code Online (Sandbox Code Playgroud)

另一个名为 getUserByIds 的方法

@Cacheable(?????)
public List<Account> getUserByIds(List<Long> accountIds) {
Run Code Online (Sandbox Code Playgroud)

如何通过帐户 ID 缓存所有帐户?谢谢

spring spring-boot spring-cache

5
推荐指数
1
解决办法
1万
查看次数

@Cacheable 不拦截方法,缓存始终为空

我有一个方法如下:

@Cacheable(value = "SAMPLE")
public List<SomeObj> find() {
     // Method that initiates and returns the List<SomeObj> and takes around 2-3 seconds, does some logging too
}
Run Code Online (Sandbox Code Playgroud)

我正在我的配置类之一中启用缓存:

@EnableCaching
@Configuration
public SomeConf extends CachingConfigurerSupport {

    // Here I also initialize my classes with @Cacheable annotation

    @Bean
    @Override
    public CacheManager cacheManager() {
        SimpleCacheManager cacheManager = new SimpleCacheManager();
        cacheManager.setCaches(Collections.singletonList((new ConcurrentMapCache("SAMPLE"))));
        return cacheManager;
    }


    @Bean
    @Override
    public CacheResolver cacheResolver() {
        return new SimpleCacheResolver(cacheManager());
    }

    @Bean
    @Override
    public KeyGenerator keyGenerator() {
        return new SimpleKeyGenerator();
    } …
Run Code Online (Sandbox Code Playgroud)

java spring caching spring-boot spring-cache

5
推荐指数
1
解决办法
5827
查看次数

无法在 RedisCacheConfiguration 中使用任何对象作为 KeySerializer

一组较旧的代码RedisCacheManager针对RedisTemplate产品中使用的大量缓存进行了配置。特别是模板会经常声明非字符串类型的键序列化器,例如:

<property name="keySerializer">
    <bean class="org.springframework.data.redis.serializer.Jackson2JsonRedisSerializer">
        <constructor-arg value="java.lang.Long"/>
    </bean>
</property>
Run Code Online (Sandbox Code Playgroud)

(有时是 UUID)。当希望使用 Springboot 升级/转换到更新版本时RedisCacheManagerBuilder,配置序列化器的唯一方法似乎是通过RedisCacheConfiguration硬编码来获取SerializationPair<String>for 键。

这种强制输入字符串是否有原因?

redis spring-boot spring-cache

5
推荐指数
0
解决办法
241
查看次数

Spring Boot:重写 CacheManager bean 使缓存相关属性不起作用

我有一个带有 Redis 缓存的 Spring Boot 2 应用程序。它工作得很好,直到我覆盖了CacheManagerbean。

问题:以下配置属性被忽略(我无法再关闭缓存):

spring.cache.type=none
Run Code Online (Sandbox Code Playgroud)

尽管根据文档它应该可以工作。

问:作品如何制作spring.cache.type=none

有一个像这样的解决方法,但它远不是一个好的解决方案。

更多详细信息:这是我的配置:

@Configuration
public class CacheConfiguration {
    @Bean
    RedisCacheWriter redisCacheWriter(RedisConnectionFactory connectionFactory) {
        return RedisCacheWriter.lockingRedisCacheWriter(connectionFactory);
    }

    @Bean
    CacheManager cacheManager(RedisCacheWriter redisCacheWriter) {
        Map<String, RedisCacheConfiguration> ttlConfiguration = ...
        RedisCacheConfiguration defaultTtlConfiguration = ...
        return new RedisCacheManager(
                redisCacheWriter, defaultTtlConfiguration, ttlConfiguration
        );
    }
}
Run Code Online (Sandbox Code Playgroud)

java spring redis spring-boot spring-cache

5
推荐指数
1
解决办法
3855
查看次数

如何在不覆盖默认 spring-cache 的情况下创建辅助 CacheManager

我的 application.yml 中有一个默认的 redis 缓存配置:

cache:
    type: redis
    redis:
      time-to-live: 7200000 # 2 hour TTL - Tune this if needed later
  redis:
    host: myHost
    port: myPort
    password: myPass
    ssl: true
    cluster:
      nodes: clusterNodes
    timeout: 10000
Run Code Online (Sandbox Code Playgroud)

它工作得很好,我不想为它创建任何自定义缓存管理器。

但是,我的代码中有一些缓存不需要使用 redis。因此,我想创建第二个 CacheManager,它是一个简单的 ConcurrentHashMap 并使用 @Cacheable 指定它

为此,我创建了一个新的 CacheManager Bean:


@Configuration
@EnableCaching
@Slf4j
class CachingConfiguration {

    @Bean(name = "inMemoryCache")
    public CacheManager inMemoryCache() {
        SimpleCacheManager cache = new SimpleCacheManager();
        cache.setCaches(Arrays.asList(new ConcurrentMapCache("CACHE"));
        return cache;
    }

}
Run Code Online (Sandbox Code Playgroud)

这导致 inMemoryCache 成为我的默认缓存,并且我所有其他 @Cacheable() 都尝试使用 inMemoryCache。我不希望我创建的 CacheManager bean 成为我的默认值。无论如何,我可以指定它是次要的,并且不会阻止 spring-cache …

java spring caching redis spring-cache

5
推荐指数
1
解决办法
2328
查看次数

如何使用 spring 缓存在 Hazelcast 缓存映射上设置 TTL

我正在使用带有 Spring Boot 的 Hazelcast 集群缓存。我使用的是 4.2 版本的 hazelcast。

缓存工作正常,但在 TTL 后不会从缓存映射中逐出数据。始终保留相同的数据。我尝试了很多设置ttl的方法,但没有成功。

这是我的机会配置类

import com.hazelcast.client.HazelcastClient;
import com.hazelcast.client.config.ClientConfig;
import com.hazelcast.core.HazelcastInstance;
import com.hazelcast.spring.cache.HazelcastCacheManager;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.cache.CacheManager;
import org.springframework.cache.annotation.EnableCaching;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

@Configuration
@EnableCaching
public class CacheConfig {

  @Value("${hazelcast.cluster-name}")
  private String hzClusterName;

  @Value("${hazelcast.address}")
  private String hzAddress;

  @Bean
  HazelcastInstance hazelcastInstance() {
    return HazelcastClient.newHazelcastClient(clientConfig());
  }

  @Bean
  public ClientConfig clientConfig() {
    ClientConfig cfg = ClientConfig.load();
    cfg.setClusterName(hzClusterName);
    cfg.getNetworkConfig().addAddress(hzAddress);
    return cfg;
  }

  @Bean
  public CacheManager cacheManager() {
    return new HazelcastCacheManager(hazelcastInstance());
  }
}
Run Code Online (Sandbox Code Playgroud)

我使用可缓存的缓存类

@Cacheable("items")
public String …
Run Code Online (Sandbox Code Playgroud)

java hazelcast spring-boot spring-cache

5
推荐指数
1
解决办法
4891
查看次数

Spring Data Cache + Redis:如何避免将类名存储在序列化的 JSON 中,从而浪费大量空间?

我正在使用 Spring Data Cache,并使用 Redis 作为缓存管理器。配置如下:

    return RedisCacheManager.builder(redisConnectionFactory)
        .cacheDefaults(
            RedisCacheConfiguration.defaultCacheConfig()
                .serializeKeysWith(SerializationPair.fromSerializer(RedisSerializer.string()))
                .serializeValuesWith(SerializationPair.fromSerializer(RedisSerializer.json()))
        )
        .build()
Run Code Online (Sandbox Code Playgroud)

让我们想象一个使用 spring 数据缓存的非常简单的例子:

@Cacheable(...)
MyPOJO compute() { ... }
Run Code Online (Sandbox Code Playgroud)

然而,RedisSerializer.json()确实是一个GenericJackson2JsonRedisSerializer。因此,恕我直言,它将存储诸如{"hello":"world","@class":"com.my.name.some.package.MyPOJO"}. 这@class: ...部分相当长,浪费了 Redis 中宝贵的内存。此外,恕我直言,Spring Data Cache 应该足够聪明,能够意识到值类型确实是MyPOJO,所以它不需要存储它"@class"

因此我的问题是:如何避免在 Spring Data Cache + Redis CacheManager 中将类名存储在序列化 JSON 中,这会浪费大量空间?

感谢您的任何建议!

java spring redis spring-data spring-cache

5
推荐指数
1
解决办法
4320
查看次数

Hibernate缓存与Spring缓存

谁能解释一下hibernate二级缓存和spring缓存有什么区别?

在单个应用程序中使用两者有意义吗?如果不推荐那么什么时候使用哪一个?

如果有人给出基于现实生活场景的解释,将非常有助于轻松理解。

spring hibernate hibernate-cache spring-boot spring-cache

5
推荐指数
1
解决办法
2988
查看次数

如果仅用于简单缓存,Redis 缓存是否比 Spring 缓存有优势?

我是缓存事物的新手,并为我的 Spring Boot 应用程序学习一些不同的解决方案。我正在研究 Spring Cache,它是比我看到的 redis 缓存更简单的缓存机制(这就是我所寻找的)。而且还有很多像“spring+redis缓存”这样的资源。当我查看简单用法时,我发现没有任何区别。即使注释是相同的(Cacheable、CacheEvict、CachePut 等),除了额外的 redis 配置和 redis docker 容器等之外,我看不到用法上的差异...而且这些spring+redis 缓存文章都没有告诉我们有什么区别介于 spring 缓存和 spring+redis 缓存之间。

redis缓存相对于spring缓存有什么优势?或者你能告诉一个简单的用例,我肯定需要使用 redis 缓存,而我无法使用 spring 缓存实现它吗?

spring redis spring-data-redis spring-boot spring-cache

5
推荐指数
1
解决办法
6206
查看次数