2

I have data in Firebase as:

video 1
 - lang: en

video 2
 - lang: zh

video 3
 - lang: fi
....

I want to query and return list of objects that has lang value as either en or zh.

What I found is to use

  orderByChild: "lang",
  equalTo: "en"

But this query returns objects for only "en", how to return for either "en" or "zh"?

Doug Stevenson
  • 297,357
  • 32
  • 422
  • 441
Xi Xiao
  • 953
  • 1
  • 12
  • 28
  • 1
    There is no logical "or" for Firebase queries. Instead, you can do two queries, then merge the results on the client. – Doug Stevenson Aug 30 '17 at 19:15
  • This seems unscalable. What if I have 12 languages and user wants to retrieve 11 out of 12? Shall I do 11 queries and merge? – Xi Xiao Aug 30 '17 at 19:31
  • 1
    Yes. I'd recommend in that case storing an inverted index, instead of a query. So `/languages/en/video1: true`. With that, each language is just a lookup. And doing multiple lookups is faster than you may think, because the requests are pipelined. See http://stackoverflow.com/questions/35931526/speed-up-fetching-posts-for-my-social-network-app-by-using-query-instead-of-obse/35932786#35932786 – Frank van Puffelen Aug 30 '17 at 23:42
  • @FrankvanPuffelen one unique feature I learned about Firebase was that it welcomes data duplication for the purpose of faster data retrieving. Now it seems the pipeline feature enables in-parallel requests returning fast. If it is the case, do we still need to take effort to consider where data should be duplicated? – Xi Xiao Sep 06 '17 at 06:42

1 Answers1

3

Because Firebase is a NoSQL database, there is no WHERE clause that sounds like this:

SELECT * FROM Video WHERE lang='en' OR lang='zh'

Unfortunately, Firebase does not allow multiple queries that can serve your purpose. What can you do instead is to use an ordering query which is equal to the desired language on the same reference twice. These queries should look like this:

.yourRef.orderByChild("lang").equalTo("en");
.yourRef.orderByChild("lang").equalTo("zh");

Now, you can combine the result of both queries and display them on the user side. If you need to query against your database by more then two languages then I suggest you change the structure of your database a little bit. You'll need to create another node named languages in which you can add the available videos for each particular language. The new structure should look like this:

Firebase-root
    |
    --- languages
           |
           --- en
           |    |
           |    --- video1: true
           |
           --- zh
           |    |
           |    --- video2: true
           |
           --- fi
                |
                --- video3: true
                |
                --- video4: true

In this way, you can add a listener to the desired language and see all the available videos. As Frank said, it will be even faster than normal queries.

Alex Mamo
  • 130,605
  • 17
  • 163
  • 193
  • Thanks Alex! I need to make sure I got this part correctly => `you can add a listener on the desired language and see all the available videos`. Do you mean, when I need both `en` and `zh` I should go through items under both`languages/en` and `languages/zh`, then fetch corresponding data from `videos` using sequential query said by Frank? – Xi Xiao Aug 31 '17 at 18:47