1

I am using firebase for real time chat. But now I am facing problem in data sorting, like in web whatsapp we get user with latest time displayed on top same way I want to display.

enter image description here

This is how i save data in firebase :

                                var rootRef = firebase.database().ref();
                                var storesRef = rootRef.child('messages');
                                var adminref = storesRef.child(username);
                                var newStoreRef = adminref.push();
                                newStoreRef.set({
                                    "file": "",
                                    "id": senderid,
                                    "message": chatdata,
                                    "time": chattime,
                                    "timestamp" : nowTimestamp,
                                    "name": senderName
                                });

and then i retrive data like this

   $(document).ready(function(){

        var rootRef = firebase.database().ref().child("users");

        rootRef.on('value', function(snapshot) 
        {
            snapshot.forEach(function(childSnapshot) 
                {
                    console.log(childSnapshot);
                    var name = childSnapshot.key;
                    var childData = childSnapshot.val();
                    //console.log(childData);

                    if($('#'+name).length) {
                        return;
                    } else {

        var rootRef = firebase.database().ref().child("messages").child(name);
                            var html = '';
                            var username = name ;
                            var userid = childData.id;

                            rootRef.limitToLast(1).orderByChild('timestamp').on('child_added', function(snapshot) 
                            {
                                     var name = snapshot.key;
                                     var childDatamsg = snapshot.val();
                                     $('#'+username).remove();
                                     //document.getElementById(username).remove();
                                     $("#users").prepend('<div class="row sideBar-body userchat" data-id="'+userid+'" onclick="showDiv()" id="'+username+'"><div class="col-sm-3 col-xs-3 sideBar-avatar"><div class="avatar-icon"><img src="http://chat.synetal.com/assets/user2.jpg"></div></div><div class="col-sm-9 col-xs-9 sideBar-main"><div class="row"><div class="col-sm-8 col-xs-8 sideBar-name-align" id="chat"><span class="name-meta">'+ username +'</span></div><div class="col-sm-4 col-xs-4 pull-right sideBar-time-align"><span class="time-meta pull-right">'+childDatamsg.time+'</span></div><div class="col-sm-10 col-xs-10 sideBar-message-align"><span class="sideBar-last-msg">'+childDatamsg.message+'</span></div><div class="col-sm-2 col-xs-2 pull-right sideBar-time-align"><span class="sideBar-msg-counter pull-right" style="">1</span></div></div></div></div>');
                                     // $(this).attr('data-id').remove();
                            });
                       }
                });
        }); 
});

enter image description here

I want to sort data from timestamp but in result i am getting the first message but i want last message which is sorted acc to timestamp

Renaud Tarnec
  • 79,263
  • 10
  • 95
  • 121
coder_B
  • 110
  • 11

1 Answers1

1

You need to store your date/time as a timestamp, i.e. the time since the Unix epoch, in milliseconds.

With the Realtime Database you can use ServerValue.TIMESTAMP, as follows:

var messagesRef = firebase.database().ref(....);
messages.push({
  name: .....,
  ....
  timestamp: firebase.database.ServerValue.TIMESTAMP
});

However, since you want to sort your messages with the "latest (message) displayed on top" (i.e. in reverse chronological order) you need to store the value of the timestamp multiplied by -1.

To do so you cannot use ServerValue.TIMESTAMP because you cannot make any math operation on this value that is populated in the back-end by the server. You should then use some standard JavaScript, as follows:

var messagesRef = firebase.database().ref(....);
var nowTimestamp = (new Date().getTime()) * -1;
messages.push({
  name: .....,
  ....
  timestamp: nowTimestamp
});

Then, to display the messages in the correct order in your app, you have to use orderByChild() as explained in the documentation, here: https://firebase.google.com/docs/database/web/lists-of-data#sort_data

Renaud Tarnec
  • 79,263
  • 10
  • 95
  • 121
  • var nowTimestamp = (new Date().getTime()) * -1; this is giving -1556283437968 so this value will store in database and i have to sort using this value? – coder_B Apr 26 '19 at 12:59
  • @coder_B Exactly, that's it! – Renaud Tarnec Apr 26 '19 at 13:07
  • 1
    hey thank you so much it worked – coder_B Apr 26 '19 at 13:13
  • 1
    Glad I could help you! An additional remark: As explained in the doc (https://firebase.google.com/docs/reference/js/firebase.database.Reference#push) "the unique keys generated by `push()` are ordered by the current time, so the resulting list of items will be chronologically sorted.". However, since you want to sort in reverse chronological order you need to do as presented in the anwser. – Renaud Tarnec Apr 26 '19 at 13:16
  • hey i think its not working, can you help me out? – coder_B Apr 27 '19 at 07:49
  • You should not use `limitToLast` IMO. Just do something like: `var anotherRootRef = firebase.database().ref().child('messages').child(name); anotherRootRef.orderByChild('timestamp').on('child_added', function(snapshot) { var name = snapshot.key; var childDatamsg = snapshot.val(); console.log(childDatamsg.message); });` – Renaud Tarnec Apr 27 '19 at 09:16
  • using this we will get latest message of the user ? – coder_B Apr 27 '19 at 11:06
  • i tired this but whenever page is refreshed this does not show list in shorted order. and yes username i.e; raja1234 love123 are coming from another table users and there messages are coming from messages tables – coder_B Apr 27 '19 at 11:09
  • Try first to use once() to get your username list and then use on() for the messages of the selected user. I would not do that in one function. You may ask a new question on Stack Overflow with all the details. – Renaud Tarnec Apr 27 '19 at 11:34