1
2
3
4
5
6
7
8
9 import copy
10 from xmpp import *
11 from xmppd import *
12
13
14
15
16
17 SESSION_NOT_AUTHED = 1
18 SESSION_AUTHED = 2
19 SESSION_BOUND = 3
20 SESSION_OPENED = 4
21
23 """ The first entity that gets access to arrived stanza. """
24 NS='presence'
26 self._data = {}
27 server.Dispatcher.RegisterHandler('presence',self.presenceHandler,xmlns=NS_CLIENT)
28 server.Dispatcher.RegisterHandler('presence',self.presenceHandler,xmlns=NS_SERVER)
29
30 server.Dispatcher.RegisterHandler('message',self.routerHandler,xmlns=NS_CLIENT)
31 server.Dispatcher.RegisterHandler('message',self.routerHandler,xmlns=NS_SERVER)
32
33 server.Dispatcher.RegisterHandler('iq',self.routerHandler,xmlns=NS_CLIENT)
34 server.Dispatcher.RegisterHandler('iq',self.routerHandler,ns=NS_DISCO_INFO,xmlns=NS_CLIENT)
35 server.Dispatcher.RegisterHandler('iq',self.routerHandler,ns=NS_DISCO_INFO,xmlns=NS_SERVER)
36 server.Dispatcher.RegisterHandler('iq',self.routerHandler,ns=NS_DISCO_ITEMS,xmlns=NS_CLIENT)
37 server.Dispatcher.RegisterHandler('iq',self.routerHandler,ns=NS_DISCO_ITEMS,xmlns=NS_SERVER)
38
39 server.Dispatcher.RegisterHandler('iq',self.routerHandler,ns='http://jabber.org/protocol/muc')
40 server.Dispatcher.RegisterHandler('iq',self.routerHandler,ns='http://jabber.org/protocol/muc#user')
41 server.Dispatcher.RegisterHandler('iq',self.routerHandler,ns='http://jabber.org/protocol/muc#admin')
42 server.Dispatcher.RegisterHandler('iq',self.routerHandler,ns='http://jabber.org/protocol/muc#owner')
43 server.Dispatcher.RegisterHandler('iq',self.routerHandler,ns="http://jabber.org/protocol/muc#roominfo")
44 server.Dispatcher.RegisterHandler('iq',self.routerHandler,ns="http://jabber.org/protocol/muc#traffic")
45 server.Dispatcher.RegisterHandler('iq',self.routerHandler,ns="http://jabber.org/protocol/muc#roomconfig")
46 server.Dispatcher.RegisterHandler('iq',self.routerHandler,ns="http://jabber.org/protocol/muc#register")
47
48 server.Dispatcher.RegisterHandler('iq',self.routerHandler,ns='http://jabber.org/protocol/si')
49
50 server.Dispatcher.RegisterNamespaceHandler(NS_SERVER,self.routerHandler)
51
53 for servername in self._owner.servernames:
54 if str(domain).endswith(servername):
55 return False
56 return True
57
59 """
60 Relays a stanza to a plugin dispatcher if such plugin is the correct receiver of the stanza
61 """
62
63 to = stanza['to']
64 if not to: return False
65 for k,p in self._owner.plugins.items():
66 if p.has_key('jid') and p['jid'] == to.getDomain():
67 try:
68 self.DEBUG("Dispatching stanza to %s plugin"%(k),"info")
69 exec("self._owner."+k+".dispatch(session,stanza)")
70 except:
71 self.DEBUG("Could not dispatch stanza to plugin "+k, "error")
72 return False
73 return True
74 return False
75
76
77
79 self.DEBUG('Presence handler called (%s::%s)' % (session.peer,str(stanza.getType())),'info')
80
81
82
83
84 to=stanza['to']
85 internal = stanza.getAttr('internal')
86 fromOutside = False
87
88
89
90
91
92
93
94 if self.pluginRelay(session,stanza) and raiseFlag: raise NodeProcessed
95
96 if to and self.isFromOutside(to.getDomain()) and internal != 'True':
97
98
99 self.DEBUG("Presence stanza has an external or component receiver: %s"%(to.getDomain()),"warn")
100
101 typ=stanza.getType()
102 jid=session.peer
103 if not jid:
104 raise NodeProcessed
105 fromOutside = False
106 try:
107 barejid = ""
108
109
110
111
112 barejid = JID(jid).getStripped()
113 resource = JID(jid).getResource()
114 domain = JID(jid).getDomain()
115 supposed_from = stanza.getFrom()
116 if (barejid and supposed_from) and (barejid == supposed_from.getDomain()):
117 barejid = str(supposed_from)
118
119 fromOutside = self.isFromOutside(JID(barejid).getDomain())
120
121 """
122 if not JID(barejid).getDomain() in self._owner.servernames:
123 self.DEBUG("Presence from Outside","info")
124 fromOutside = True
125 """
126
127 self.DEBUG("The real from seems to be "+barejid, "info")
128 except:
129
130 self.DEBUG('Presence: Could not set barejid from jid: %s'%(str(jid)),'error')
131
132 """
133 if fromOutside == True:
134 if typ in ['subscribe','subscribed','unsubscribe','unsubscribed']:
135 self.DEBUG("Redirecting stanza to subscriber", "warn")
136 self.subscriber(session,stanza)
137 else:
138 # Find each session
139 s = None
140 # If it's our server
141 if to.getDomain() in self._owner.servernames:
142 s = self._owner.getsession(str(to))
143 if s == None:
144 # TODO: Store if it's real user
145 self.DEBUG("Could not find session for "+str(to),"error")
146 return
147 # Enqueue the message to the receiver
148 self.DEBUG("Redirecting stanza to receiver", "info")
149 p = Presence(to=s.peer,frm=stanza.getFrom(),typ=stanza.getType())
150
151
152 for child in stanza.getChildren():
153 if child.getName() == 'status' or child.getName() == 'Status':
154 p.setStatus(child.getData())
155 elif child.getName() == 'show' or child.getName() == 'Show':
156 p.setShow(child.getData())
157 elif child.getName() == 'priority' or child.getName() == 'Priority':
158 p.setPriority(child.getData())
159
160 s.enqueue(p)
161 raise NodeProcessed
162 else:
163 self.DEBUG("Stupid situation: from and to are outsiders. WTF?","error")
164 return
165 """
166
167
168 if not typ or typ=='available':
169 if fromOutside:
170
171 s = None
172 s = self._owner.getsession(str(to))
173 if s == None:
174
175 self.DEBUG("Could not find session for "+str(to),"warn")
176 return
177 stanza.setNamespace(NS_CLIENT)
178 s.enqueue(stanza)
179 raise NodeProcessed
180
181 else:
182
183 if not self._data.has_key(barejid): self._data[barejid]={}
184 if not self._data[barejid].has_key(resource): self._data[barejid][resource]=Presence(frm=jid,typ=typ)
185 bp=self._data[barejid][resource]
186
187 try: priority=int(stanza.getTagData('priority'))
188 except: priority=0
189 bp.T.priority=`priority`
190 self._owner.activatesession(session)
191
192 show=stanza.getTag('show')
193 if show: bp.T.show=show
194 else: bp.T.show=''
195 status=stanza.getTag('status')
196 if status: bp.T.status=status
197 else: bp.T.status=''
198 for x in bp.getTags('x',namespace='jabber:x:delay'):
199 bp.delChild(x)
200 bp.setTimestamp()
201 self.update(barejid)
202
203 self.DEBUG("available presence " + str(bp),'info')
204
205
206 self.broadcastAvailable(session)
207
208 if self._owner._socker != None:
209 self._owner._socker.add_data_root({'jid':{barejid:self._data[barejid].keys()}})
210 self._owner._socker.add_data({'jid':{barejid:self._data[barejid].keys()}})
211
212 elif (typ=='unavailable' or typ=='error'):
213
214 if not fromOutside:
215 jid_info = self._owner.tool_split_jid(barejid)
216 contacts = session.getRoster()
217 for k,v in contacts.iteritems():
218 if v['subscription'] in ['from','both']:
219 self.DEBUG('Un-Presence attempt for contact "%s":'%k,'warn')
220 p = Presence(to=k,frm=session.peer,typ='unavailable')
221 status=stanza.getTag('status')
222 if status: p.T.show=status
223 else: p.T.show='Logged Out'
224
225
226 k_jid = JID(k)
227
228 s = None
229
230 if k_jid.getDomain() in self._owner.servernames or k in self._owner.servernames:
231 s = self._owner.getsession(k)
232 if s == None:
233
234 pass
235 else:
236 s=self._owner.S2S(session.ourname,k_jid.getDomain())
237
238
239 if s != None:
240 s.enqueue(p)
241 else:
242 self.DEBUG('Could not find active session for contact %s'%(k),'warn')
243
244 else:
245
246 s = None
247 s = self._owner.getsession(str(to))
248 if s == None:
249
250 self.DEBUG("Could not find session for "+str(to),"warn")
251 return
252 stanza.setNamespace(NS_CLIENT)
253 s.enqueue(stanza)
254 raise NodeProcessed
255
256
257 self.DEBUG('Finished for "%s"'%k,'info')
258
259 if self._owner._socker != None:
260 self._owner._socker.remove_data_root(['jid',barejid])
261 self._owner._socker.remove_data(['jid',barejid])
262
263 if not self._data.has_key(barejid) and raiseFlag == True: raise NodeProcessed
264
265
266
267
268
269 elif typ=='invisible' and fromOutside == False:
270
271 jid_info = self._owner.tool_split_jid(barejid)
272 contacts = session.getRoster()
273 for k,v in contacts.iteritems():
274 self.DEBUG('Un-Presence attempt for contact [INVISIBLE!!!]"%s":'%k,'warn')
275 p = Presence(to=k,frm=session.peer,typ='unavailable')
276 status=stanza.getTag('status')
277 if status: p.T.show=status
278 else: p.T.show='Logged Out'
279 session.dispatch(p)
280 self.DEBUG('Finished for "%s" [INVISIBLE!!!]'%k,'info')
281
282 elif typ=='probe':
283 self.DEBUG('Probe activated!','info')
284 if stanza.getTo() in self._owner.servernames:
285 session.enqueue(Presence(to=stanza.getFrom(),frm=stanza.getTo()))
286 raise NodeProcessed
287 if stanza.getAttr('internal') == 'True':
288 self.DEBUG('Internal Probe activated!','info')
289 try:
290 resources=[stanza.getTo().getResource()]
291 if not resources[0]: resources=self._data[stanza.getTo()].keys()
292 flag=1
293 for resource in resources:
294 p=Presence(to=stanza.getFrom(),frm='%s/%s'%(stanza.getTo(),resource),node=self._data[stanza.getTo()][resource])
295 if flag:
296
297 flag=None
298 session.enqueue(p)
299 except KeyError: pass
300 else:
301 if not self.isFromOutside(stanza.getTo().getDomain()):
302
303 bareto = stanza.getTo().getStripped()
304
305 if self._data.has_key(bareto):
306
307 for resourceto in self._data[bareto].keys():
308 p = copy.copy(self._data[bareto][resourceto])
309 p.setTo(barejid)
310 s = None
311 if not fromOutside:
312 s = self._owner.getsession(barejid)
313 else:
314 s = self._owner.S2S(session.ourname,domain)
315 if s:
316 s.enqueue(p)
317 self.DEBUG('Probe '+str(p) +' sent','info')
318 raise NodeProcessed
319 session.enqueue(Presence(to=stanza.getFrom(),frm=stanza.getTo(),typ='unavailable'))
320 self.DEBUG('Probe "unavailable" sent','info')
321 raise NodeProcessed
322 else:
323 self.DEBUG("Probe message ignored",'warn')
324
325 elif typ in ['subscribe', 'subscribed', 'unsubscribe', 'unsubscribed']:
326 self.DEBUG("Redirecting stanza to subscriber", "warn")
327 self.subscriber(session, stanza)
328
329 else:
330 self.DEBUG('Woah, nothing to call???','warn')
331 if raiseFlag: raise NodeProcessed
332
334 try:
335
336 barejid = JID(session.peer).getStripped()
337 resource = JID(session.peer).getResource()
338 except:
339 fromOutside = True
340 self.DEBUG('Presence: Could not set barejid, fromOutside=True','warn')
341
342 contacts = session.getRoster()
343 if contacts == None: return
344
345
346
347
348 for x,y in contacts.items():
349
350 j = JID(x)
351 name = j.getNode(); domain = j.getDomain()
352 self.DEBUG('Presence attempt for contact "%s":'%x,'warn')
353
354 try:
355 if y['subscription'] in ['from','both']:
356
357
358 if self.isFromOutside(domain) \
359 or self._owner.DB.pull_roster(domain,name,barejid) != None:
360 if (x in self._owner.servernames):
361 self.DEBUG("Contact %s is the server. returning"%(str(x)),'warn')
362 return
363 self.DEBUG('Contact "%s" has from/both'%x,'warn')
364
365
366
367 s = None
368
369
370 pres = Presence(to=x,frm=session.peer,node=self._data[barejid][session.getResource()])
371 if not self.isFromOutside(domain) or x in self._owner.servernames:
372 s = self._owner.getsession(x)
373 if s == None:
374
375 pass
376 else:
377
378 s=self._owner.S2S(session.ourname,domain)
379
380
381
382 if s != None:
383 s.enqueue(pres)
384 self.DEBUG('Finished for "%s" (from/both)'%x,'info')
385
386 if y['subscription'] in ['to','both']:
387
388
389
390 if (x in self._owner.servernames) \
391 or self.isFromOutside(domain) \
392 or self._owner.DB.pull_roster(domain,name,barejid) != None:
393 self.DEBUG('Contact "%s" has to/both'%x,'warn')
394
395
396
397 if self._data.has_key(str(x)):
398
399 for res in self._data[str(x)].keys():
400 session.enqueue(self._data[x][res])
401 elif x in self._owner.servernames or str(x) in self._owner.servernames:
402
403 session.enqueue(Presence(to=session.peer, frm=str(x), typ='available'))
404 elif self.isFromOutside(domain):
405 s=self._owner.S2S(session.ourname,domain)
406 if s:
407 s.enqueue(Presence(to=x, frm=session.peer, typ='probe'))
408 else:
409
410 session.enqueue(Presence(to=session.peer, frm=str(x), typ='unavailable'))
411
412 self.DEBUG('Finished for "%s" (to/both)'%x,'info')
413
414 except Exception, err:
415 self.DEBUG("PRESENCE_BROADCAST_ERR: %s\nx:%s\ny:%s"%(err,x,y),'error')
416
418 self.DEBUG("Router update","info")
419 pri=-1
420 s=None
421 for resource in self._data[barejid].keys():
422 rpri=int(self._data[barejid][resource].getTagData('priority'))
423 if rpri>pri: s=self._owner.getsession(barejid+'/'+resource)
424 if s:
425 self._owner.activatesession(s,barejid)
426 else:
427 self._owner.deactivatesession(barejid)
428
429
459
461 """
462 Subscription manager that actually works (cough, cough, BoP, cough, cough ;-)
463
464 0. COMMON TASKS
465 0.1 Get 'from' and 'to'
466 0.2 Get the session of the receiver
467 """
468
469 try:
470 supposed_from = JID(session.peer)
471 if supposed_from.getNode() == '':
472 fromOutside = self.isFromOutside(JID(supposed_from).getDomain())
473 if fromOutside:
474 frm = str(stanza.getFrom())
475 else:
476 frm = str(JID(session.peer).getStripped())
477 else:
478 frm = str(JID(session.peer).getStripped())
479 fromOutside = False
480
481 except:
482 self.DEBUG('Could not state real from', 'error')
483 raise NodeProcessed
484
485 to = stanza['to']
486 session_jid = [to.getNode(), to.getDomain()]
487 jfrom_node = JID(session.peer).getNode()
488 jfrom_domain = JID(session.peer).getDomain()
489
490
491 if session_jid[0] == '': bareto = session_jid[1]
492 else: bareto = session_jid[0] + '@' + session_jid[1]
493
494
495 s = None
496 s = self._owner.getsession(bareto)
497 if s == None:
498 if self.isFromOutside(to.getDomain()):
499 s=self._owner.S2S(session.ourname,to.getDomain())
500
501 if s == None:
502 self.DEBUG("DANGER! There is still no session for the receiver","error")
503
504
505 raise NodeProcessed
506
507
508 if not fromOutside:
509 contact = self._owner.DB.pull_roster(str(jfrom_domain),str(jfrom_node),str(bareto))
510
511 else: contact = None
512
513
514 if not self.isFromOutside(to.getDomain()):
515 inbound = True
516 inbound_contact = self._owner.DB.pull_roster(to.getDomain(), to.getNode(), frm)
517 self.DEBUG("Inbound Contact: %s : %s"%(bareto,str(inbound_contact)),"warn")
518 else:
519 inbound = False
520
521 if not self.isFromOutside(jfrom_domain):
522 outbound = True
523 outbound_contact = self._owner.DB.pull_roster( str(jfrom_domain), str(jfrom_node), str(bareto))
524 self.DEBUG("Outbound Contact: %s : %s"%(frm,str(outbound_contact)),"warn")
525 else:
526 outbound = False
527
528
529 if stanza.getType() == "subscribe":
530
531 pass
532 """
533 1. SUBSCRIBE
534 1.2 Modify and push the sender's roster
535 1.3 Relay the presence stanza to the receiver
536 1.4 Do the victory dance and raise NodeProcessed
537 """
538
539 """
540 self.DEBUG("Checking if contact is already subscribed","info")
541 try:
542 if contact and contact['subscription'] in ['both', 'to']:
543 # We're ALREADY subscribed, we should dismiss this request to prevent
544 # infinite loops of presence stanzas
545 print "### CONTACT ALREADY SUBSCRIBED"
546 raise NodeProcessed
547 except KeyError:
548 # This contact wasn't in the roster or the subscription wasn't done
549 self.DEBUG("This contact wasn't in the roster or the subscription wasn't done","warn")
550 except AttributeError:
551 self.DEBUG("The subscription wasn't done","warn")
552 """
553
554
555
556
557 route=False
558 if inbound:
559
560 """
561 if contact and not fromOutside:
562 # Add 'ask' key to the roster
563 contact.update({'ask':'subscribe'})
564 self._owner.DB.save_to_roster(jfrom_domain, jfrom_node, bareto, contact)
565 elif not fromOutside:
566 """
567
568
569
570
571 if inbound_contact and inbound_contact.has_key('subscription'): subs = inbound_contact['subscription']
572 else: subs = "none"
573 if inbound_contact and inbound_contact.has_key('state'): state = inbound_contact['state']
574 else: state = ""
575
576
577
578 route = True
579 if subs == "none" and not state: state="pending_in"
580 elif subs == "none" and state == "pending_out": state = "pending_out_in"
581 elif subs == "to" and not state: state = "pending_in"
582 else: route = False
583
584
585
586 if subs in ['from','both']:
587 session.enqueue(Presence(frm=bareto,typ='subscribed',to=frm))
588 raise NodeProcessed
589
590 try:
591 if not inbound_contact: inbound_contact = {}
592 inbound_contact.update({'subscription':subs})
593 inbound_contact.update({'state':state})
594 self._owner.DB.save_to_roster(to.getDomain(), to.getNode(), frm, inbound_contact)
595
596 self._owner.ROSTER.RosterPushOneToClient(contact=frm,to=bareto,to_session=s)
597
598
599 except:
600 self.DEBUG("Could not create roster for client "+str(bareto), 'error')
601
602
603 if outbound:
604 try:
605
606 if outbound_contact and outbound_contact.has_key('subscription'):subs=outbound_contact['subscription']
607 else: subs = "none"
608 if outbound_contact and outbound_contact.has_key('state'): state = outbound_contact['state']
609 else: state = ""
610
611 if subs == "none" and not state: state="pending_out"
612 elif subs == "none" and state == "pending_in": state = "pending_out_in"
613 elif subs == "from" and not state: state = "pending_out"
614
615
616 if not outbound_contact: outbound_contact = {}
617 outbound_contact.update({'subscription':subs})
618 outbound_contact.update({'state':state})
619 if not subs or subs == "none": outbound_contact.update({'ask':'subscribe'})
620 self._owner.DB.save_to_roster(jfrom_domain, jfrom_node, bareto, outbound_contact)
621
622 self._owner.ROSTER.RosterPushOneToClient(contact=bareto,to=frm,to_session=session)
623
624 except:
625 self.DEBUG("Could not create roster for client "+str(frm), 'error')
626
627
628
629 if outbound or route:
630 self.DEBUG("Routing stanza to receiver: "+str(bareto),"info")
631 stanza.setFrom(frm)
632 stanza.setNamespace(NS_CLIENT)
633 s.enqueue(stanza)
634
635
636
637
638
639
640 raise NodeProcessed
641
642 elif stanza.getType() == "subscribed":
643
644 """
645 2. SUBSCRIBED
646 2.1 Relay the presence stanza to the receiver
647 2.2 Modify and push the receiver's roster
648 2.2.2 Modify and push the sender's roster ??
649 2.3 Send a presence probe on behalf of the sender
650 """
651 route=False
652 if inbound:
653
654 try:
655
656 if inbound_contact and inbound_contact.has_key('subscription'): subs = inbound_contact['subscription']
657 else: subs = "none"
658 if inbound_contact and inbound_contact.has_key('state'): state = inbound_contact['state']
659 else: state = ""
660
661 route = True
662 if subs == "none" and state == "pending_out": subs = "to"; state = ""
663 elif subs == "none" and state == "pending_out_in": subs = "to"; state = "pending_in"
664 elif subs == "from" and state == "pending_out": subs = "both"; state = ""
665 elif subs == "from" and not state: subs = "both"
666 else: route = False
667
668 if not inbound_contact: inbound_contact = {}
669 inbound_contact.update({'subscription':subs})
670 inbound_contact.update({'state':state})
671 if inbound_contact.has_key('ask'): del inbound_contact['ask']
672 self._owner.DB.save_to_roster(to.getDomain(), to.getNode(), frm, inbound_contact)
673
674
675 self._owner.ROSTER.RosterPushOneToClient(contact=frm, to=bareto, to_session=s)
676
677 except:
678 self.DEBUG("Could not create roster for client "+str(bareto), 'error')
679
680 if outbound:
681 try:
682
683 if outbound_contact and outbound_contact.has_key('subscription'): subs = outbound_contact['subscription']
684 else: subs = None
685 if outbound_contact and outbound_contact.has_key('state'): state = outbound_contact['state']
686 else: state = None
687
688 if subs == "none" and state == "pending_in": subs = "from"; state = ""; route = True
689 elif subs == "none" and state == "pending_out_in": subs = "from"; state = "pending_out"; route = True
690 elif subs == "to" and state == "pending_in": subs = "both"; state = ""; route = True
691
692 if not outbound_contact: outbound_contact = {}
693 outbound_contact.update({'subscription':subs})
694 outbound_contact.update({'state':state})
695 self._owner.DB.save_to_roster(jfrom_domain, jfrom_node, bareto, outbound_contact)
696
697
698 self._owner.ROSTER.RosterPushOneToClient(contact=bareto,to=frm, to_session=session)
699
700 except:
701 self.DEBUG("Could not create roster for client "+str(frm), 'error')
702
703 if route:
704 stanza.setFrom(frm)
705 stanza.setNamespace(NS_CLIENT)
706 s.enqueue(stanza)
707 self.DEBUG("Subscribed-stanza relied to proper client","ok")
708
709
710 try:
711 barefrom = JID(frm).getStripped()
712 if self._data.has_key(barefrom):
713 for pres in self._data[barefrom].values():
714 pres_c = copy.copy(pres)
715 pres_c.setType('available')
716 pres_c.setTo(bareto)
717 s.enqueue(pres_c)
718 except Exception, e:
719 print "### EXCEPTION " + str(e)
720
721
722
723
724 raise NodeProcessed
725
726 elif stanza.getType() == "unsubscribe":
727
728 """
729 3. UNSUBSCRIBE
730 3.1 Check if the contact is already subscribed
731 3.2 Modify and push the sender's roster
732 3.3 Relay the presence stanza to the receiver
733 3.4 Send the sender (wow) an 'unsubscribed' presence probe on behalf of the receiver
734 3.5 Send the sender (wowwow) probes of 'unavailable' on behalf of the receiver
735 """
736
737 route = False
738 if inbound:
739
740
741 try:
742
743 if inbound_contact and inbound_contact.has_key('subscription'): subs = inbound_contact['subscription']
744 else: subs = "none"
745 if inbound_contact and inbound_contact.has_key('state'): state = inbound_contact['state']
746 else: state = ""
747
748 if subs == "none" and state == "pending_in": state=""; route = True
749 elif subs == "none" and state == "pending_out_in": state = "pending_out"; route = True
750 elif subs == "to" and state == "pending_in": state=""; route = True
751 elif subs == "from" and not state : subs="none"; route = True
752 elif subs == "from" and state == "pending_out" : subs="none"; route = True
753 elif subs == "both" and not state : subs="to"; route = True
754
755 if not inbound_contact: inbound_contact = {}
756 inbound_contact.update({'subscription':subs})
757 inbound_contact.update({'state':state})
758 self._owner.DB.save_to_roster(to.getDomain(), to.getNode(), frm, inbound_contact)
759
760 self._owner.ROSTER.RosterPushOneToClient(contact=frm,to=bareto,to_session=s)
761
762 except:
763 self.DEBUG("Could not create roster for client "+str(bareto), 'error')
764
765
766 if outbound:
767 try:
768
769 if outbound_contact and outbound_contact.has_key('subscription'):subs=outbound_contact['subscription']
770 else: subs = "none"
771 if outbound_contact and outbound_contact.has_key('state'): state = outbound_contact['state']
772 else: state = ""
773
774 if subs == "none" and state == "pending_out": state=""
775 elif subs == "none" and state == "pending_out_in": state = "pending_in"
776 elif subs == "to" and not state: subs = "none"
777 elif subs == "to" and state == "pending_in" : subs="none"
778 elif subs == "from" and state == "pending_out" : state=""
779 elif subs == "both" and not state : subs="from"
780
781 if not outbound_contact: outbound_contact = {}
782 outbound_contact.update({'subscription':subs})
783 outbound_contact.update({'state':state})
784 self._owner.DB.save_to_roster(jfrom_domain, jfrom_node, bareto, outbound_contact)
785
786 self._owner.ROSTER.RosterPushOneToClient(contact=bareto,to=frm,to_session=session)
787
788 except:
789 self.DEBUG("Could not create roster for client "+str(frm), 'error')
790
791
792 if outbound or route:
793 stanza.setFrom(frm)
794 stanza.setNamespace(NS_CLIENT)
795 s.enqueue(stanza)
796 if route:
797 session.enqueue(Presence(to=frm,frm=bareto,typ="unsubscribed"))
798
799 raise NodeProcessed
800
801
802 """
803 for pres in self._data[bareto].values():
804 p = copy.copy(pres)
805 p.setType('unavailable')
806 p.setTo(frm)
807 session.enqueue(p)
808 """
809
810 raise NodeProcessed
811
812
813 elif stanza.getType() == "unsubscribed":
814 pass
815
816 """
817 4. UNSUBSCRIBED
818 4.1 Relay the presence stanza to the receiver
819 4.2 Modify and push the receiver and sender rosters
820 """
821
822 route = False
823 if inbound:
824
825 try:
826
827 if inbound_contact and inbound_contact.has_key('subscription'): subs = inbound_contact['subscription']
828 else: subs = "none"
829 if inbound_contact and inbound_contact.has_key('state'): state = inbound_contact['state']
830 else: state = ""
831
832 if subs == "none" and state == "pending_out": subs = "none"; state = ""; route = True
833 elif subs == "none" and state == "pending_out_in": subs = "none"; state = "pending_in"; route = True
834 elif subs == "to" and not state: subs = "none"; route = True
835 elif subs == "to" and state == "pending_in": subs = "none"; route = True
836 elif subs == "from" and state == "pending_out": subs = "from"; route = True
837 elif subs == "both" and not state: subs = "from"; route = True
838
839 if not inbound_contact: inbound_contact = {}
840 inbound_contact.update({'subscription':subs})
841 inbound_contact.update({'state':state})
842 self._owner.DB.save_to_roster(to.getDomain(), to.getNode(), frm, inbound_contact)
843
844
845 self._owner.ROSTER.RosterPushOneToClient(contact=frm,to=bareto,to_session=s)
846
847 except:
848 self.DEBUG("Could not create roster for client "+str(bareto), 'error')
849
850 if outbound:
851 try:
852
853 if outbound_contact and outbound_contact.has_key('subscription'): subs = outbound_contact['subscription']
854 else: subs = "none"
855 if outbound_contact and outbound_contact.has_key('state'): state = outbound_contact['state']
856 else: state = ""
857
858 if subs == "none" and state == "pending_in": state = ""; route = True
859 elif subs == "none" and state == "pending_out_in": state = "pending_out"; route = True
860 elif subs == "to" and state == "pending_in": state = ""; route = True
861 elif subs == "from" and not state: subs = "none"; route = True
862 elif subs == "from" and state == "pending_out": subs = "none"; route = True
863 elif subs == "both" and not state: subs = "to"; route = True
864
865 if not outbound_contact: outbound_contact = {}
866 outbound_contact.update({'subscription':subs})
867 outbound_contact.update({'state':state})
868 self._owner.DB.save_to_roster(jfrom_domain, jfrom_node, bareto, outbound_contact)
869
870
871 self._owner.ROSTER.RosterPushOneToClient(contact=bareto, to=frm, to_session=session)
872
873
874 except:
875 self.DEBUG("Could not create roster for client "+str(frm), 'error')
876
877 if route:
878 stanza.setFrom(frm)
879 stanza.setNamespace(NS_CLIENT)
880 s.enqueue(stanza)
881
882 """
883 # 4.3 Send the receiver probes of 'unavailable' on behalf of the sender
884 # This is highly optional, so we don't do it
885 self.DEBUG("Now, we are going to send 'unavailable' probes on behalf of the client "+str(frm), 'warn')
886 for pres in self._data[frm].values():
887 pres.setType('unavailable')
888 s.enqueue(pres)
889 """
890
891 raise NodeProcessed
892
893
894
895
896 """
897 def balance_of_presence(self,session,stanza):
898 "Figures-out what should be done to a particular contact"
899 self.DEBUG('###BoP: SYSTEM PASS-THROUGH INSTIGATED [%s]'%unicode(stanza).encode('utf-8'),'warn')
900 #Predefined settings
901 # ["subscribe", "subscribed", "unsubscribe", "unsubscribed"]
902
903 #Stanza Stuff
904 try:
905 frm=stanza['from']
906 frm_node=frm.getNode()
907 frm_domain=frm.getDomain()
908 outfrom=frm_node+'@'+frm_domain
909 self.DEBUG('###BoP: RECIEVED STANZA WITH \'FROM\' ATTR','warn')
910 except:
911 frm = None
912 self.DEBUG('###BoP: RECIEVED STANZA WITHOUT \'FROM\' ATTR','warn')
913
914
915 component = False
916 session_jid = session.getSplitJID()
917 to=stanza['to']
918 if not to: return # Not for us.
919 to_node=to.getNode()
920 #if not to_node: return # Yep, not for us.
921 to_domain=to.getDomain()
922 if str(to_domain) in self._owner.components.keys(): component = True
923 if not component or (component and to_node): bareto=to_node+'@'+to_domain
924 else: bareto = to_domain
925
926 if component:
927 s = self._owner.getsession(to)
928 if s:
929 s.enqueue(stanza)
930 raise NodeProcessed
931
932
933 #bareto=to_node+'@'+to_domain
934
935 # 1. If the user wants to request a subscription to the contact's presence information,
936 # the user's client MUST send a presence stanza of type='subscribe' to the contact:
937
938 if stanza.getType() == 'subscribe':
939 if not self.isFromOutside(session_jid[1]) and frm == None:
940 self.DEBUG('###BoP: TYP=SUBSCRIBE;U->C','warn')
941
942 # 2. As a result, the user's server MUST initiate a second roster push to all of the user's
943 # available resources that have requested the roster, setting the contact to the pending
944 # sub-state of the 'none' subscription state; this pending sub-state is denoted by the
945 # inclusion of the ask='subscribe' attribute in the roster item:
946 #
947 # Note: If the user did not create a roster item before sending the subscription request,
948 # the server MUST now create one on behalf of the user:
949
950 '''
951 <iq type='set' id='set1'>
952 <query xmlns='jabber:iq:roster'>
953 <item
954 jid='contact@example.org'
955 subscription='none'
956 ask='subscribe'>
957 </item>
958 </query>
959 </iq>
960 '''
961
962
963 rsess = Iq(typ='set')
964 rsess.T.query.setNamespace(NS_ROSTER)
965 newitem = rsess.T.query.NT.item
966 newitem.setAttr('jid',bareto)
967 newitem.setAttr('ask','subscribe')
968 # Subscription?
969 #Dispatch?
970 session.dispatch(rsess)
971 self._owner.ROSTER.RosterAdd(session,rsess) #add to roster!
972
973 #{'attr':{'ask':'subscribe'}}
974 self._owner.ROSTER.RosterPushOne(session,stanza) #We'll let roster services take the bullet.
975
976 # 3. The user's server MUST also stamp the presence stanza of type "subscribe" with the user's
977 # bare JID (i.e., <user@example.com>) as the 'from' address (if the user provided a 'from'
978 # address set to the user's full JID, the server SHOULD remove the resource identifier). If
979 # the contact is served by a different host than the user, the user's server MUST route the
980 # presence stanza to the contact's server for delivery to the contact (this case is assumed
981 # throughout; however, if the contact is served by the same host, then the server can simply
982 # deliver the presence stanza directly):
983
984 stanza.setFrom(session.getBareJID())
985 self.DEBUG('###BoP: TYP=SUBSCRIBE;U->C [DONE]','warn')
986 elif not self.isFromOutside(to_domain) and frm != None:
987 self.DEBUG('###BoP: THE UN-EXPECTED WAS TRIGGERED','warn')
988 pass
989 elif stanza.getType() == 'subscribed':
990
991 # 5. As a result, the contact's server (1) MUST initiate a roster push to all available resources
992 # associated with the contact that have requested the roster, containing a roster item for the
993 # user with the subscription state set to 'from' (the server MUST send this even if the contact
994 # did not perform a roster set); (2) MUST return an IQ result to the sending resource indicating
995 # the success of the roster set; (3) MUST route the presence stanza of type "subscribed" to the user,
996 # first stamping the 'from' address as the bare JID (<contact@example.org>) of the contact; and
997 # (4) MUST send available presence from all of the contact's available resources to the user:
998 '''
999 <iq type='set' to='contact@example.org/resource'>
1000 <query xmlns='jabber:iq:roster'>
1001 <item
1002 jid='user@example.com'
1003 subscription='from'
1004 name='SomeUser'>
1005 <group>SomeGroup</group>
1006 </item>
1007 </query>
1008 </iq>
1009 '''
1010 if not self.isFromOutside(session_jid[1]) and frm != None:
1011 self.DEBUG('###BoP: TYP=SUBSCRIBED;C->U','warn')
1012 roster = self._owner.DB.pull_roster(session_jid[1],session_jid[0],bareto)
1013 if roster == None:
1014 self.DEBUG('###BoP: TYP=SUBSCRIBED;U->C [NO ROSTER; KILLING NODEPROCESS!','error')
1015 raise NodeProcessed
1016 rsess = Iq(typ='set')
1017 rsess.NT.query.setNamespace(NS_ROSTER)
1018 newitem = rsess.T.query.NT.item
1019 newitem.setAttr('jid',bareto)
1020 self.DEBUG('###BoP: TYP=SUBSCRIBED;U->C SUBSCRIPTION=%s'%roster['subscription'],'warn')
1021 if roster['subscription'] != 'to':
1022 self.DEBUG('###BoP: TYP=SUBSCRIBED;U->C [TO IS NOT ACTIVE!]','warn')
1023 newitem.setAttr('subscription','from')
1024 else:
1025 self.DEBUG('###BoP: TYP=SUBSCRIBED;U->C [TO IS ACTIVE!]','warn')
1026 newitem.setAttr('subscription','both')
1027 newitem.setAttr('ask','InternalDelete')
1028 self._owner.ROSTER.RosterAdd(session,rsess) #add to roster!
1029
1030 self._owner.ROSTER.RosterPushOne(session,stanza) #,{'attr':{'ask':'subscribe'}})
1031 barejid = session.getBareJID()
1032 stanza.setFrom(barejid)
1033 session.dispatch(stanza)
1034 s=None
1035 for resource in self._data[barejid].keys():
1036 s=self._owner.getsession(barejid+'/'+resource)
1037 if s: self.broadcastAvailable(s)
1038 self.DEBUG('###BoP: TYP=SUBSCRIBED;C->U [DONE]','warn')
1039 self.DEBUG('###BoP: PASS-THROUGH COMPLETE','warn')
1040 raise NodeProcessed
1041 return session,stanza
1042
1043 # 6. Upon receiving the presence stanza of type "subscribed" addressed to the user, the user's
1044 # server MUST first verify that the contact is in the user's roster with either of the following
1045 # states: (a) subscription='none' and ask='subscribe' or (b) subscription='from' and ask='subscribe'.
1046 # If the contact is not in the user's roster with either of those states, the user's server MUST
1047 # silently ignore the presence stanza of type "subscribed" (i.e., it MUST NOT route it to the user,
1048 # modify the user's roster, or generate a roster push to the user's available resources). If the
1049 # contact is in the user's roster with either of those states, the user's server (1) MUST deliver
1050 # the presence stanza of type "subscribed" from the contact to the user; (2) MUST initiate a roster
1051 # push to all of the user's available resources that have requested the roster, containing an updated
1052 # roster item for the contact with the 'subscription' attribute set to a value of "to"; and (3) MUST
1053 # deliver the available presence stanza received from each of the contact's available resources to
1054 # each of the user's available resources:
1055 elif not self.isFromOutside(to_domain) and frm == None:
1056 self.DEBUG('###BoP: TYP=SUBSCRIBED;U->C','warn')
1057 roster = self._owner.DB.pull_roster(to_domain,to_node,outfrom)
1058 if roster == None: raise NodeProcessed
1059 ask_good = False
1060 subscription_good = False
1061 from_active = False
1062 for x,y in roster.iteritems():
1063 if x=='ask' and y=='subscribe': ask_good = True
1064 if x=='subscription' and y in ['none','from']: subscription_good = True
1065 if y == 'from': from_active = True
1066 if subscription_good==True and ask_good==True: break
1067
1068 if subscription_good!=True and ask_good!=True: raise NodeProcessed
1069
1070 rsess = Iq(typ='set')
1071 rsess.T.query.setNamespace(NS_ROSTER)
1072 newitem = rsess.T.query.NT.item
1073 newitem.setAttr('jid',outfrom)
1074 if from_active == True:
1075 self.DEBUG('###BoP: TYP=SUBSCRIBED;U->C [FROM IS ACTIVE!]','warn')
1076 newitem.setAttr('subscription','both')
1077 else:
1078 self.DEBUG('###BoP: TYP=SUBSCRIBED;U->C [FROM IS NOT ACTIVE!]','warn')
1079 newitem.setAttr('subscription','to')
1080 newitem.setAttr('ask','InternalDelete')
1081 self._owner.ROSTER.RosterAdd(session,rsess) #add to roster!
1082
1083 self._owner.ROSTER.RosterPushOne(session,stanza) #,{'attr':{'ask':'subscribe'}})
1084 self.DEBUG('###BoP: TYP=SUBSCRIBED;U->C [DONE]','warn')
1085 elif stanza.getType() == 'unsubscribe':
1086
1087 if not self.isFromOutside(session_jid[1]) and frm == None:
1088 self.DEBUG('###BoP: TYP=UNSUBSCRIBE;U->C','warn')
1089 roster = self._owner.DB.pull_roster(session_jid[1],session_jid[0],bareto)
1090 if roster == None: raise NodeProcessed
1091 rsess = Iq(typ='set')
1092 rsess.T.query.setNamespace(NS_ROSTER)
1093 newitem = rsess.T.query.NT.item
1094 newitem.setAttr('jid',outfrom)
1095 if roster['subscription'] == 'both':
1096 newitem.setAttr('subscription','from')
1097 else:
1098 newitem.setAttr('subscription','none')
1099 newitem.setAttr('ask','InternalDelete')
1100 self._owner.ROSTER.RosterAdd(session,rsess) #add to roster!
1101
1102 self._owner.ROSTER.RosterPushOne(session,stanza) #,{'attr':{'ask':'subscribe'}})
1103 self.DEBUG('###BoP: TYP=UNSUBSCRIBE;U->C [DONE]','warn')
1104
1105 if not self.isFromOutside(to_domain) and frm != None:
1106 self.DEBUG('###BoP: TYP=UNSUBSCRIBE;C->U','warn')
1107 roster = self._owner.DB.pull_roster(to_domain,to_node,outfrom)
1108 if roster == None: raise NodeProcessed
1109 rsess = Iq(typ='set')
1110 rsess.T.query.setNamespace(NS_ROSTER)
1111 newitem = rsess.T.query.NT.item
1112 newitem.setAttr('jid',outfrom)
1113 if roster['subscription'] == 'both':
1114 newitem.setAttr('subscription','to')
1115 else:
1116 newitem.setAttr('subscription','none')
1117 newitem.setAttr('ask','InternalDelete')
1118 self._owner.ROSTER.RosterAdd(session,rsess) #add to roster!
1119
1120 self._owner.ROSTER.RosterPushOne(session,stanza) #,{'attr':{'ask':'subscribe'}})
1121 self.DEBUG('###BoP: TYP=UNSUBSCRIBE;C->U [DONE]','warn')
1122 elif stanza.getType() == 'unsubscribed':
1123 self.DEBUG('###BoP: TYP=UNSUBSCRIBED','warn')
1124
1125 # 1. If the contact wants to refuse the request, the contact's client MUST send a presence stanza of
1126 # type "unsubscribed" to the user (instead of the presence stanza of type "subscribed" sent in Step
1127 # 6 of Section 8.2):
1128
1129 # 2. As a result, the contact's server MUST route the presence stanza of type "unsubscribed" to the user,
1130 # first stamping the 'from' address as the bare JID (<contact@example.org>) of the contact:
1131 if not self.isFromOutside(session_jid[1]) and frm == None:
1132 stanza.setFrom(session.getBareJID())
1133
1134 # Note: If the contact's server previously added the user to the contact's roster for tracking purposes,
1135 # it MUST remove the relevant item at this time.
1136 self._owner.DB.del_from_roster(session_jid[1],session_jid[0],bareto)
1137
1138 # 3. Upon receiving the presence stanza of type "unsubscribed" addressed to the user, the user's server
1139 # (1) MUST deliver that presence stanza to the user and (2) MUST initiate a roster push to all of the
1140 # user's available resources that have requested the roster, containing an updated roster item for the
1141 # contact with the 'subscription' attribute set to a value of "none" and with no 'ask' attribute:
1142
1143 if not self.isFromOutside(to_domain) and frm != None:
1144 self.DEBUG('###BoP: TYP=UNSUBSCRIBED;C->U','warn')
1145 roster = self._owner.DB.pull_roster(to_domain,to_node,outfrom)
1146 if roster == None: raise NodeProcessed
1147 rsess = Iq(typ='set')
1148 rsess.T.query.setNamespace(NS_ROSTER)
1149 newitem = rsess.T.query.NT.item
1150 newitem.setAttr('jid',outfrom)
1151 if roster['subscription'] == 'to':
1152 newitem.setAttr('subscription','none')
1153 elif roster['subscription'] == 'both':
1154 newitem.setAttr('subscription','from')
1155 else:
1156 newitem.setAttr('subscription','none')
1157 newitem.setAttr('ask','InternalDelete')
1158 self._owner.ROSTER.RosterAdd(session,rsess) #add to roster!
1159
1160 self._owner.ROSTER.RosterPushOne(session,stanza) #,{'attr':{'ask':'subscribe'}})
1161 p=Presence(to=outfrom,frm=bareto,typ='unavailable')
1162 p.setNamespace(NS_CLIENT)
1163 session.dispatch(p)
1164 self.DEBUG('###BoP: TYP=UNSUBSCRIBED;C->U [DONE]','warn')
1165
1166 self.DEBUG('###BoP: PASS-THROUGH COMPLETE','warn')
1167 return session,stanza
1168 """
1169
1171 karma = s.getKarma()
1172 data_len = len(unicode(stanza))
1173 if karma != None and time.time() - karma['last_time'] >= 60:
1174 karma['last_time'] == time.time()
1175 karma['tot_up'] = 0
1176 karma['tot_down'] = 0
1177 if karma != None and karma['tot_up'] + data_len > karma['up']:
1178 s.send(Error(stanza,ERR_NOT_ALLOWED))
1179 raise NodeProcessed
1180 else:
1181 if karma != None:
1182 karma['tot_up'] += data_len
1183 s.updateKarma(karma)
1184
1190
1191
1193 """ XMPP-Core 9.1.1 rules """
1194
1195 name=stanza.getName()
1196 self.DEBUG('Router handler called','info')
1197
1198
1199 if name == "presence":
1200
1201 return
1202
1203 try:
1204 self.DEBUG('with stanza %s'%(str(stanza)),'info')
1205 except:
1206 self.DEBUG('with UNKNOWN stanza','info')
1207
1208
1209
1210
1211
1212
1213
1214 """
1215 # Sometimes, a presence stanza arrives here. Let's redirect it to presenceHandler
1216 if name == "presence" and stanza.getNamespace() == NS_SERVER:
1217 """
1218
1219 to=stanza['to']
1220 if stanza.getNamespace()==NS_CLIENT and \
1221 (not to or to==session.ourname) and \
1222 stanza.props in ( [NS_AUTH], [NS_REGISTER], [NS_BIND], [NS_SESSION] ):
1223 return
1224
1225 try:
1226 if not session.trusted and session.peer != '__ir__@127.0.0.1/ROUTER': self.safeguard(session,stanza)
1227 except:
1228 self.DEBUG("NOT SAFEGUARD","error")
1229
1230 if not to:
1231 stanza.setTo(session.ourname)
1232 to=stanza['to']
1233
1234
1235 if self.pluginRelay(session,stanza) and raiseFlag: raise NodeProcessed
1236 self.DEBUG("Stanza not for a plugin","warn")
1237
1238
1239
1240
1241 domain=to.getDomain()
1242
1243
1244 component = False
1245 """
1246 component_jids = []
1247 try:
1248 for v in self._owner.components.values():
1249 print "V: "+ str(v)
1250 if v.has_key('jid'):
1251 component_jids.append(v['jid'])
1252 except Exception, e:
1253 print str(e)
1254 """
1255
1256
1257 getsession=self._owner.getsession
1258 if not self.isFromOutside(domain):
1259
1260 for v in self._owner.components.values():
1261 try:
1262
1263 if v['jid'] in domain:
1264 component = True
1265 break
1266 except:
1267 pass
1268
1269
1270 node=to.getNode()
1271 if not node and not component:
1272 return
1273
1274 if not component or (component and node): bareto=node+'@'+domain
1275 else: bareto = domain
1276 resource=to.getResource()
1277
1278
1279
1280
1281
1282
1283 try:
1284 rpri=int(self._data[bareto][resource].getTagData('priority'))
1285 if rpri<0:
1286 session.enqueue(Error(stanza,ERR_SERVICE_UNAVAILABLE))
1287 return
1288 except:
1289 rpri = None
1290 if resource and rpri != None and rpri>-1:
1291 to=bareto+'/'+resource
1292 s=getsession(to)
1293 if s:
1294 s.enqueue(stanza)
1295 if raiseFlag: raise NodeProcessed
1296
1297
1298
1299
1300
1301
1302
1303
1304
1305 if component:
1306 node,domain = domain.split(".",1)
1307 if not self._owner.AUTH.isuser(node,domain):
1308 if name in ['iq','message']:
1309 if stanza.getType()<>'error': session.enqueue(Error(stanza,ERR_SERVICE_UNAVAILABLE))
1310 if raiseFlag: raise NodeProcessed
1311
1312
1313
1314
1315
1316 if resource and name<>'message':
1317 self.intra_route(stanza)
1318 if name=='iq' and stanza.getType()<>'error': session.enqueue(Error(stanza,ERR_SERVICE_UNAVAILABLE))
1319 if raiseFlag: raise NodeProcessed
1320
1321
1322
1323 pri=-1
1324 highest_pri = {'pri':0,'s':None}
1325 s=None
1326 try:
1327 for resource in self._data[bareto].keys():
1328 rpri=int(self._data[bareto][resource].getTagData('priority'))
1329 if rpri>pri and rpri>=highest_pri['pri']:
1330 highest_pri['pri'] = rpri
1331 highest_pri['s'] = self._owner.getsession(bareto+'/'+resource)
1332
1333 if highest_pri['s'] != None:
1334 s=highest_pri['s']
1335 else:
1336 s=getsession(to)
1337 except:
1338 s=getsession(to)
1339 if s:
1340
1341
1342
1343
1344
1345
1346
1347
1348
1349
1350 if name=='message':
1351 s.enqueue(stanza)
1352 if raiseFlag: raise NodeProcessed
1353
1354
1355
1356
1357
1358
1359 elif name=='presence':
1360 self.DEBUG('Presence stanza detected! (%s)'%stanza['to'],'warn')
1361 if stanza.getType() == 'probe' and stanza['to'].getDomain() in self._owner.servernames:
1362 stanza.setAttr('internal','True')
1363 self.presenceHandler(session,stanza,raiseFlag)
1364
1365 if stanza.getType() in ["subscribe", "subscribed", "unsubscribe", "unsubscribed"]:
1366
1367 session,stanza = self.subscriber(session,stanza)
1368
1369
1370 ps = None
1371 for resource in self._data[bareto].keys():
1372 ps=getsession(bareto+'/'+resource)
1373 if ps: ps.enqueue(stanza)
1374 if raiseFlag: raise NodeProcessed
1375
1376
1377
1378
1379
1380
1381 if name=='iq':
1382 s.enqueue(stanza)
1383 if raiseFlag: raise NodeProcessed
1384 return
1385
1386
1387 else:
1388 self.intra_route(stanza)
1389
1390
1391
1392
1393
1394
1395 if name=='presence':
1396 if stanza.getType() == 'probe' and stanza['to'].getDomain() in self._owner.servernames:
1397 stanza.setAttr('internal','True')
1398 self.presenceHandler(session,stanza,raiseFlag)
1399
1400 if stanza.getType() in ["subscribe", "subscribed", "unsubscribe", "unsubscribed"]:
1401
1402 session,stanza = self.subscriber(session,stanza)
1403
1404
1405
1406
1407 if raiseFlag: raise NodeProcessed
1408
1409
1410
1411
1412
1413
1414 elif name=='message':
1415
1416
1417 if raiseFlag: raise NodeProcessed
1418
1419
1420
1421
1422 return
1423 else:
1424 s=getsession(domain)
1425 if not s:
1426 s=self._owner.S2S(session.ourname,domain)
1427
1428 s.enqueue(stanza)
1429 if raiseFlag: raise NodeProcessed
1430