Я пробовал с блокировкой в Hibernate, но не могу получить правильный результат. Поток таков: я записываю транзакцию из истории баланса, вычисляю из базы данных, чтобы получить текущий баланс по счету, каждая вставленная новая запись получит новое текущее сальдо, а за вычетом суммы транзакции - имя базы данных InvoiceItems, как то, что я не получилнесоответствие движения текущего баланса:
id | account_id | date | amount | current_balance | type
1 A 2019-09-08:09:11:43.122 10 10 Topup
2 A 2019-10-08:11:23:21.331 -1 9 Transaction
3 A 2019-10-08:11:23:21.571 -1 9 Transaction
4 A 2019-10-08:11:23:21.721 -1 9 Transaction
5 A 2019-10-08:12:45:19.012 -1 6 Transaction
6 b 2019-10-08:11:23:21.721 100 100 Topup
запрос, как я получил расчет текущего баланса в Java, выглядит следующим образом:
public BigDecimal getBalance(String accountid) {
return (BigDecimal)this.session.createQuery("select SUM(amount) from InvoiceItems I WHERE account_id = '" + accountid + "' AND type='CBA_ADJ' ").setLockMode("I", LockMode.PESSIMISTIC_FORCE_INCREMENT).getSingleResult();
}
вызов основной функции:
InvoiceItemsDao ido = new InvoiceItemsDao(db);
InvoicesDao idio = new InvoicesDao(db);
String accountid = ido.getAccountId(jsonRecv.getString("externalkey"), tenantApiKey.getRecord_id());
BigDecimal balance = ido.getBalance(accountid); <-------- The locking query is here
LogSystem.info(request, "Balance before transaction : " + ido.getBalance(accountid));
InvoiceItems invoiceUsage = new InvoiceItems();
Accounts ac = ado.findByExternalKey(jsonRecv.getString("externalkey"), tenantApiKey.getRecord_id());
invoiceUsage.setAccount_id(ac.getId());
invoiceUsage.setAccount_record_id(ac);
invoiceUsage.setAmount(BigDecimal.valueOf(-jsonRecv.getLong("amount")));
invoiceUsage.setCreated_date(new Date());
invoiceUsage.setUsage_name("Transaction");
invoiceUsage.setCurrent_balance(balance.subtract(BigDecimal.valueOf(jsonRecv.getLong("amount"))));
db.session().save(invoiceItemsCBA_ADJ);
tx.commit();
Что мне не хватает с блокировкой потока, какая-либо подсказка?