1515from yowsup .structs import ProtocolTreeNode
1616from .protocolentities import GetKeysIqProtocolEntity , ResultGetKeysIqProtocolEntity
1717from axolotl .util .hexutil import HexUtil
18- from yowsup .env import CURRENT_ENV
1918from axolotl .invalidmessageexception import InvalidMessageException
2019from .protocolentities import EncryptNotification
2120from yowsup .layers .protocol_acks .protocolentities import OutgoingAckProtocolEntity
21+ from axolotl .invalidkeyidexception import InvalidKeyIdException
22+ from axolotl .nosessionexception import NoSessionException
23+ from .protocolentities .receipt_outgoing_retry import RetryOutgoingReceiptProtocolEntity
2224import binascii
2325import sys
2426
@@ -40,6 +42,7 @@ def __init__(self):
4042
4143 self .sessionCiphers = {}
4244 self .pendingMessages = {}
45+ self .pendingIncomingMessages = {}
4346 self .skipEncJids = []
4447
4548 def __str__ (self ):
@@ -101,6 +104,10 @@ def receive(self, protocolTreeNode):
101104 elif protocolTreeNode .tag == "notification" and protocolTreeNode ["type" ] == "encrypt" :
102105 self .onEncryptNotification (protocolTreeNode )
103106 return
107+ elif protocolTreeNode .tag == "receipt" and protocolTreeNode ["type" ] == "retry" :
108+ # should bring up that message, resend it, but in upper layer?
109+ # as it might have to be fetched from a persistent storage
110+ pass
104111 self .toUpper (protocolTreeNode )
105112 ######
106113
@@ -130,6 +137,13 @@ def processPendingMessages(self, jid):
130137
131138 del self .pendingMessages [jid ]
132139
140+ def processPendingIncomingMessages (self , jid ):
141+ if jid in self .pendingIncomingMessages :
142+ for messageNode in self .pendingIncomingMessages [jid ]:
143+ self .onMessage (messageNode )
144+
145+ del self .pendingIncomingMessages [jid ]
146+
133147 #### handling message types
134148
135149 def handlePlaintextNode (self , node ):
@@ -143,7 +157,7 @@ def handlePlaintextNode(self, node):
143157 self .pendingMessages [node ["to" ]] = []
144158 self .pendingMessages [node ["to" ]].append (node )
145159
146- self ._sendIq (entity , self .onGetKeysResult , self .onGetKeysError )
160+ self ._sendIq (entity , lambda a , b : self .onGetKeysResult ( a , b , self . processPendingMessages ) , self .onGetKeysError )
147161 else :
148162
149163 sessionCipher = self .getSessionCipher (recipient_id )
@@ -172,9 +186,29 @@ def handleEncMessage(self, node):
172186 self .handlePreKeyWhisperMessage (node )
173187 else :
174188 self .handleWhisperMessage (node )
175- except InvalidMessageException :
176- logger .error ("Invalid message from %s!! Your axololtl database data might be inconsistent with WhatsApp, or with what that contact has" % node ["from" ])
177- sys .exit (1 )
189+ except InvalidMessageException as e :
190+ # logger.error("Invalid message from %s!! Your axololtl database data might be inconsistent with WhatsApp, or with what that contact has" % node["from"])
191+ # sys.exit(1)
192+ logger .error (e )
193+ retry = RetryOutgoingReceiptProtocolEntity .fromMesageNode (node )
194+ retry .setRegData (self .store .getLocalRegistrationId ())
195+ self .toLower (retry .toProtocolTreeNode ())
196+ except InvalidKeyIdException as e :
197+ logger .error (e )
198+ retry = RetryOutgoingReceiptProtocolEntity .fromMesageNode (node )
199+ retry .setRegData (self .store .getLocalRegistrationId ())
200+ self .toLower (retry .toProtocolTreeNode ())
201+ except NoSessionException as e :
202+ logger .error (e )
203+ entity = GetKeysIqProtocolEntity ([node ["from" ]])
204+ if node ["from" ] not in self .pendingIncomingMessages :
205+ self .pendingIncomingMessages [node ["from" ]] = []
206+ self .pendingIncomingMessages [node ["from" ]].append (node )
207+
208+ self ._sendIq (entity , lambda a , b : self .onGetKeysResult (a , b , self .processPendingIncomingMessages ), self .onGetKeysError )
209+
210+
211+
178212 def handlePreKeyWhisperMessage (self , node ):
179213 pkMessageProtocolEntity = EncryptedMessageProtocolEntity .fromProtocolTreeNode (node )
180214
@@ -243,7 +277,7 @@ def persistKeys(self, registrationId, identityKeyPair, preKeys, signedPreKey, fr
243277 def onSentKeysError (self , errorNode , keysEntity ):
244278 raise Exception ("Sent keys were not accepted" )
245279
246- def onGetKeysResult (self , resultNode , getKeysEntity ):
280+ def onGetKeysResult (self , resultNode , getKeysEntity , processPendingFn ):
247281 entity = ResultGetKeysIqProtocolEntity .fromProtocolTreeNode (resultNode )
248282
249283 resultJids = entity .getJids ()
@@ -261,7 +295,7 @@ def onGetKeysResult(self, resultNode, getKeysEntity):
261295 self .store , recipient_id , 1 )
262296 sessionBuilder .processPreKeyBundle (preKeyBundle )
263297
264- self . processPendingMessages (jid )
298+ processPendingFn (jid )
265299
266300 def onGetKeysError (self , errorNode , getKeysEntity ):
267301 pass
0 commit comments