在一个事务Transactional内,查询缓存,并更新缓存实体;方法异常之后。数据库没有被更新。造成数据库和缓存不一致。
service代码如下:
public interface EmployeeService {
public void CacheTest();
}
EmployeeServiceImpl代码如下:
@Service
public class EmployeeServiceImpl implements EmployeeService {
private EmployeeService getProxy() {
return (EmployeeService)AopContext.currentProxy();
}
@Override
@Transactional
public void CacheTest() {
// from db
Employee employee = getProxy().findByUid("327d626c-bffc-11e9-b4c9-00163e06591c");
// from cache
employee = getProxy().findByUid("327d626c-bffc-11e9-b4c9-00163e06591c");
employee.setName("name update");
if (employee != null)
throw new ApiException("dd");
}
}
测试代码如下:
@Test
public void CacheTest(){
try {
employeeService.CacheTest();
} catch (Exception e) {
e.printStackTrace();
}
logger.info(employeeService.findByUid("327d626c-bffc-11e9-b4c9-00163e06591c").getName());
}
打印的结果name update
表示名字确实被更新了,但是我们没操作数据库,数据库没有被更新。
结论:
从缓存拿出来的对象不能随便更改。要和数据库保存一致。@Transactional
注解对缓存没有效果。如果能实现,最好的方式是缓存的对象都没有setter方法。