Swift - Firebase search in database

后端 未结 1 1977
天命终不由人
天命终不由人 2020-12-13 07:42

I search for users while typing. However at the end it returns every users. I don\'t know why exactly this happens. It seems alright

 class func findUsers(te         


        
相关标签:
1条回答
  • 2020-12-13 08:13

    You are using queryStartingAtValue. From the documentation:

    The FIRDatabaseQuery instance returned by queryStartingAtValue:childKey will respond to events at nodes with a value greater than startValue, or equal to startValue and with a key greater than or equal to childKey.

    So keep in mind that if you search for the name of an user it will give all the users that have name greater in alphabetic order than the given one. You need to set a queryEndingAtValue to limit the query range.

    ref.child("Users").queryOrderedByChild("name").queryStartingAtValue(text).queryEndingAtValue(text+"\u{f8ff}")
    

    Firebase legacy documentation is such a good resource to understand on how firebase handle queries. There you will find:

    The f8ff character used in the query above is a very high code point in the Unicode range. Because it is after most regular characters in Unicode, the query matches all values that start with a b.

    You might also get interested in Elasticsearch. Flashlight is a node service that integrates elasticsearch and firebase.


    Update:

    As pointed out in the comments this won't work if the string you are searching for has upper case characters. The solution in this case is to have an additional field in the object with the info you are searching all in lower case. So if you have Satoshi Nakamoto as name you would save an additional nameSearch property with satoshi nakamoto.

    And finally make sure your searching string is in lower case too.


    There is a few other problems with your code.

    • You are setting an observer. It will trigger the callback anytime your data changes so you should be resetting the users array inside the callback so you don't have duplicated and dirty data.

    • Your function won't return the users with the data since firebase call is async. When you call return users you won't have the users array populated. I recommend you using self.users = users instead of returning it in the function. Otherwise, if you want to proceed with the current approach and return it, you should set a completion handler.


    class func findUsers(text: String)->Void{
        ref.child("Users").queryOrderedByChild("name").queryStartingAtValue(text).queryEndingAtValue(text+"\u{f8ff}").observeEventType(.Value, withBlock: { snapshot in
            var user = User()
            var users = [User]()
            for u in snapshot.children{
                user.name = u.value!["name"] as? String
                ...
                users.append(user)
            }
            self.users = users
        })
    }
    
    0 讨论(0)
提交回复
热议问题