comparison sat/core/xmpp.py @ 3784:efc34a89e70b

comp AP gateway: message conversion: Convert direct AP items to XMPP `<message>` stanzas, and vice versa. Documentation will follow soon to explain the behaviour. rel 366
author Goffi <goffi@goffi.org>
date Tue, 24 May 2022 17:57:36 +0200
parents 001ea5f4a2f9
children 967a8e109cda
comparison
equal deleted inserted replaced
3783:fedbf7aade11 3784:efc34a89e70b
610 610
611 @param post_xml_treatments(D): the same Deferred as in sendMessage trigger 611 @param post_xml_treatments(D): the same Deferred as in sendMessage trigger
612 """ 612 """
613 raise NotImplementedError 613 raise NotImplementedError
614 614
615 def send(self, obj):
616 # original send method accept string
617 # but we restrict to domish.Element to make trigger treatments easier
618 assert isinstance(obj, domish.Element)
619 # XXX: this trigger is the last one before sending stanza on wire
620 # it is intended for things like end 2 end encryption.
621 # *DO NOT* cancel (i.e. return False) without very good reason
622 # (out of band transmission for instance).
623 # e2e should have a priority of 0 here, and out of band transmission
624 # a lower priority
625 #  FIXME: trigger not used yet, can be uncommented when e2e full stanza
626 # encryption is implemented
627 #  if not self.host_app.trigger.point("send", self, obj):
628 #   return
629 super().send(obj)
630
631 @defer.inlineCallbacks
632 def sendMessageData(self, mess_data):
633 """Convenient method to send message data to stream
634
635 This method will send mess_data[u'xml'] to stream, but a trigger is there
636 The trigger can't be cancelled, it's a good place for e2e encryption which
637 don't handle full stanza encryption
638 This trigger can return a Deferred (it's an asyncPoint)
639 @param mess_data(dict): message data as constructed by onMessage workflow
640 @return (dict): mess_data (so it can be used in a deferred chain)
641 """
642 # XXX: This is the last trigger before u"send" (last but one globally)
643 # for sending message.
644 # This is intented for e2e encryption which doesn't do full stanza
645 # encryption (e.g. OTR)
646 # This trigger point can't cancel the method
647 yield self.host_app.trigger.asyncPoint("sendMessageData", self, mess_data,
648 triggers_no_cancel=True)
649 self.send(mess_data["xml"])
650 defer.returnValue(mess_data)
651
615 def sendMessage( 652 def sendMessage(
616 self, to_jid, message, subject=None, mess_type="auto", extra=None, uid=None, 653 self, to_jid, message, subject=None, mess_type="auto", extra=None, uid=None,
617 no_trigger=False): 654 no_trigger=False):
618 r"""Send a message to an entity 655 r"""Send a message to an entity
619 656
657 694
658 if data["type"] == C.MESS_TYPE_AUTO: 695 if data["type"] == C.MESS_TYPE_AUTO:
659 # we try to guess the type 696 # we try to guess the type
660 if data["subject"]: 697 if data["subject"]:
661 data["type"] = C.MESS_TYPE_NORMAL 698 data["type"] = C.MESS_TYPE_NORMAL
662 elif not data["to"].resource: # if to JID has a resource, 699 elif not data["to"].resource:
663 # the type is not 'groupchat'
664 # we may have a groupchat message, we check if the we know this jid 700 # we may have a groupchat message, we check if the we know this jid
665 try: 701 try:
666 entity_type = self.host_app.memory.getEntityDatum( 702 entity_type = self.host_app.memory.getEntityDatum(
667 self, data["to"], C.ENTITY_TYPE 703 self, data["to"], C.ENTITY_TYPE
668 ) 704 )
673 if entity_type == C.ENTITY_TYPE_MUC: 709 if entity_type == C.ENTITY_TYPE_MUC:
674 data["type"] = C.MESS_TYPE_GROUPCHAT 710 data["type"] = C.MESS_TYPE_GROUPCHAT
675 else: 711 else:
676 data["type"] = C.MESS_TYPE_CHAT 712 data["type"] = C.MESS_TYPE_CHAT
677 else: 713 else:
678 data["type"] == C.MESS_TYPE_CHAT 714 data["type"] = C.MESS_TYPE_CHAT
679 data["type"] == C.MESS_TYPE_CHAT if data["subject"] else C.MESS_TYPE_NORMAL
680 715
681 # FIXME: send_only is used by libervia's OTR plugin to avoid 716 # FIXME: send_only is used by libervia's OTR plugin to avoid
682 # the triggers from frontend, and no_trigger do the same 717 # the triggers from frontend, and no_trigger do the same
683 # thing internally, this could be unified 718 # thing internally, this could be unified
684 send_only = data["extra"].get("send_only", False) 719 send_only = data["extra"].get("send_only", False)
892 post_xml_treatments.addCallback(self.messageProt.completeAttachments) 927 post_xml_treatments.addCallback(self.messageProt.completeAttachments)
893 post_xml_treatments.addCallback( 928 post_xml_treatments.addCallback(
894 lambda ret: defer.ensureDeferred(self.messageAddToHistory(ret)) 929 lambda ret: defer.ensureDeferred(self.messageAddToHistory(ret))
895 ) 930 )
896 post_xml_treatments.addCallback(self.messageSendToBridge) 931 post_xml_treatments.addCallback(self.messageSendToBridge)
897
898 def send(self, obj):
899 # original send method accept string
900 # but we restrict to domish.Element to make trigger treatments easier
901 assert isinstance(obj, domish.Element)
902 # XXX: this trigger is the last one before sending stanza on wire
903 # it is intended for things like end 2 end encryption.
904 # *DO NOT* cancel (i.e. return False) without very good reason
905 # (out of band transmission for instance).
906 # e2e should have a priority of 0 here, and out of band transmission
907 # a lower priority
908 #  FIXME: trigger not used yet, can be uncommented when e2e full stanza
909 # encryption is implemented
910 #  if not self.host_app.trigger.point("send", self, obj):
911 #   return
912 super(SatXMPPClient, self).send(obj)
913
914 @defer.inlineCallbacks
915 def sendMessageData(self, mess_data):
916 """Convenient method to send message data to stream
917
918 This method will send mess_data[u'xml'] to stream, but a trigger is there
919 The trigger can't be cancelled, it's a good place for e2e encryption which
920 don't handle full stanza encryption
921 This trigger can return a Deferred (it's an asyncPoint)
922 @param mess_data(dict): message data as constructed by onMessage workflow
923 @return (dict): mess_data (so it can be used in a deferred chain)
924 """
925 # XXX: This is the last trigger before u"send" (last but one globally)
926 # for sending message.
927 # This is intented for e2e encryption which doesn't do full stanza
928 # encryption (e.g. OTR)
929 # This trigger point can't cancel the method
930 yield self.host_app.trigger.asyncPoint("sendMessageData", self, mess_data,
931 triggers_no_cancel=True)
932 self.send(mess_data["xml"])
933 defer.returnValue(mess_data)
934 932
935 def feedback(self, to_jid, message, extra=None): 933 def feedback(self, to_jid, message, extra=None):
936 """Send message to frontends 934 """Send message to frontends
937 935
938 This message will be an info message, not recorded in history. 936 This message will be an info message, not recorded in history.