[英]How to listen for Firebase setValue completion
我想在 Firebase 中设置类似群聊的内容。 如果您有正确的组 ID,则可以加入。
问题是 Firebase 引用始终存在。 它们是动态创建的。 为了允许在加入过程中进行一些错误检查,我想将创建新数据库条目的用户添加到用户表中。
public void createParty() {
// you need to be signed in to create a party
assertState(DBState.SignedIn);
// create a new party
ourPartyDatabaseReference = partiesDatabaseReference.push();
usersDatabaseReference = ourPartyDatabaseReference.child("users");
// write our user to the table of users, now the ourPartyReference actually exists
// and if you look for existing users, you will always find at least the original creator
Task initTask = usersDatabaseReference.child(user.getUid()).setValue(true);
完成此操作后,我调用一个辅助方法connectToParty
来设置一些引用并将数据库连接的状态更改为DBState.Connected
。 现在您可以获取聚会的密钥并将其传输给其他用户。 关键是指firebase中的名称。
问题是:其他用户需要检查他们是否使用了有效的密钥进行连接。 他们通过检查key/users
下是否有数据来做到这一点。 因此,只有当第一个用户已成功写入数据库时,该方才有效。
有时写入过程需要很长时间,有时似乎完全失败。 所以我设置了监听器:
Task initTask = usersDatabaseReference.child(user.getUid()).setValue(true);
initTask.addOnSuccessListener(new OnSuccessListener() {
@Override
public void onSuccess(Object o) {
connectToParty();
}
});
initTask.addOnFailureListener(new OnFailureListener() {
@Override
public void onFailure(@NonNull Exception e) {
changeState(DBState.SignedIn, DBTransition.Failure);
}
});
这是由测试覆盖的。 该测试会建立连接、登录并创建派对。 如果聚会在特定超时内创建,则测试通过。
10 次中有 9 次都没有问题。 但有时测试失败。
这与超时时间过短无关。 任务的回调根本不会被调用。 我读到此回调仅在您的连接在线时才有效。
所以我添加了firebaseDatabase.goOnline();
到我的代码,就在任务之前。 但这无济于事。
我通过局域网连接到互联网。 所有其他测试都通过了,他们也需要访问 firebase。 例如登录过程。
将值写入数据库并等待写入完成的正确方法是什么?
正如官方文档所说:
如果您想知道数据何时提交,可以添加完成侦听器。 setValue() 和 updateChildren() 都采用可选的完成侦听器,当写入已提交到数据库时调用该侦听器。
这是一个简单的例子:
ref.setValue("I'm writing data to a Firebase database", new Firebase.CompletionListener() {
@Override
public void onComplete(FirebaseError firebaseError, Firebase firebase) {
if (firebaseError != null) {
System.out.println("Data could not be saved. " + firebaseError.getMessage());
} else {
System.out.println("Data saved successfully.");
}
}
});
对于 Kotlin 用户,你可以使用这个
firebaeRef.setValue("your_value", { error, ref ->
//setValue operation is done, you'll get null in errror and ref is the path reference for firebase database
})
这里, firebaeRef
是对设置值的节点/子节点的引用,而your_value
是要设置的值。
只需将您的代码放在 try catch 块中,然后在 Toast 中查看您的错误
btn.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
EditText t=findViewById(R.id.edittext);
String data=t.getText().toString();
try {
ref.setValue(data);
Toast.makeText(MainActivity.this, "Inserted", Toast.LENGTH_SHORT).show();
}catch (Exception e){
Toast.makeText(MainActivity.this, ""+e.getMessage(), Toast.LENGTH_SHORT).show();
}
}
});
您可以考虑为每个可能的返回结果添加侦听器。
ref.child(user.getUid()).setValue(true)
.addOnFailureListener {
print("Update failed: $it")
}.addOnCanceledListener {
print("Update canceled")
}.addOnSuccessListener {
print("Update completed ")
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.