如何在 Spring Boot 中使用控制器/服务上的缓存?

Cha*_*hea 3 java spring-boot spring-cache

我正在尝试按照https://www.java4s.com/spring-boot-tutorials/how-to-configure-cache-in-spring-boot-applications/ 上的说明在我的 spring-boot 应用程序上添加缓存,但它不起作用。我不完全确定如何测试它。我在控制器下有一个 system.out.print 就像这篇文章一样。如果缓存有效,那么它只会打印“测试”一次,但从具有相同输入的请求中返回相同的结果。我的代码如下:

货币控制器.java

    @RequestMapping(method = RequestMethod.POST)
    @Cacheable(value="currency")
    public ResponseEntity getExchangedCurrency(final @RequestBody CurrencyExchange currencyExchange) {
        System.out.println("Test");
        return ResponseEntity.ok()
              .headers(responseHeaders)
              .body(currencyService.calculate(currencyExchange));
    }

Run Code Online (Sandbox Code Playgroud)

应用程序.java

@SpringBootApplication
@EnableCaching
public class App {
    public static void main(String[] args) {
        SpringApplication.run(App.class, args);



    }
}

Run Code Online (Sandbox Code Playgroud)

Pas*_*kam 6

@Cacheable注释的工作方式是默认使用方法参数作为缓存映射的键。在这种情况下currencyExchange对象。由于它是每个请求上的对象,spring 请求调度程序创建新对象,缓存管理器作为单独的键保留。

Req1 -> object1 -> map.put(object1, response)

Req2 -> object2 -> map.contains(object2) -> false -> map.put(object2, response)

如果您认为所有发布请求都从缓存发送相同的响应,但情况并非总是如此,您可以像这样更改密钥。

@RequestMapping(method = RequestMethod.POST)
@Cacheable(value="currency", key="#root.method")
public ResponseEntity getExchangedCurrency(final @RequestBody CurrencyExchange currencyExchange) {
    System.out.println("Test");
    return ResponseEntity.ok()
          .headers(responseHeaders)
          .body(currencyService.calculate(currencyExchange));
}
Run Code Online (Sandbox Code Playgroud)

您还可以使用 Spring 表达式语言 (SpEL) 表达式来定义键,如果您的currencyExchange 具有getId()可用作潜在缓存键的方法,您可以这样做

@Cacheable(value="currency", key="#root.args[0].getId()")
Run Code Online (Sandbox Code Playgroud)

清除缓存@EnableCaching在spring boot主类上添加,fixedDelay以毫秒为单位

@CacheEvict(allEntries = true, value = {"currency"})
@Scheduled(fixedDelay = 5000 ,  initialDelay = 5000)
public void clearCache() {
    System.out.println("Cache cleared");
}
Run Code Online (Sandbox Code Playgroud)