comparison sat/plugins/plugin_xep_0045.py @ 2991:f4590ca2acff

plugin XEP-0045: avoid sending useless presence signals: - presence signals were sent twice (from XEP-0045 itself + core), this is now avoided by cancelling presence workflow in core when presence if from a joined room. - filter out cached presences if no status or show information is set (occupants are already specified in mucRoomJoined signal)
author Goffi <goffi@goffi.org>
date Sun, 07 Jul 2019 15:39:53 +0200
parents 6959c71ab8bf
children 94708a7d3ecf
comparison
equal deleted inserted replaced
2990:6959c71ab8bf 2991:f4590ca2acff
790 790
791 def presenceReceivedTrigger(self, client, entity, show, priority, statuses): 791 def presenceReceivedTrigger(self, client, entity, show, priority, statuses):
792 entity_bare = entity.userhostJID() 792 entity_bare = entity.userhostJID()
793 muc_client = client._muc_client 793 muc_client = client._muc_client
794 if entity_bare in muc_client.joined_rooms: 794 if entity_bare in muc_client.joined_rooms:
795 room = muc_client.joined_rooms[entity_bare] 795 # presence is already handled in (un)availableReceived
796 if hasattr(room, "_cache_presence"): 796 return False
797 # room has a cache for presence, meaning it has not been fully
798 # joined yet. So we put presence in cache, and stop workflow.
799 # Or delete current presence and continue workflow if it's an
800 # "unavailable" presence
801 cache = room._cache_presence
802 if show == C.PRESENCE_UNAVAILABLE:
803 try:
804 del cache[entity]
805 except KeyError:
806 pass
807 return True
808 else:
809 cache[entity] = {
810 "entity": entity,
811 "show": show,
812 "statuses": statuses,
813 "priority": priority}
814 return False
815 return True 797 return True
816 798
817 799
818 class SatMUCClient(muc.MUCClient): 800 class SatMUCClient(muc.MUCClient):
819 implements(iwokkel.IDisco) 801 implements(iwokkel.IDisco)
1148 1130
1149 def userChangedNick(self, room, user, new_nick): 1131 def userChangedNick(self, room, user, new_nick):
1150 self.host.bridge.mucRoomUserChangedNick(room.roomJID.userhost(), user.nick, new_nick, self.client.profile) 1132 self.host.bridge.mucRoomUserChangedNick(room.roomJID.userhost(), user.nick, new_nick, self.client.profile)
1151 1133
1152 def userUpdatedStatus(self, room, user, show, status): 1134 def userUpdatedStatus(self, room, user, show, status):
1153 self.host.bridge.presenceUpdate(room.roomJID.userhost() + '/' + user.nick, show or '', 0, {C.PRESENCE_STATUSES_DEFAULT: status or ''}, self.client.profile) 1135 entity = jid.JID(tuple=(room.roomJID.user, room.roomJID.host, user.nick))
1136 if hasattr(room, "_cache_presence"):
1137 # room has a cache for presence, meaning it has not been fully
1138 # joined yet. So we put presence in cache, and stop workflow.
1139 # Or delete current presence and continue workflow if it's an
1140 # "unavailable" presence
1141 cache = room._cache_presence
1142 cache[entity] = {
1143 "room": room,
1144 "user": user,
1145 "show": show,
1146 "status": status,
1147 }
1148 return
1149 statuses = {C.PRESENCE_STATUSES_DEFAULT: status or ''}
1150 self.host.bridge.presenceUpdate(
1151 entity.full(), show or '', 0, statuses, self.client.profile)
1154 1152
1155 ## messages ## 1153 ## messages ##
1156 1154
1157 def receivedGroupChat(self, room, user, body): 1155 def receivedGroupChat(self, room, user, body):
1158 log.debug(u'receivedGroupChat: room=%s user=%s body=%s' % (room.roomJID.full(), user, body)) 1156 log.debug(u'receivedGroupChat: room=%s user=%s body=%s' % (room.roomJID.full(), user, body))
1254 del room._cache 1252 del room._cache
1255 cache_presence = room._cache_presence 1253 cache_presence = room._cache_presence
1256 del room._cache_presence 1254 del room._cache_presence
1257 for elem in cache: 1255 for elem in cache:
1258 self.client.xmlstream.dispatch(elem) 1256 self.client.xmlstream.dispatch(elem)
1259 for __, presence_data in cache_presence.iteritems(): 1257 for presence_data in cache_presence.itervalues():
1260 self.client.presence.availableReceived(**presence_data) 1258 if not presence_data[u'show'] and not presence_data[u'status']:
1259 # occupants are already sent in mucRoomJoined, so if we don't have
1260 # extra information like show or statuses, we can discard the signal
1261 continue
1262 else:
1263 self.userUpdatedStatus(**presence_data)
1261 1264
1262 def _historyEb(self, failure_, room): 1265 def _historyEb(self, failure_, room):
1263 log.error(u"Error while managing history: {}".format(failure_)) 1266 log.error(u"Error while managing history: {}".format(failure_))
1264 self._historyCb(None, room) 1267 self._historyCb(None, room)
1265 1268