This question already has answers here:
Firestore: How to get random documents in a collection
(15 answers)
Closed 1 year ago.
Here is my current DB structure, I have a collection store all the survey question documents, and under each question doc, it has an Answers sub-collection that stores all the users who answered the question. The challenging part is that how do I randomly load 8 questions that are not answered by a specific user, without query the entire question collection? What is the least costly approach? Any suggestions are helpful. Thanks
Below are my Db structure:
The best option that you have is to store all question IDs you have in your application into a document in an array data type. If you are worried about the 1 MiB limitation, then you should consider sharding the IDs over multiple documents.
Every time a user answers 8 questions, add those IDs in an array in the User object.
The challenging part is that how do I randomly load 8 questions that are not answered by a specific user, without query the entire question collection?
To load 8 random questions, all you have to do is to download both arrays and remove from the question IDs all the IDs the users already answered. In this way, you'll only have an array of question IDs the user didn't answer. Get other 8 IDs, add them to the User object, and so on.
Remember also that you also need to keep the data in sync, meaning that each time you add a new question, add to the array as well. Do it for the delete operation too.
You should store the ids of the questions the user has answered in the user data. Then you can just query enough docs that don't match those ids by using a where clause. https://firebase.google.com/docs/firestore/query-data/get-data#get_multiple_documents_from_a_collection
Related
Closed. This question does not meet Stack Overflow guidelines. It is not currently accepting answers.
We don’t allow questions seeking recommendations for books, tools, software libraries, and more. You can edit the question so it can be answered with facts and citations.
Closed 3 months ago.
Improve this question
Does anyone have good ideas about what kind of a data model makes sense in Firestore for time dependent data?
I have a lot of event data that I would like to store in Firestore and then run an analysis on it
Each event has a timestamp and I would like to run the aggregated analysis for example for 1 day of data, 7 day of data, X days of data, 1 month, X months, etc
How should this be setup in firestore, 7 days of event data is already a lot of data that and I can't return it to the client and make the analysis there.
If I aggregate some predefined set of days beforehand in firestore it is then locked to only those days and you can't choose an arbitrary amount of days.
I would also need to keep updating the aggregated data every time there is new data
Any help much appreciated!
As I understand you're looking to perform a query similar to:
SELECT hits, COUNT(*) FROM event_type_api GROUP BY hits WHERE start_date > TODAY - X
Firestore is a NoSQL database, but that doesn't mean that you cannot know the number of documents in a query. You cannot in SQL terms, but you can count them. It's a little costly to read all documents in a collection to only have the number of documents. That's why you need to call count(). As you already mentioned, there is also no "GROUP BY" present in Firestore. However, we can achieve almost the same thing.
Assuming that you'll create a collection called "hits" in which you store documents that have a field of type timestamp, then you can perform the following query:
val queryByTimestamp = db.collection("hits").whereGreaterThan("timestamp", TODAY - X)
If you want to know how many documents the query returns, you need to call count() like this:
val numberOfDocuments = queryByTimestamp.count()
The last thing is related to grouping. As mentioned before, Firestore doesn't offer any aggregation queries such as grouping. However, there are two solutions for this use case. You can get all the documents in the hits collection, and then group them in your application code by whatever fields you need. Or you can create separate collections of pre-grouped documents to satisfy your needs. The latter is the recommended approach. And remember, that duplicating data is a quite common practice when it comes to NoSQL databases.
This question already has answers here:
What are the benefits of using a root collection in Firestore vs. a subcollection?
(2 answers)
Closed 7 months ago.
I am working on a quiz game, where players have to answer questions of different categories (sports, music, .....). Right now, I have two different ideas how to store these categories /questions in Firestore:
Creating a new Root-level collection for each category. Every document in this collection would define a question of that category. Stcuture would look like this:
user_collection
user_1_document
user_2_document
user_X_document
music_questions_collection
music_questions_1_document
music_questions_2_document
music_questions_X_document
sports_questions_collection
sports_questions_1_document
sports_questions_2_document
sports_questions_X_document
Creating ONE Root-level collection and create a document inside this collection for each category, where each document contains a subcollection of questions:
user_collection
user_1_document
user_2_document
user_X_document
category_collection
music_document
music_question_subcollection
music_question_document_1
music_question_document_2
music_question_document_3
sports_document
sports_question_subcollection
sports_question_document_1
sports_question_document_2
sports_question_document_3
I have already read about some advantages and limitations of subcollections and root-collections, but have not found enough information regarding read-costs and speed for this specific use case. Can anyone give me some information about drawbacks and advantages of the two listed approaches.
I have not found enough information regarding read-costs and speed for
this specific use case. Can anyone give me some information about
the drawbacks and advantages of the two listed approaches?
In terms of "read-costs and speed", the two approaches are equivalent: using a root collection or a sub-collection is exactly the same.
As a matter of fact, from a technical perspective, a root collection and one of its sub-collections are not at all related to each other. They just share a part of their path but nothing else.
So, since you store the same documents in either a root collection or a sub-collection (i.e. same number of docs in each category collection and same field structure for these docs), there is no difference.
I have quiz game and I want to add 1000 questions on firebase firestore and I have thousands of users in my game and every user has special id.
What is the best way to know if the user answered this question before or no?
Should I add user id inside every question who answered it or there is the another way?
I want build data structure logically for reduce consumptionmy read limit on firestore.
The two most common solutions I can quickly think of:
Create a single top-level collection answers, where you store all answers for all users. In that collection use the combination of UID and question ID to name each document, so that you can check if a document /answers/$uid+$questionID exists.
Create a top-level collection users in which each UID represents a user. Under each UID document create sub-collection answers, where you use the question ID to name the documents. Now you can check for each user if they answered a specific question, by checking /users/$uid/answers/$questionId.
Neither of these is pertinently better than the other, and they typically allow for similar use-cases. I'd usually pick the second structure simply because it results in a more natural distribution of the data, but it's s pretty small preference in practice.
This question already has answers here:
Can Firestore update multiple documents matching a condition, using one query?
(8 answers)
Updating documents in Cloud Firestore based on a query
(2 answers)
Closed 2 years ago.
i need to update a field in some documents of my users collection, after another document changes, only if those users meet a required criteria. I know i can do querys filtering for the criteria but this would download the documents (i dont need this) i just need to update the field changed in the first document.
is this even posible or should i look for another aproach?
You must know the full path of every document in order to update it. There is equivalent of SQL's "update where" type queries that will both query and update the matching rows. You will need to query first, iterate the results, and update what you need from that set.
This question already has answers here:
How to list subcollections in a Cloud Firestore document
(4 answers)
Closed 5 years ago.
I am reading the docs and see that FireStore allows sub-collection. Which is great. Consider the following example as mentioned here int he docs.
As shown in the docs I can get the reference to the last doc as follows
var messageRef = db.collection('rooms').doc('roomA')
.collection('messages').doc('message1');
In the above example, the id's for docs and collections are typed in.
There are cases when id's are dynamically generated. In such a case how can I know how many collections a doc has? Or whether a doc has any sub-collections. How can I do that?
On mobile clients, you can't know how many collections or what collections a document has. There is just no API for that. You have to know ahead of time what collections may exist for a document, or accept that a query on an unknown subcollection may return no documents.