Firebase DocumentReference.update is deleting the document - firebase

I have flutter code that I have been using for a while that I use to perform crud operations on my firestore documents. I have one situation where an update appears to be deleting a document. I have put a breakpoint in my code just before the update and hold a reference to the document in the firestore console. As soon as the update runs, the document is removed from firestore. Does this make sense? Is there any condition that would cause a document to be deleted when invoking a DocumentReference.update? Here is a snippet of my code showing the update I am trying to perform:
Future<void> updateInMyCartIndicator(
ShoppingListItem shoppingListItem) async {
logger.d("FSShoppingListItemHelper:updateInMyCartIndicator - ENTRY");
try {
CollectionReference shoppingListItemCollection =
FirebaseFirestore.instance.collection('shopping_list_items');
QuerySnapshot shoppingListQuery = await shoppingListItemCollection
.where("id", isEqualTo: shoppingListItem.id)
.get();
final DocumentReference docRefShoppingListItem =
shoppingListItemCollection.doc(shoppingListQuery.docs[0].id);
await docRefShoppingListItem
.update({'in_my_cart': shoppingListItem.inMyCart});
logger.d(
"FSShoppingListItemHelper:updateInMyCartIndicator - Update complete");
} catch (e) {
logger.d("FSShoppingListItemHelper:updateInMyCartIndicator - Exception");
print(e.toString());
}
}

I have tried to reproduce this behavior and no matter how did I update a document (empty HashMap as argument, null fields, etc..) it was not getting deleted. As such the most likely scenario is that the document gets deleted somewhere else in your code, probably as an unintended side effect.

Thanks for the response. I was able to get past this. Honestly, all I did was kill the simulator and my ide and the deleting stopped. I can’t explain why it was happening, but it has gone away.

Related

How to create a document if the document doesn't exist or else don't do anything?

