Firebase按顺序获取数据

Rya*_*zzo 4 firebase swift firebase-realtime-database

我正在使用Firebase,直到最近我才按字母顺序获取数据.我从不使用查询,我总是只使用数据快照并逐个排序.最近,数据并不总是按照snapVal的字母顺序排列.我怎么做到这一点,我得到一个按字母顺序排序的snapVal数据,就像它在数据库的快照中一样?

真实示例:有4条消息,id1-id4(按此顺序).他们传达了消息"1" - "4".快照看起来正确.但是snapVal(snapshot.value)看起来像这样:

["id2": {
    DATE = "10/20/16";
    "FIRST_NAME" = first;
    ID = userID;
    "LAST_NAME" = last;
    MESSAGE = 2;
    TIME = "8:12 PM";
}, "id4": {
    DATE = "10/20/16";
    "FIRST_NAME" = first;
    ID = userID;
    "LAST_NAME" = last;
    MESSAGE = 4;
    TIME = "8:12 PM";
}, "id1": {
    DATE = "10/20/16";
    "FIRST_NAME" = first;
    ID = userID;
    "LAST_NAME" = last;
    MESSAGE = 1;
    TIME = "8:12 PM";
}, "id3": {
    DATE = "10/20/16";
    "FIRST_NAME" = first;
    ID = userID;
    "LAST_NAME" = last;
    MESSAGE = 3;
    TIME = "8:12 PM";
}]
Run Code Online (Sandbox Code Playgroud)

快照的样子:

["id1": {
    DATE = "10/20/16";
    "FIRST_NAME" = first;
    ID = userID;
    "LAST_NAME" = last;
    MESSAGE = 1;
    TIME = "8:12 PM";
}, "id2": {
    DATE = "10/20/16";
    "FIRST_NAME" = first;
    ID = userID;
    "LAST_NAME" = last;
    MESSAGE = 2;
    TIME = "8:12 PM";
}, "id3": {
    DATE = "10/20/16";
    "FIRST_NAME" = first;
    ID = userID;
    "LAST_NAME" = last;
    MESSAGE = 3;
    TIME = "8:12 PM";
}, "id4": {
    DATE = "10/20/16";
    "FIRST_NAME" = first;
    ID = userID;
    "LAST_NAME" = last;
    MESSAGE = 4;
    TIME = "8:12 PM";
}]
Run Code Online (Sandbox Code Playgroud)

要获取snapVal,我使用:

if let snapVal = snapshot.value as? [String: AnyObject] {
     // Comes out of order..
}
Run Code Online (Sandbox Code Playgroud)

澄清:

快照(最终结果正确):

Snap (CHAT) {
    id1 =     {
        DATE = "10/20/16";
        "FIRST_NAME" = first;
        ID = userID;
        "LAST_NAME" = last;
        MESSAGE = 1;
        TIME = "8:12 PM";
    };
    id2 =     {
        DATE = "10/20/16";
        "FIRST_NAME" = first;
        ID = userID;
        "LAST_NAME" = last;
        MESSAGE = 2;
        TIME = "8:12 PM";
    };
    id3 =     {
        DATE = "10/20/16";
        "FIRST_NAME" = first;
        ID = userID;
        "LAST_NAME" = last;
        MESSAGE = 3;
        TIME = "8:12 PM";
    };
    id4 =     {
        DATE = "10/20/16";
        "FIRST_NAME" = first;
        ID = userID;
        "LAST_NAME" = last;
        MESSAGE = 4;
        TIME = "8:12 PM";
    };
}
Run Code Online (Sandbox Code Playgroud)

这是print(snapVal.keys)内部的输出if let snapVal = snapshot.value as? [String: AnyObject]:

LazyMapCollection<Dictionary<String, AnyObject>, String>(_base: ["id2": {
    DATE = "10/20/16";
    "FIRST_NAME" = first;
    ID = userID;
    "LAST_NAME" = last;
    MESSAGE = 2;
    TIME = "8:12 PM";
}, "id4": {
    DATE = "10/20/16";
    "FIRST_NAME" = first;
    ID = userID;
    "LAST_NAME" = last;
    MESSAGE = 4;
    TIME = "8:12 PM";
}, "id1": {
    DATE = "10/20/16";
    "FIRST_NAME" = first;
    ID = userID;
    "LAST_NAME" = last;
    MESSAGE = 1;
    TIME = "8:12 PM";
}, "id3": {
    DATE = "10/20/16";
    "FIRST_NAME" = first;
    ID = userID;
    "LAST_NAME" = last;
    MESSAGE = 3;
    TIME = "8:12 PM";
}], _transform: (Function))
Run Code Online (Sandbox Code Playgroud)

我的代码:

  self.firebase.child("Chats").child(chatID).queryOrderedByKey().observeSingleEvent(of: .value, with: { (snapshot) in
                          print(snapshot)
                        if let snapVal = snapshot.value as? [String: AnyObject] {

                            print(snapVal)

                            for c in snapVal {
                                print("checking Message as child")
                                let message = c.value["MESSAGE"] as? String

                                let fn = c.value["FIRST_NAME"] as? String
                                let ln = c.value["LAST_NAME"] as? String

                                let USER_ID = c.value["ID"] as? String

                                if let userID = USER_ID {
                                    if let msg = message {
                                        if let firstName = fn {
                                            if let lastName = ln {
                                                let username = "\(firstName) \(lastName)"
                                                self.addMessage(userID, text: msg, name: username)

                                                print("Message added! \nMessage Info:")
                                                print("User ID: \(userID)")
                                                print("text: \(msg)")
                                                print("Username: \(username)")
                                            } else {
                                                print("LN did not pass")
                                            }
                                        } else {
                                            print("FN did not pass")
                                        }
                                    } else {
                                        print("Msg did not pass")
                                    }
                                } else {
                                    print("User ID did not pass")
                                }
                            }
                          }  
})
Run Code Online (Sandbox Code Playgroud)

Fra*_*len 6

既然你没有共享必要的代码,我会假设你正在做这些事情:

ref!.queryOrdered(byChild: "text").observe(.value, with: { (snapshot) in
    print("\(snapshot.value)")
})
Run Code Online (Sandbox Code Playgroud)

在Firebase位置上执行查询时,将根据查询返回包含项目顺序信息的数据.观察事件时,快照包含键,值和子项的顺序.

但是当您转换请求snapshot.value属性时,所有信息都必须转换为字典.每个孩子的钥匙和价值在这次转换中幸存下来,但有关订购的信息会丢失.

因此,您必须使用children快照的属性以正确的顺序迭代子项:

ref!.queryOrdered(byChild: "text").observe(.value, with: { snapshot in
    for child in snapshot.children {
        print("child \(child)")
    }
})
Run Code Online (Sandbox Code Playgroud)