def getAsTree(self): """Return the roster item as an Element tree starting from <item>""" item = Element('item', { 'jid' : self.jid, 'subscription' : Subscription.getPrimaryNameFromState(self.subscription) }) if self.name: item.set('name', self.name) for group in self.groups: SubElement(item, 'group').text = group return item
def getAsTree(self): """Return the roster item as an Element tree starting from <item>""" item = Element( 'item', { 'jid': self.jid, 'subscription': Subscription.getPrimaryNameFromState(self.subscription) }) if self.name: item.set('name', self.name) for group in self.groups: SubElement(item, 'group').text = group return item
def act(): d = msg.conn.data retVal = lastRetVal jid = d['user']['jid'] resource = d['user']['resource'] roster = Roster(jid) presTree = deepcopy(tree) presTree.set('from', '%s/%s' % (jid, resource)) probes = [] if tree.get('to') is None and not d['user']['active']: # initial presence # TODO: we don't need to do it every time. we can cache the # data after the first resource is active and just resend # that to all new resources d['user']['active'] = True # get jids of the contacts whose status we're interested in cjids = roster.getPresenceSubscriptions() probeTree = Element('presence', { 'type': 'probe', 'from' : '%s/%s' \ % (jid, resource) }) # TODO: replace this with a more efficient router handler for cjid in cjids: probeTree.set('to', cjid) probeRouteData = {'to': cjid, 'data': deepcopy(probeTree)} probes.append(probeRouteData) # they're sent first. see below # broadcast to other resources of this user retVal = self.broadcastToOtherResources( presTree, msg, retVal, jid, resource) elif tree.get('to') is not None: # TODO: directed presence return elif tree.get('type') == 'unavailable': # broadcast to other resources of this user d['user']['active'] = False retVal = self.broadcastToOtherResources( presTree, msg, retVal, jid, resource) # record this stanza as the last presence sent from this client lastPresence = deepcopy(tree) lastPresence.set('from', '%s/%s' % (jid, resource)) d['user']['lastPresence'] = lastPresence # lookup contacts interested in presence cjids = roster.getPresenceSubscribers() # TODO: replace this with another router handler that would send # it out to all cjids in a batch instead of queuing a handler # for each for cjid in cjids: presTree.set('to', cjid) presRouteData = {'to': cjid, 'data': deepcopy(presTree)} retVal = chainOutput(retVal, presRouteData) msg.setNextHandler('route-server') # send the probes first for probe in probes: msg.setNextHandler('route-server') retVal = chainOutput(retVal, probe) return retVal
def act(): d = msg.conn.data retVal = lastRetVal jid = d['user']['jid'] resource = d['user']['resource'] roster = Roster(jid) presTree = deepcopy(tree) presTree.set('from', '%s/%s' % (jid, resource)) probes = [] init_rosters = [] offline_msgs = [] if tree.get('to') is None and not d['user']['active']: # initial presence # TODO: we don't need to do it every time. we can cache the # data after the first resource is active and just resend # that to all new resources d['user']['active'] = True # get jids of the contacts whose status we're interested in cjids = roster.getPresenceSubscriptions() probeTree = Element('presence', { 'type': 'probe', 'from' : '%s/%s' \ % (jid, resource) }) # TODO: replace this with a more efficient router handler for cjid in cjids: probeTree.set('to', cjid) probeRouteData = { 'to' : cjid, 'data' : deepcopy(probeTree) } probes.append(probeRouteData) # they're sent first. see below # send initial roster list to this user rosterTree = Element('presence', { 'type': 'unavailable', 'to' : '%s/%s' \ % (jid, resource) }) for cjid in cjids: rosterTree.set('from', cjid) rosterRouterData = { 'to' : '%s/%s' % (jid, resource), 'data' : deepcopy(rosterTree) } init_rosters.append(rosterRouterData) # send offline message to this user try: con = DB() result = [] to_jid = JID(jid) with closing(con.cursor()) as cursor: cursor.execute("SELECT fromid, time, content FROM offline WHERE toid = %d ORDER BY time DESC" % (to_jid.getNumId())) con.commit() result = cursor.fetchall() with closing(con.cursor()) as cursor: cursor.execute("DELETE FROM offline WHERE toid = %d" % (to_jid.getNumId())) con.commit() for fromid, time, content in result: fromJID = JID(fromid, True).getBare() toJID = '%s/%s' % (jid, resource) reply = Element('message', { 'to': toJID, 'from': fromJID, 'type': 'chat' }) body = Element('body') body.text = content reply.append(body) delay = Element('delay', { 'xmlns': 'urn:xmpp:delay', 'from': fromJID, 'stamp': time.strftime("%Y-%m-%dT%H:%M:%SZ") }) reply.append(delay) routeData = { 'to' : toJID, 'data': reply } offline_msgs.append(routeData) logging.debug("[%s] Sending %d offline messages to %s", self.__class__, len(offline_msgs), to_jid.getBare()) except Exception as e: logging.warning("[%s] Failed to read offline messages: %s", self.__class__, str(e)) # broadcast to other resources of this user retVal = self.broadcastToOtherResources(presTree, msg, retVal, jid, resource) elif tree.get('to') is not None: # TODO: directed presence return elif tree.get('type') == 'unavailable': # broadcast to other resources of this user d['user']['active'] = False retVal = self.broadcastToOtherResources(presTree, msg, retVal, jid, resource) # record this stanza as the last presence sent from this client lastPresence = deepcopy(tree) lastPresence.set('from', '%s/%s' % (jid, resource)) d['user']['lastPresence'] = lastPresence # lookup contacts interested in presence cjids = roster.getPresenceSubscribers() # TODO: replace this with another router handler that would send # it out to all cjids in a batch instead of queuing a handler # for each for cjid in cjids: presTree.set('to', cjid) presRouteData = { 'to' : cjid, 'data' : deepcopy(presTree) } retVal = chainOutput(retVal, presRouteData) msg.setNextHandler('route-server') # send the probes first for probe in probes: msg.setNextHandler('route-server') retVal = chainOutput(retVal, probe) # send initial rosters for init_roster in init_rosters: msg.setNextHandler('route-client') retVal = chainOutput(retVal, init_roster) # send offline messages for offline_msg in offline_msgs: msg.setNextHandler('route-client') retVal = chainOutput(retVal, offline_msg) return retVal
def act(): d = msg.conn.data retVal = lastRetVal jid = d['user']['jid'] resource = d['user']['resource'] roster = Roster(jid) presTree = deepcopy(tree) presTree.set('from', '%s/%s' % (jid, resource)) probes = [] if tree.get('to') is None and not d['user']['active']: # initial presence # TODO: we don't need to do it every time. we can cache the # data after the first resource is active and just resend # that to all new resources d['user']['active'] = True # get jids of the contacts whose status we're interested in cjids = roster.getPresenceSubscriptions() probeTree = Element('presence', { 'type': 'probe', 'from' : '%s/%s' \ % (jid, resource) }) # TODO: replace this with a more efficient router handler for cjid in cjids: probeTree.set('to', cjid) probeRouteData = { 'to' : cjid, 'data' : deepcopy(probeTree) } probes.append(probeRouteData) # they're sent first. see below # broadcast to other resources of this user retVal = self.broadcastToOtherResources(presTree, msg, retVal, jid, resource) elif tree.get('to') is not None: # TODO: directed presence return elif tree.get('type') == 'unavailable': # broadcast to other resources of this user d['user']['active'] = False retVal = self.broadcastToOtherResources(presTree, msg, retVal, jid, resource) # record this stanza as the last presence sent from this client lastPresence = deepcopy(tree) lastPresence.set('from', '%s/%s' % (jid, resource)) d['user']['lastPresence'] = lastPresence # lookup contacts interested in presence cjids = roster.getPresenceSubscribers() # TODO: replace this with another router handler that would send # it out to all cjids in a batch instead of queuing a handler # for each for cjid in cjids: presTree.set('to', cjid) presRouteData = { 'to' : cjid, 'data' : deepcopy(presTree) } retVal = chainOutput(retVal, presRouteData) msg.setNextHandler('route-server') # send the probes first for probe in probes: msg.setNextHandler('route-server') retVal = chainOutput(retVal, probe) return retVal