问题描述
一个函数内多次update 资金,每次变化都需要记录交易日志;
每次资金变化都需要重新查询变化后的Amount。
相关代码
//更新一
long amountWX = 100;
int up = UserAccountMapper.updateAccount(id, amountWX);
//日志记录一
if (createAccountLog(id, rid, amountWX) == 0) {
throw new RuntimeException("日志失败");
}
//更新二
long amountAli = 200;
int up = UserAccountMapper.updateAccount(id, amountAli);
//日志记录二
if (createAccountLog(id, rid, amountAli) == 0) {
throw new RuntimeException("日志失败");
}
//更新三
long amountJD = 300;
int up = UserAccountMapper.updateAccount(id, amountJD);
//日志记录三
if (createAccountLog(id, rid, amountJD) == 0) {
throw new RuntimeException("日志失败");
}
protected int createAccountLog(long id, long rid, long amount) {
AccountLog accountLog = new AccountLog();
accountLog.setUserId(id);
accountLog.setType(rid);
accountLog.setChangeTime(System.currentTimeMillis());
//变化资金
accountLog.setCurrAmount(amount);
//重新查询变化后的资金情况记录?
Account account = UserAccountMapper.getUserAccount(id);
accountLog.setTotalAmount(account.getAmount);
return accountLogMapper.save(accountLog);
}
目前想到的解决办法是通过记录每次更新的amount 到内存,在最后一次通过批处理insert。这样解决了多次save日志的操作,但还需要每次查询变化后的资金情况,还有什么其他解决办法没?
第二次修改:
@Transactional(rollbackFor = Exception.class)
public SuccessOrderDTO doPay(GoodsBean goodsBean) throws Exception {
try {
SuccessOrderDTO successOrderDTO = new SuccessOrderDTO();
//支出
if (userAccountMapper.userAccountByExpend(/**参数省略*/) == 0) {
throw new BuyException();
}
if (createAccountLog(/**参数省略*/) == 0) {
throw new AuctionException("保存日志失败");
}
//收益
if (userAccountMapper.accountByIncome(/**参数省略*/) == 0) {
throw new BuyException();
}
//日志
if (createAccountLog(/**参数省略*/) == 0) {
throw new AuctionException("保存日志失败");
}
//日志
if (createAccountLog(/**参数省略*/) == 0) {
throw new AuctionException("保存日志失败");
}
//日志
if (createAccountLog(/**参数省略*/) {
throw new AuctionException("保存日志失败");
}
successOrderDTO.setTypeName(csAuctionType.getTypeName());
successOrderDTO.setGoodsPrice(goodsPrice.toString());
successOrderDTO.setVouchersNum(csAuctionType.getGiftVoucherNum());
successOrderDTO.setGoodsName(csAuctionOrder.getGoodsName());
successOrderDTO.setOrderNo(csAuctionOrder.getOrderNo());
successOrderDTO.setAuctionUserName(csAuctionOrder.getRefAuctionUserName());
successOrderDTO.setCreateOrderTime(csAuctionOrder.getCreateTime());
return successOrderDTO;
} catch (Exception e) {
log.error("=========Exception============ {} =============", e.getMessage());
throw e;
}
}
建议把你业务代码贴进来,不要 mock 代码
或者具体说一下你的业务场景,看是否可以通过业务场景优化。
本身看你这个方法觉得有些奇怪