Alejandra Hernandez
Alejandra Hernandez

Reputation: 31

Firebase query documents by popularity(trending) crashes. Swift

Hi I'm trying to fetch some posts by their popularity, I need them to be posts from this month and to be ordered by the number of saved.

  func fetch() {
    let query = Firestore.firestore().collection("posts").whereField("timestamp", isGreaterThanOrEqualTo: Date().ThisMonth).order(by: "Likes", descending: true)
        
        query.getDocuments { snapshot, error in
            if error != nil {
               print(error?.localizedDescription as Any)
               return
            }
            guard let documents = snapshot?.documents else { return }
            let data = documents.compactMap({ try? $0.data(as: Post.self) })
            self.posts.append(contentsOf: data) 
        }
    }

But when I run the code I get the following:

*** Terminating app due to uncaught exception 'FIRInvalidArgumentException', reason: 'Invalid query. You have a where filter with an inequality (notEqual, lessThan, lessThanOrEqual, greaterThan, or greaterThanOrEqual) on field 'timestamp' and so you must also use 'timestamp' as your first queryOrderedBy field, but your first queryOrderedBy is currently on field 'Likes 'instead.' terminating with uncaught exception of type NSException

I already tried to do it this way but it still won't let me:

func fetch() {
    let query = Firestore.firestore().collection("posts").order(by: "timestamp", descending: true).whereField("timestamp", isGreaterThanOrEqualTo: Date().ThisMonth).order(by: "Likes", descending: true)
    query.getDocuments { snapshot, error in
            if error != nil {
                print(error?.localizedDescription as Any)
                return
            }
        
        guard let documents = snapshot?.documents else { return }
        let data = documents.compactMap({ try? $0.data(as: Post.self) })
        self.posts.append(contentsOf: data)
    }
}

Is there a way to order the posts in this way? What I want is to order them by popularity but only the posts of this month, not all the posts

Thanks!

Upvotes: 1

Views: 146

Answers (1)

Mises
Mises

Reputation: 4623

Error says that you have wrong field name isGraterThenOrEqualTo: it should be greaterThanOrEqual: and bad order of .order() method. Try bellow example.

Get all doc created in this month

let query = Firestore.firestore().collection("posts")
   .whereField("timestamp", greaterThanOrEqual: Date().ThisMonth)

Then you must sort documents on client side by likes. It is becouse if you have whereField("timestamp", greaterThanOrEqual: Date().ThisMonth) with a range you have to first order by this field. And after that if you order with another field it only will work on items where timestamp is exacly same in both docs and will impact only those two docs.

This is way you can sort in JavaScript

   posts.sort((a,b) => b.likes - a.likes)

Upvotes: 0

Related Questions