前言
今天一个上线许久的系统突然无法新增
证书,但是不是所有都不允许新增,只是编号重复的无法新增。从逻辑
上想,我是设置了编号重复判断
,但是该业务判断逻辑未生效,从缓存
上将,会不会是id=null
导致的问题。
报错详情:
java.lang.IllegalArgumentException: Null key returned for cache operation (maybe you are using named params on classes without debug info?) Builder[public java.lang.Object com.egag.cert.controller.CertCompanyController.save(com.egag.cert.entity.CertCompany)] caches=[cache-certCompany] | key='#certCompany.certId' | keyGenerator='' | cacheManager='' | cacheResolver='' | condition='',false,false
at org.springframework.cache.interceptor.CacheAspectSupport.generateKey(CacheAspectSupport.java:578)
at org.springframework.cache.interceptor.CacheAspectSupport.performCacheEvict(CacheAspectSupport.java:492)
at org.springframework.cache.interceptor.CacheAspectSupport.processCacheEvicts(CacheAspectSupport.java:476)
at org.springframework.cache.interceptor.CacheAspectSupport.execute(CacheAspectSupport.java:433)
at org.springframework.cache.interceptor.CacheAspectSupport.execute(CacheAspectSupport.java:345)
at org.springframework.cache.interceptor.CacheInterceptor.invoke(CacheInterceptor.java:61)
检查思路
报错信息非常清晰,首先是缓存报错
,另一方面是发生在新增的情况(id = null / 0)
且编号重复
的情况,编辑旧的数据则不会影响。
public class EhCacheUtil {
public static final String CACHE_NAME_CERT_COMPANY="cache-certCompany";
public static final String CACHE_NAME_CERT_COMPANY_LIST="cache-certCompanyList";
public static final String CACHE_KEY_CERT_COMPANY_OBJ="#certCompany.certId";
public static final String CACHE_KEY_CERT_COMPANY_ID="#id";
//省略其他
}
思来想去莫非是新增的对象在缓存中判断不严谨,因为我们重点在于更新旧的数据,新的数据查询的时候自己加载到缓存就可以了。于是我们需要增加一个condition
的参数。
/**
* 新增或编辑
*/
@PostMapping("/save")
@CacheEvict(value = EhCacheUtil.CACHE_NAME_CERT_COMPANY, key = EhCacheUtil.CACHE_KEY_CERT_COMPANY_OBJ)
public Object save(@RequestBody CertCompany certCompany){
log.info("certCompany:"+JSON.toJSONString(certCompany));
CertCompany oldCertCompany = certCompanyMapper.selectOne(new QueryWrapper<CertCompany>().eq("cert_id",certCompany.getCertId()));
certCompany.setUpdateTime(new Date());
if(oldCertCompany!=null){
certCompanyMapper.updateById(certCompany);
}else{
if(certCompanyMapper.selectOne(new QueryWrapper<CertCompany>().eq("cert_number",certCompany.getCertNumber()))!=null){
return ReturnT.ERROR("保存失败,名字重复");
}
//创建MiniCode
certCompanyMapper.insert(certCompany);
}
//省略部分业务逻辑
//清空列表缓存
cacheService.cleanCompanyListByPageLimit();
return ReturnT.SUCCESS("保存成功");
}
解决方案
public class EhCacheUtil {
public static final String CACHE_NAME_CERT_COMPANY="cache-certCompany";
public static final String CACHE_NAME_CERT_COMPANY_LIST="cache-certCompanyList";
public static final String CACHE_KEY_CERT_COMPANY_OBJ="#certCompany.certId";
//zhengkai.blog.csdn.net 新增以解决Null key returned for cache operation问题
public static final String CACHE_KEY_CERT_COMPANY_OBJ_NOTNULL="#certCompany.certId !=null ";
public static final String CACHE_KEY_CERT_COMPANY_ID="#id";
//省略其他
}
/**
* 新增或编辑
*/
@PostMapping("/save")
@CacheEvict(value = EhCacheUtil.CACHE_NAME_CERT_COMPANY, key = EhCacheUtil.CACHE_KEY_CERT_COMPANY_OBJ,condition = EhCacheUtil.CACHE_KEY_CERT_COMPANY_OBJ_NOTNULL)
public Object save(@RequestBody CertCompany certCompany){
//省略业务逻辑
}