# HG changeset patch
# User Goffi <goffi@goffi.org>
# Date 1562088975 -7200
# Node ID 4bac4e73466620ad8514a31fd830474303e75855
# Parent  97a1faca8f583002d83956e073618a30a7f60b5b
core (xmpp): set message timestamp on message reception:

message timestamp was set during the parsing, but this could lead to misordering as async
calls are done before message is parsed (so a variable delay could happen before the
timestamp was set). This patch workaround this by setting timestamp as soon as message is
received (in onMessage).

diff -r 97a1faca8f58 -r 4bac4e734666 sat/core/xmpp.py
--- a/sat/core/xmpp.py	Tue Jul 02 09:09:04 2019 +0200
+++ b/sat/core/xmpp.py	Tue Jul 02 19:36:15 2019 +0200
@@ -17,6 +17,10 @@
 # You should have received a copy of the GNU Affero General Public License
 # along with this program.  If not, see <http://www.gnu.org/licenses/>.
 
+import sys
+import time
+import calendar
+import uuid
 from functools import partial
 from sat.core.i18n import _
 from sat.core.constants import Const as C
@@ -37,10 +41,6 @@
 from sat.memory import persistent
 from sat.tools import xml_tools
 from zope.interface import implements
-import time
-import calendar
-import uuid
-import sys
 
 log = getLogger(__name__)
 
@@ -1014,13 +1014,22 @@
 
         # delay and timestamp
         try:
+            received_timestamp = message_elt._received_timestamp
+        except AttributeError:
+            # message_elt._received_timestamp should have been set in onMessage
+            # but if parseMessage is called directly, it can be missing
+            log.debug(u"missing received timestamp for {message_elt}".format(
+                message_elt=message_elt))
+            received_timestamp = time.time()
+
+        try:
             delay_elt = message_elt.elements(delay.NS_DELAY, "delay").next()
         except StopIteration:
-            data["timestamp"] = time.time()
+            data["timestamp"] = received_timestamp
         else:
             parsed_delay = delay.Delay.fromElement(delay_elt)
             data["timestamp"] = calendar.timegm(parsed_delay.stamp.utctimetuple())
-            data["received_timestamp"] = unicode(time.time())
+            data["received_timestamp"] = received_timestamp
             if parsed_delay.sender:
                 data["delay_sender"] = parsed_delay.sender.full()
 
@@ -1047,6 +1056,7 @@
 
     def onMessage(self, message_elt):
         # TODO: handle threads
+        message_elt._received_timestamp = time.time()
         client = self.parent
         if not "from" in message_elt.attributes:
             message_elt["from"] = client.jid.host
@@ -1079,7 +1089,7 @@
 
     def bridgeSignal(self, __, data):
         try:
-            data["extra"]["received_timestamp"] = data["received_timestamp"]
+            data["extra"]["received_timestamp"] = unicode(data["received_timestamp"])
             data["extra"]["delay_sender"] = data["delay_sender"]
         except KeyError:
             pass