comparison src/plugins/plugin_xep_0277.py @ 1821:d6062afdd54f

plugin XEP-0277: comments handling improvments: - if comments*, comments*_node or comments*_service are provided, they are used instead of generated values - moved node and service generation to getCommentNode and getCommentService, so they can be used by an external plugin
author Goffi <goffi@goffi.org>
date Fri, 22 Jan 2016 20:24:17 +0100
parents 3c8cf120a0fd
children aaf034bc6f7a
comparison
equal deleted inserted replaced
1820:3c8cf120a0fd 1821:d6062afdd54f
453 453
454 defer.returnValue(item_elt) 454 defer.returnValue(item_elt)
455 455
456 ## publish ## 456 ## publish ##
457 457
458 def getCommentNode(self, item_id):
459 """Generate comment node
460
461 @param item_id(unicode): id of the parent item
462 @return (unicode): comment node to use
463 """
464 return u"{}{}".format(NS_COMMENT_PREFIX, item_id)
465
466 def getCommentService(self, client, parent_service=None):
467 """Get prefered PubSub service to create comment node
468
469 @param pubsub_service(jid.JID, None): PubSub service of the parent item
470 @param return(jid.JID, None): PubSub service to use
471 """
472 return client.pubsub_service if client.pubsub_service is not None else parent_service
473
458 @defer.inlineCallbacks 474 @defer.inlineCallbacks
459 def _manageComments(self, access, mb_data, service, node, item_id, profile): 475 def _manageComments(self, access, mb_data, service, node, item_id, profile):
460 """Check comments keys in mb_data and create comments node if necessary 476 """Check comments keys in mb_data and create comments node if necessary
461 477
478 if mb_data['comments'] exists, it is used (or mb_data['comments_service'] and/or mb_data['comments_node']),
479 else it is generated (if allow_comments is True).
462 @param access(unicode): access model 480 @param access(unicode): access model
463 @param mb_data(dict): microblog mb_data 481 @param mb_data(dict): microblog mb_data
464 @param service(jid.JID): Pubsub service of the parent item 482 @param service(jid.JID, None): PubSub service of the parent item
465 @param node(unicode): node of the parent item 483 @param node(unicode): node of the parent item
466 @param item_id(unicoe): id of the parent item 484 @param item_id(unicoe): id of the parent item
467 """ 485 """
486 # FIXME: if 'comments' already exists in mb_data, it is not used to create the Node
468 allow_comments = C.bool(mb_data.pop("allow_comments", "false")) 487 allow_comments = C.bool(mb_data.pop("allow_comments", "false"))
469 if not allow_comments: 488 if not allow_comments:
489 if 'comments' in mb_data:
490 log.warning(u"comments are not allowed but there is already a comments node, it may be lost: {uri}".format(uri=mb_data['comments']))
491 del mb_data['comments']
470 return 492 return
471 493
472 client = self.host.getClient(profile) 494 client = self.host.getClient(profile)
473 495
474 options = {self._p.OPT_ACCESS_MODEL: access, 496 options = {self._p.OPT_ACCESS_MODEL: access,
480 } 502 }
481 503
482 # if other plugins need to change the options 504 # if other plugins need to change the options
483 yield self.host.trigger.point("XEP-0277_comments", client, mb_data, options) 505 yield self.host.trigger.point("XEP-0277_comments", client, mb_data, options)
484 506
485 comments_node_base = u"{}{}".format(NS_COMMENT_PREFIX, item_id) 507 try:
486 comments_node = comments_node_base 508 comments_node = mb_data['comments_node']
487 comments_service = client.pubsub_service if client.pubsub_service is not None else service 509 except KeyError:
510 comments_node = self.getCommentNode(item_id)
511 else:
512 if not comments_node:
513 raise exceptions.DataError(u"if comments_node is present, it must not be empty")
514
515 try:
516 comments_service = mb_data['comments_service']
517 except KeyError:
518 comments_service = self.getCommentService(client, service)
488 519
489 try: 520 try:
490 yield self._p.createNode(comments_service, comments_node, options, profile_key=profile) 521 yield self._p.createNode(comments_service, comments_node, options, profile_key=profile)
491 except error.StanzaError as e: 522 except error.StanzaError as e:
492 if e.condition == 'conflict': 523 if e.condition == 'conflict':
495 raise e 526 raise e
496 527
497 if comments_service is None: 528 if comments_service is None:
498 comments_service = client.jid.userhostJID() 529 comments_service = client.jid.userhostJID()
499 530
500 mb_data['comments'] = "xmpp:%(service)s?%(query)s" % { 531 if 'comments' in mb_data:
501 'service': comments_service.userhost(), 532 if not mb_data['comments']:
502 'query': urllib.urlencode([('node', comments_node.encode('utf-8'))]) 533 raise exceptions.DataError(u"if comments is present, it must not be empty")
503 } 534 if 'comments_node' in mb_data or 'comments_service' in mb_data:
535 raise exceptions.DataError(u"You can't use comments_service/comments_node and comments at the same time")
536 else:
537 mb_data['comments'] = u"xmpp:%(service)s?%(query)s" % {
538 'service': comments_service.userhost(),
539 'query': urllib.urlencode([('node', comments_node.encode('utf-8'))])
540 }
504 541
505 def _mbSend(self, service, node, data, profile_key): 542 def _mbSend(self, service, node, data, profile_key):
506 service = jid.JID(service) if service else None 543 service = jid.JID(service) if service else None
507 node = node if node else NS_MICROBLOG 544 node = node if node else NS_MICROBLOG
508 profile = self.host.memory.getProfileName(profile_key) 545 profile = self.host.memory.getProfileName(profile_key)
509 return self.send(service, node, data, profile) 546 return self.send(data, service, node, profile)
510 547
511 @defer.inlineCallbacks 548 @defer.inlineCallbacks
512 def send(self, service=None, node=NS_MICROBLOG, data=None, profile=None): 549 def send(self, data, service=None, node=NS_MICROBLOG, profile=None):
513 """Send XEP-0277's microblog data 550 """Send XEP-0277's microblog data
514 551
552 @param data(dict): microblog data (must include at least a "content" or a "title" key).
553 see http://wiki.goffi.org/wiki/Bridge_API_-_Microblogging/en for details
515 @param service(jid.JID, None): PubSub service where the microblog must be published 554 @param service(jid.JID, None): PubSub service where the microblog must be published
516 None to publish on profile's PEP 555 None to publish on profile's PEP
517 @param node(unicode): PubSub node to use (defaut to microblog NS) 556 @param node(unicode, None): PubSub node to use (defaut to microblog NS)
518 @param data(dict): microblog data (must include at least a "content" or a "title" key). 557 None is equivalend as using default value
519 see http://wiki.goffi.org/wiki/Bridge_API_-_Microblogging/en for details
520 @param profile: %(doc_profile)s 558 @param profile: %(doc_profile)s
521 """ 559 """
522 # TODO: check that all data keys are used, this would avoid sending publicly a private message 560 # TODO: check that all data keys are used, this would avoid sending publicly a private message
523 # by accident (e.g. if group pluging is not loaded, and "grou*" key are not used) 561 # by accident (e.g. if group pluging is not loaded, and "grou*" key are not used)
524 assert profile is not None 562 assert profile is not None
563 if node is None:
564 node = NS_MICROBLOG
525 565
526 item_id = data.get('id') or unicode(uuid.uuid4()) 566 item_id = data.get('id') or unicode(uuid.uuid4())
527 try: 567 try:
528 yield self._manageComments(self._p.ACCESS_OPEN, data, service, node, item_id, profile) 568 yield self._manageComments(self._p.ACCESS_OPEN, data, service, node, item_id, profile)
529 except error.StanzaError: 569 except error.StanzaError: