Following is the schema of my Firebase Realtime Database:
Chats node
- chats
- chatId
- chatId
- adminUserId
- chatSubject
- chatIconUrl
- chatCretionDate
- lastUpdated
- chatId
User chats node
- user_chats
- userId
- chatId: true
- userId
What I want to do:
What I want to do is to present a list of all chats a user is subscribed to in the ChatListFragment
of my app and observe it for changes, e.g., new chat added, any chat removed, a change in chatSubject
, chatIconUrl
, lastUpdated
etc.
What I have done:
Since I've already denormalized the data, the first step would be to retrieve a list of chat ids a given user is subscribed to, and this I can very easily achieve as follows:
FirebaseDatabase.getInstance().getReference("user_chats").child(userId).addValueEventListener()
Next task is to get the complete chat data from chats
node against each of the chat ids retrieved above.
I know that I can't write a query to achieve this because the retrieved chat ids are a random subset out of the hundreds or thousands of total chat ids.
So, I loop through the retrieved chat ids and fire a query for each as follows and collect the retrieved Chat
(A POJO that maps to the fields in chats
node) object one by one in an ArrayList
:
FirebaseDatabase.getInstance().getReference("chats").child(chatId).addValueEventListener()
Here, I've to ensure completeness of data by matching the size of ArrayList<Chat>
with the size of chat ids retrieved from user_chats
node. When both sizes are equal, I supply the ArrayList<Chat>
to the ListAdapter
.
BUT, in addition to above, I also have to deal with the following:
- See why onDataChanged() of the listener attached to each chat id has been called: to supply a new chat snapshot or report changes in an already supplied chat snapshot.
- Remove listener associated with a chat id that the given user is no longer subscribed to.
This becomes even more complicated when I try to do it all in a ViewModel
using LiveData
.
Here are my questions:
Do I really have to go through such a trouble just to compile a list of chats that a user is subscribed to? This is supposed to be the first screen of my app and I can't happen to get past it.
Is there a standard / better way to achieve my objective with the same data structure?
Do I need to make further changes in my data structure to achieve my objective? What I'm thinking is to expand the
user_chats
node by adding the same fields thatchats
node has. That seems pretty weird though because, first, if there are lets say, 500 members in a chat, there would be 500 ditto copies of the chat inuser_chats
node and second, in case of any update in data, I would be updating the chat info inchats
node and then all the 500 copies inuser_chats
node. That would be ridiculous when we think about how frequently thelastUpdated
field would be updated.
Any help would be really appreciated!