gpt4 book ai didi

java - Firestore,交易已经完成

转载 作者:行者123 更新时间:2023-11-29 19:01:24 24 4
gpt4 key购买 nike

我有 2 个集合,“用户”和“用户名”。我想单独保存所有使用过的用户名及其关联的 uid,这样我就可以快速访问它们,而不是查询成千上万的用户。它应该用于将来的用户名选择。为了防止用户使用与其他人相同的用户名,我想我会在一个事务中完成它,我首先检查用户名是否存在,如果不存在,我添加它并更新“用户”中的用户名属性。这就是我到目前为止所拥有的:

db.runTransaction(new Transaction.Function<Void>() {
@Override
public Void apply(final Transaction transaction) throws FirebaseFirestoreException {

db.collection("usernames").document(editTextUsername.getText().toString()).get().addOnCompleteListener(new OnCompleteListener<DocumentSnapshot>() {
@Override
public void onComplete(@NonNull Task<DocumentSnapshot> task) {
if (!task.getResult().exists()) {
transaction.update(sfDocRef, "username", editTextUsername.getText().toString());

Map<String, Object> usernameMap = new HashMap<>();
usernameMap.put("uid", FirebaseAuth.getInstance().getUid());

db.collection("usernames").document(editTextUsername.getText().toString()).set(usernameMap);
}
}
});

return null;
}
}).addOnSuccessListener(new OnSuccessListener<Void>() {
@Override
public void onSuccess(Void aVoid) {
Log.d(TAG, "Transaction success!");
}
})
.addOnFailureListener(new OnFailureListener() {
@Override
public void onFailure(@NonNull Exception e) {
Log.w(TAG, "Transaction failure.", e);
}
});

如果我用这段代码运行我的应用程序,我会得到这个异常

java.lang.IllegalStateException: Transaction has already completed.
at com.google.android.gms.internal.zzeof.zzbb(Unknown Source)
at com.google.android.gms.internal.zzeof.zza(Unknown Source)
at com.google.firebase.firestore.Transaction.zza(Unknown Source)
at com.google.firebase.firestore.Transaction.update(Unknown Source)
at com.lala.rerere.ProfileAssistant.FragmentUsernameAsk$7$1.onComplete(FragmentUsernameAsk.java:179)
at com.google.android.gms.tasks.zzf.run(Unknown Source)
at android.os.Handler.handleCallback(Handler.java:751)
at android.os.Handler.dispatchMessage(Handler.java:95)
at android.os.Looper.loop(Looper.java:154)
at android.app.ActivityThread.main(ActivityThread.java:6776)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1520)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1410)

所以我认为在我的查询进入 onCompleteListener 之前事务返回 null,可能是因为它是一个异步调用。现在我尝试在查询末尾添加 getResult()。好吧,它奏效了!但是我收到了一个丑陋的警告

java.lang.IllegalStateException: Task is not yet complete
at com.google.android.gms.common.internal.zzbq.zza(Unknown Source)
at com.google.android.gms.tasks.zzn.zzbjk(Unknown Source)
at com.google.android.gms.tasks.zzn.getResult(Unknown Source)
at com.lala.rerere.ProfileAssistant.FragmentUsernameAsk$7.apply(FragmentUsernameAsk.java:181)
at com.lala.rerere.ProfileAssistant.FragmentUsernameAsk$7.apply(FragmentUsernameAsk.java:165)
at com.google.firebase.firestore.zzf.call(Unknown Source)
at com.google.android.gms.tasks.zzo.run(Unknown Source)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1133)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:607)
at java.lang.Thread.run(Thread.java:762)

在我的场景中最好的方法是什么?

最佳答案

在这种情况下不需要使用事务。如果我们知道在我们的应用程序中有可能两个用户可以同时进行相同的写入操作,我们就会使用transactions。我们将使用事务,以便不同用户在同一时间进行的每次写入都在不同的执行线程中进行。这就是我们使用事务来避免数据不一致的原因。

在您的情况下,您只需要使用 get() 调用并使用 exists() 方法即可!

关于java - Firestore,交易已经完成,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48989103/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com