comparison src/plugins/plugin_xep_0060.py @ 2338:b1bbd2994ceb

plugin XEP-0060: implemented subscriptions management method for node owner: added getNodeSubscriptions and setNodeSubscriptions and their bridge method (psNodeSubscriptionsGet and psNodeSubscriptionsSet)
author Goffi <goffi@goffi.org>
date Sun, 20 Aug 2017 10:31:53 +0200
parents e715a29c4f9b
children 6c26f435a02d
comparison
equal deleted inserted replaced
2337:3399971f0aa0 2338:b1bbd2994ceb
86 self._node_cb = {} # dictionnary of callbacks for node (key: node, value: list of callbacks) 86 self._node_cb = {} # dictionnary of callbacks for node (key: node, value: list of callbacks)
87 self.rt_sessions = sat_defer.RTDeferredSessions() 87 self.rt_sessions = sat_defer.RTDeferredSessions()
88 host.bridge.addMethod("psNodeCreate", ".plugin", in_sign='ssa{ss}s', out_sign='s', method=self._createNode, async=True) 88 host.bridge.addMethod("psNodeCreate", ".plugin", in_sign='ssa{ss}s', out_sign='s', method=self._createNode, async=True)
89 host.bridge.addMethod("psNodeConfigurationGet", ".plugin", in_sign='sss', out_sign='a{ss}', method=self._getNodeConfiguration, async=True) 89 host.bridge.addMethod("psNodeConfigurationGet", ".plugin", in_sign='sss', out_sign='a{ss}', method=self._getNodeConfiguration, async=True)
90 host.bridge.addMethod("psNodeConfigurationSet", ".plugin", in_sign='ssa{ss}s', out_sign='', method=self._setNodeConfiguration, async=True) 90 host.bridge.addMethod("psNodeConfigurationSet", ".plugin", in_sign='ssa{ss}s', out_sign='', method=self._setNodeConfiguration, async=True)
91 host.bridge.addMethod("psAffiliationsGet", ".plugin", in_sign='sss', out_sign='a{ss}', method=self._getAffiliations, async=True)
92 host.bridge.addMethod("psNodeAffiliationsGet", ".plugin", in_sign='sss', out_sign='a{ss}', method=self._getNodeAffiliations, async=True) 91 host.bridge.addMethod("psNodeAffiliationsGet", ".plugin", in_sign='sss', out_sign='a{ss}', method=self._getNodeAffiliations, async=True)
93 host.bridge.addMethod("psNodeAffiliationsSet", ".plugin", in_sign='ssa{ss}s', out_sign='', method=self._setNodeAffiliations, async=True) 92 host.bridge.addMethod("psNodeAffiliationsSet", ".plugin", in_sign='ssa{ss}s', out_sign='', method=self._setNodeAffiliations, async=True)
93 host.bridge.addMethod("psNodeSubscriptionsGet", ".plugin", in_sign='sss', out_sign='a{ss}', method=self._getNodeSubscriptions, async=True)
94 host.bridge.addMethod("psNodeSubscriptionsSet", ".plugin", in_sign='ssa{ss}s', out_sign='', method=self._setNodeSubscriptions, async=True)
95 host.bridge.addMethod("psAffiliationsGet", ".plugin", in_sign='sss', out_sign='a{ss}', method=self._getAffiliations, async=True)
94 host.bridge.addMethod("psNodeDelete", ".plugin", in_sign='sss', out_sign='', method=self._deleteNode, async=True) 96 host.bridge.addMethod("psNodeDelete", ".plugin", in_sign='sss', out_sign='', method=self._deleteNode, async=True)
95 host.bridge.addMethod("psItemsGet", ".plugin", in_sign='ssiassa{ss}s', out_sign='(asa{ss})', method=self._getItems, async=True) 97 host.bridge.addMethod("psItemsGet", ".plugin", in_sign='ssiassa{ss}s', out_sign='(asa{ss})', method=self._getItems, async=True)
96 host.bridge.addMethod("psItemSend", ".plugin", in_sign='ssssa{ss}s', out_sign='s', method=self._sendItem, async=True) 98 host.bridge.addMethod("psItemSend", ".plugin", in_sign='ssssa{ss}s', out_sign='s', method=self._sendItem, async=True)
97 host.bridge.addMethod("psRetractItem", ".plugin", in_sign='sssbs', out_sign='', method=self._retractItem, async=True) 99 host.bridge.addMethod("psRetractItem", ".plugin", in_sign='sssbs', out_sign='', method=self._retractItem, async=True)
98 host.bridge.addMethod("psRetractItems", ".plugin", in_sign='ssasbs', out_sign='', method=self._retractItems, async=True) 100 host.bridge.addMethod("psRetractItems", ".plugin", in_sign='ssasbs', out_sign='', method=self._retractItems, async=True)
661 failure_result = () 663 failure_result = ()
662 return [('', result) if success else (unicode(result.result) or UNSPECIFIED, failure_result) for success, result in results] 664 return [('', result) if success else (unicode(result.result) or UNSPECIFIED, failure_result) for success, result in results]
663 665
664 # subscribe # 666 # subscribe #
665 667
668 def _getNodeSubscriptions(self, service_s, nodeIdentifier, profile_key):
669 client = self.host.getClient(profile_key)
670 d = self.getNodeSubscriptions(client, jid.JID(service_s) if service_s else None, nodeIdentifier)
671 d.addCallback(lambda subscriptions: {j.full(): a for j, a in subscriptions.iteritems()})
672 return d
673
674 def getNodeSubscriptions(self, client, service, nodeIdentifier):
675 """Retrieve subscriptions to a node
676
677 @param nodeIdentifier(unicode): node to get subscriptions from
678 """
679 if not nodeIdentifier:
680 raise exceptions.DataError("node identifier can't be empty")
681 request = pubsub.PubSubRequest('subscriptionsGet')
682 request.recipient = service
683 request.nodeIdentifier = nodeIdentifier
684
685 def cb(iq_elt):
686 try:
687 subscriptions_elt = next(iq_elt.pubsub.elements((pubsub.NS_PUBSUB, 'subscriptions')))
688 except StopIteration:
689 raise ValueError(_(u"Invalid result: missing <subscriptions> element: {}").format(iq_elt.toXml))
690 except AttributeError as e:
691 raise ValueError(_(u"Invalid result: {}").format(e))
692 try:
693 return {jid.JID(s['jid']): s['subscription'] for s in subscriptions_elt.elements((pubsub.NS_PUBSUB, 'subscription'))}
694 except KeyError:
695 raise ValueError(_(u"Invalid result: bad <subscription> element: {}").format(iq_elt.toXml))
696
697 d = request.send(client.xmlstream)
698 d.addCallback(cb)
699 return d
700
701 def _setNodeSubscriptions(self, service_s, nodeIdentifier, subscriptions, profile_key=C.PROF_KEY_NONE):
702 client = self.host.getClient(profile_key)
703 subscriptions = {jid.JID(jid_): subscription for jid_, subscription in subscriptions.iteritems()}
704 d = self.setNodeSubscriptions(client, jid.JID(service_s) if service_s else None, nodeIdentifier, subscriptions)
705 return d
706
707 def setNodeSubscriptions(self, client, service, nodeIdentifier, subscriptions):
708 """Set or update subscriptions of a node owned by profile
709
710 @param subscriptions(dict[jid.JID, unicode]): subscriptions to set
711 check https://xmpp.org/extensions/xep-0060.html#substates for a list of possible subscriptions
712 """
713 request = pubsub.PubSubRequest('subscriptionsSet')
714 request.recipient = service
715 request.nodeIdentifier = nodeIdentifier
716 request.subscriptions = {pubsub.Subscription(nodeIdentifier, jid_, state) for jid_, state in subscriptions.iteritems()}
717 d = request.send(client.xmlstream)
718 return d
719
666 def _manySubscribeRTResult(self, session_id, profile_key=C.PROF_KEY_DEFAULT): 720 def _manySubscribeRTResult(self, session_id, profile_key=C.PROF_KEY_DEFAULT):
667 """Get real-time results for subcribeToManu session 721 """Get real-time results for subcribeToManu session
668 722
669 @param session_id: id of the real-time deferred session 723 @param session_id: id of the real-time deferred session
670 @param return (tuple): (remaining, results) where: 724 @param return (tuple): (remaining, results) where: