@Cacheable键值碰撞问题

最近遇到一个非常奇怪的问题,就是一个使用了缓存的方法,获取到的一条数据出现了问题,之前并没有缓存过这组查询参数,但是并没有从数据库查询,而是直接从缓存中拿到了数据。但是这个方法从来没有改过,以前也没出现过问题。

方法使用的是@Cacheable注解的,开始我以为是并发过高导致,但是看了日志发现并不是。

于是我把一个小时内(缓存的有效时间)的调用这个方法的参数全部来执行了一遍这个方法,发现缓存的数据大小少了一个。于是我找了一下缓存的默认生成策略是HashCodeCacheKeyGenerator。于是用这个生成策略使用参数生成了key发现出现了重复的。问题就是它了。

public static void main(String[] args) throws Exception {
//	ListCacheKeyGenerator g = new ListCacheKeyGenerator();
//	StringCacheKeyGenerator g = new StringCacheKeyGenerator();
	HashCodeCacheKeyGenerator g = new HashCodeCacheKeyGenerator();
//	MessageDigestCacheKeyGenerator g = new MessageDigestCacheKeyGenerator();
	System.out.println(g.generateKey(1, "87"));
	System.out.println(g.generateKey(2, "77"));
}

问题找到了,修复办法其实就简单了,指定其他的生成策略就可以了:

@Cacheable(cacheName = "messages", keyGenerator = @KeyGenerator(name = StringCacheKeyGenerator.DEFAULT_BEAN_NAME))