【问题标题】:Spring Boot cache not caching method call based on dynamic controller parameterSpring Boot缓存不缓存基于动态控制器参数的方法调用
【发布时间】:2020-08-03 22:42:48
【问题描述】:

我正在尝试将 Spring Boot Cache 与 Caffeine cacheManager 一起使用。

我已经将一个服务类注入到这样的控制器中:

@RestController
@RequestMapping("property")
public class PropertyController {

    private final PropertyService propertyService;

    @Autowired
    public PropertyController(PropertyService propertyService) {
        this.propertyService = propertyService;
    }

    @PostMapping("get")
    public Property getPropertyByName(@RequestParam("name") String name) {
        return propertyService.get(name);
    }
}

PropertyService 看起来像这样:

@CacheConfig(cacheNames = "property")
@Service
public class PropertyServiceImpl implements PropertyService {

    private final PropertyRepository propertyRepository;

    @Autowired
    public PropertyServiceImpl(PropertyRepository propertyRepository) {
        this.propertyRepository = propertyRepository;
    }
    
    @Override
    public Property get(@NonNull String name, @Nullable String entity, @Nullable Long entityId) {
        System.out.println("inside: " + name);
        return propertyRepository.findByNameAndEntityAndEntityId(name, entity, entityId);
    }

    @Cacheable
    @Override
    public Property get(@NonNull String name) {
        return get(name, null, null);
    }
}

现在,当我调用 RestController get 端点并为名称提供一个值时,每个请求最终都会在应该被缓存的方法中执行。

但是,如果我调用控制器 get 端点但将硬编码的字符串传递给服务类方法,如下所示:

@PostMapping("get")
public Property getPropertyByName(@RequestParam("name") String name) {
    return propertyService.get("hardcoded");
}

那么该方法只会在第一次被调用,而不会在后续调用中被调用。

这里发生了什么?为什么动态提供值时不缓存方法调用?

这是一些配置:

@Configuration
public class CacheConfiguration {

    @Bean
    public CacheManager cacheManager() {
        val caffeineCacheManager = new CaffeineCacheManager("property", "another");
        caffeineCacheManager.setCaffeine(caffeineCacheBuilder());
        return caffeineCacheManager;
    }

    public Caffeine<Object, Object> caffeineCacheBuilder() {
        return Caffeine.newBuilder()
                .initialCapacity(200)
                .maximumSize(500)
                .weakKeys()
                .recordStats();
    }
}

【问题讨论】:

    标签: java spring spring-boot caching


    【解决方案1】:

    2 个解决方案(它们对我有用):

    • 删除.weakKeys()

    • propertyService.get(name.intern()) - 不会真的这样做,可能会付出很大的代价

    抱歉,我没有足够的知识来解释这一点。可能与 Caffeine 的内部键表示有关。

    【讨论】:

      猜你喜欢
      • 2021-01-25
      • 2016-05-25
      • 1970-01-01
      • 1970-01-01
      • 2017-01-01
      • 2021-11-10
      • 2018-06-03
      • 1970-01-01
      • 2018-05-27
      相关资源
      最近更新 更多