I Wanted To Ask If It Is Possible To Make A New Document With A UID If It DOESN'T Exist But if it exists NOT To Do Anything (and if possible return an error) In Firestore. (In Modular Javascript)
And If It Is Possible How?
Note: I Already Read This Question:StackOverFlow 46888701 But It Doesn't Fit My Requirements because after creating the document I want to be able to update it too.
Edit: I Wanted To Know Without Using getDoc because when i use it acts like a read and i don't want to spend lots of my no of reads from my limit.
You should first try to get the document and check if it exists then proceed to your document set/update. See sample code below:
import { doc, getDoc } from "firebase/firestore";
const docRef = doc(db, "<collection>", "<UID>");
const docSnap = await getDoc(docRef);
if (docSnap.exists()) {
console.log("Document exist!");
// Throws an error.
throw new Error('Document Exist!');
} else {
await setDoc(docRef, {
// Document Data
});
}
For more relevant information, check out these documentations:
Get a document
Update a document
Set a document
Edit:
If you don' t want to use getDoc then you have the option to use updateDoc, it will produce an error but you can still execute a setDoc method on the catch method. On this approach, you're doing a fail-safe practice that you're responding in the event of failure. See code below:
const docRef = doc(db, "<collection>", "<UID>");
// Produces error log if no document to update
updateDoc(docRef, {
// document data
})
.catch((error) => {
// console.log(error);
setDoc(docRef, {
// document data
});
});
According to the documentation, an update is just a write operation:
Charges for writes and deletes are straightforward. For writes, each set or update operation counts a single write.
We have established that an update is just a write operation (there's no reading involved). A write is a change in a document, since you're not changing anything because the document didn't exist then you won't be charged at all.
In web version 9, the function that can help you create a document is named setDoc(), which creates or overwrites a document at a specific document reference.
How to create a document if the document doesn't exist or else don't do anything?
If you want to achieve that, you have to check if the document already exists. If it doesn't exist, create it using setDoc(), otherwise, take no action, but do not use the updateDoc() function in this case.
Remember that the updateDoc() function helps only when you want to update some fields of a document without overwriting the entire document. If the document doesn't exist, the update operation will fail.
Edit:
According to your edited question, please note that there is no way you can know if a document exists, without checking it explicitly. You can indeed not do that check, but you'll end up overwriting the document over and over again. Please also note, that a write operation is more expensive than a read operation. So that's the best option that you have.

Firebase Firestore Data Not Visible Issue

I ran into issue where Firestore is not reflecting data on client.
Lets say when I create cart manually from Firebase Console it reflects on client side but when I create Cart from client side it does not reflects, although a empty card appears but its null. Assist me on this
Firestore Rules are Public
Data Calling Method
public async Task<ObservableCollection<T>> GetCollection(string collection)
{
var tcs = new TaskCompletionSource<ObservableCollection<T>>();
await DataStore.Collection(collection).Get()
.AddOnCompleteListener(new OnCollectionCompleteListener<T>(tcs));
return await tcs.Task;
}
Thanks
I resolved this issue on my own. While working with Firestore, I understood that if you keep any field null in Firestore, the data inside the document will not be visible. So make sure to not leave any field empty.

how to where query a collectionGroup in firestore flutter?

I need to query a collectionGroup with where clause and While doing it I stumbled on to a thing.
var payData = FirebaseFirestore.instance.collectionGroup("payment").where("balance", isNotEqualTo: 0);
While executing the above code when I tried to print payData it prints Instance of _JsonQuery. How to access the data inside that variable and what's its structure.
I think the above code is incorrect.
var payData = FirebaseFirestore.instance.collectionGroup("payment").where("balance", isNotEqualTo: 0).getDocuments();
After surfing I got through the above code but VSCode says it's an error in getDocuments()
So, What I need is to print the data that is in the variable for the query I used above.
getDocuments() was deprecated in favor of get() in version 0.14.0 of the cloud_firestore package (Release notes). You need to call this method on your Query, i.e. payData.
The get() method returns a Future, so you can use then() as follows:
FirebaseFirestore.instance
.collectionGroup("payment")
.where("balance", isNotEqualTo: 0)
.get()
.then((QuerySnapshot querySnapshot) {
querySnapshot.docs.forEach((doc) {
print(doc["<name_of_a_field_in_the_doc>"]);
});
});
However, most of the times you will use one of the approaches shown in the FluterFire doc: depending on whether you want to read the data once or listening to changes in realtime you will use a FutureBuilder or a StreamBuilder.

Firebase await error: Some requested document was not found

async function confirmCode() {
try {
data = await confirm.confirm(code);
if(data.additionalUserInfo.isNewUser){
await firestore.collection("Users").doc(auth.currentUser.uid).update({
id:auth.currentUser.uid,
})
}
} catch (error) {
console.log(error)
}
//Error: [firestore/not-found] Some requested document was not found.
When I use this code to create user & also make firestore data of user it returns error.
But if user is already created, this returns wonderful result.
Any helps can I get to successfully create firestore data when new user comes?
From the error message //Error: [firestore/not-found] Some requested document was not found. is seems that you have a problem with the Firestore document you try to update with await firestore.collection("Users").doc(auth.currentUser.uid).update();
One classical problem when using auth.currentUser is that it is possible that the Auth object is not fully initialized and that auth.currentUser.uid is therefore null. As explained in the doc you should either use the onAuthStateChanged() observer or check that auth.currentUser is not null.
It may also happen that the document is not existing for another reason (e.g. you never created it!): since you are calling update() the document must exist, see the doc: "The update will fail if applied to a document that does not exist.".

increment a value in firestore with flutter

hi i am trying to increment a value when clicked the button if data is available in firestore this is my code bloc if you have any suggestion lmk please
int q = 0;
final snapShot = await Firestore.instance.collection('cart').document("LIihBLtbfuJ8Dy640DPd").get();
if(snapShot.exists){
q=q+1;
}
Firestore.instance.runTransaction((Transaction transaction) async {
await transaction.update(
Firestore.instance
.collection("cart")
.document("LIihBLtbfuJ8Dy640DPd"),
{
foodItem.name: {
'itemName': foodItem.name,
'imgUrl': foodItem.imageAssetPath,
'itemPrice': foodItem.price,
'quantity': q,
}
});
});
In November 2021, this worked for me.
FirebaseFirestore.instance.collection('users').doc(currentUser?.id).update({
'bronzeBadges': FieldValue.increment(2),
});
var quantityref = db.collection("cart").document("LIihBLtbfuJ8Dy640DPd");
// Increment the quantity field by 1.
quantityref.update({
"quantity" : firebase.firestore.FieldValue.increment(1)});
If your want to change a value based on the previous one, you have basically two approaches:
Make use of transactions. I see you're doing that but incorrectly, because you're fetching the current value outside of it, and it could change by the moment you run the update, causing data inconsistencies. I don't know about Flutter, but as far as I know, a Transaction in Firebase consists in a read operation followed by one or more write operations, and the value returned from the read will be the very last one and won't be changed before you finish the transaction, so you can be sure you're working with the latest one. I suggest you to read the Transactions docs.
increment method (recommended): See this see this answer for incrementing in Flutter
First of all, you need to get the desired document and its elements to update the document of fields. In your example, it is quantity.
First, get the document:
Firestore.instance
.collection('cart')
.document('documentID')
.get()
.then((DocumentSnapshot ds) {
// use ds, parse ds then access the quantity
});
After doing the job, you need to update the field. Thankfully, there is an updateData function in firestore instance.
db.collection('cart')
.document('documentID')
.updateData({'quantity': someQuantity});
Hope it helps.

Resources