Firebase Realtime Database调用Transaction读写数据时报空指针异常
问题成因
- 核心原因是Firebase Realtime Database的
doTransaction回调会被多次触发:首次触发时通常读取的是本地缓存数据,如果本地没有对应account_details/Gn2eRixQQiTpvhX870n6nZp66tO2/initialBalance节点的缓存,currentData.child("initialBalance").getValue()会返回null,直接将null强转为double基础类型,就触发了日志中提示的空指针异常。 - 额外逻辑问题:当前代码仅读取余额后直接回写,没有叠加收款金额,就算空指针修复也无法完成余额更新的业务需求。
修复方案
修正后的完整代码如下:
private void receiveMoney() { String mobile=recipientText.getText().toString().trim(); Double amount=Double.parseDouble(amountText.getText().toString().trim()); mDatabase3=FirebaseDatabase.getInstance().getReference("account_details/Gn2eRixQQiTpvhX870n6nZp66tO2"); mDatabase3.runTransaction(new Transaction.Handler() { @NonNull @Override public Transaction.Result doTransaction(@NonNull MutableData currentData) { // 先做非空判断,避免空指针 Object balanceVal = currentData.child("initialBalance").getValue(); if (balanceVal == null) { // 本地无缓存时直接返回,Firebase会自动重试事务 return Transaction.success(currentData); } Double newBalance = (Double) balanceVal; System.out.println("Current Balance: "+newBalance+" Amount: "+amount); // 叠加收款金额后回写到对应字段 currentData.child("initialBalance").setValue(newBalance + amount); return Transaction.success(currentData); } @Override public void onComplete(@Nullable DatabaseError error, boolean committed, @Nullable DataSnapshot currentData) { // 补充错误处理,方便排查问题 if (error != null) { Log.e("TransactionError", "事务执行失败: " + error.getMessage()); return; } if (committed) { Log.d("TransactionSuccess", "余额更新成功"); } } }); }
主要修改点:
- 增加了
initialBalance取值的非空判断,本地无缓存时直接返回触发Firebase自动重试,从根源避免空指针 - 修正业务逻辑,读取余额后叠加收款金额再回写到
initialBalance字段,而非直接覆盖整个父节点 - 补充
onComplete回调的错误和成功状态处理,方便后续问题排查
内容的提问来源于stack exchange,提问作者yuri yuna
相关产品推荐
相关产品推荐

