0

I have one Android project where I need to query nearby items & these items should be sorted by time.

Basically, I need docs that are in 100KM. Sorted by time (Field).

So I have checked Firestore docs for this & I got solution (Add geoHash to docs & then query them by geoHasBounds) But there is an issue what if there are 1k docs in 100km then it will load all which is not good, so how can I limit those different queries & gets only 25-30 docs then next 25-30 docs ??

In short, this is what I need-

How can I query the latest 25 docs in 100KM radius & when the user scroll down the next 25 docs?

this is my code of query-

List<GeoQueryBounds> bounds = GeoFireUtils.getGeoHashQueryBounds(center, radiusInM);
    final List<Task<QuerySnapshot>> tasks = new ArrayList<>();
    for (GeoQueryBounds b : bounds) {
         Query newQuery = itemQuery.orderBy("geoHash").startAt(b.startHash).endAt(b.endHash);

        tasks.add(newQuery.get());
    }

    // Collect all the query results together into a single list
    Tasks.whenAllComplete(tasks).........

1 Answers1

1

What you are looking for is called pagination. I have answered a question here on Stackoverflow, where I have explained a recommended way in which you can paginate queries by combining query cursors with the "limit() method". I also recommend you take a look at this video for a better understanding.

If you are willing to try Paging 3 library, please see below an article that will help you achieve that.

Edit:

The Tasks.whenAllComplete() method:

Returns a Task with a list of Tasks that completes successfully when all of the specified Tasks complete.

So you can then simply convert each object to a type of object that you need and paginate that list accordingly. Unfortunately, this implies getting all the objects in the first place. Otherwise, you can divide those queries into separate queries and treat them accordingly, by using separate paginantion.

Alex Mamo
  • 130,605
  • 17
  • 163
  • 193
  • Sorry, I already know this but issue is geoQueries are not simple. Basically If you click on link of solution in question you will see that there are multiple queries for a radius. – Ashok Kumar Choudhary Apr 21 '21 at 10:56
  • You can paginate those queries in the same way I have explained in my answer. The key is to pass to the startAfter() method, into the next Query, the last DocumentSnapshot that is visible. – Alex Mamo Apr 21 '21 at 11:16
  • Yeah definitely, I can limit but issue is I don't know how many documents each query is going to return, I need to limit 25 docs for all those queries (together). Suppose I get 5 geoHashBounds then if I putt limit of 5-5 to each & then suppose 4 bounds inly has 1-1 docs & 5th one has 20 docs then I will get only 9 docs (1+1+1+1+5) because no query will return more then 5 docs – Ashok Kumar Choudhary Apr 21 '21 at 13:39
  • Yes, that correct. You cannot know in advance how many results your query may return. But it doesn't really matter. You can request pages of data of a certain size. So in that case you should create a single query to get the location in a radius of 100KM and then sort the result according to a Timestamp, for getting the latest elements. Don't also forget to create an [index](https://stackoverflow.com/questions/63663454/geofirestore-is-it-possible-to-combine-the-methods-near-and-where-in-a-geo) – Alex Mamo Apr 21 '21 at 14:22
  • I don't think there is a way to get all docs in single query you have to query docs for all geoHash Bounds. I don't know why I am not able to understand can you please provide code ? I will be very thankful of you – Ashok Kumar Choudhary Apr 21 '21 at 18:50
  • You should provide the exact queries you intend to perform, so I can understand better what is the exact data you want to achieve. Please also edit your question and add your database structure as a screenshot. – Alex Mamo Apr 21 '21 at 19:07
  • ANd I have added a new edit. Please check. Is it more clear now? – Alex Mamo Apr 22 '21 at 06:02
  • I am glad that you tried to help me. but still I am not able to find exact solution & Problem is that in your answer you have said that "Unfortunately, this implies getting all the objects in the first place" . I can not do that because there coud be 5000-10000 docs. And If I place limits on each query then there will be so many problems like- how I know which query returned how many docs & how many docs are still there in query after increasing limit ? – Ashok Kumar Choudhary Apr 28 '21 at 10:31