Changeset 660

Show
Ignore:
Timestamp:
05/12/08 10:26:46 (7 months ago)
Author:
sylvain
Message:

support for in-band registration

Files:

Legend:

Unmodified
Added
Removed
Modified
Copied
Moved
  • oss/headstock/headstock/api/dataform.py

    r450 r660  
    1111        self.type = form_type 
    1212        self.reported = reported 
     13        self.instructions = None 
    1314        self.title = None 
    1415        self.fields = [] 
     
    2324                return field 
    2425     
    25     def from_element(cls, e): 
    26         d = Data(unicode(e.get_attribute('type'))) 
     26    @staticmethod 
     27    def from_element(e): 
     28        d = Data(e.get_attribute_value('type')) 
    2729        title = e.get_child('title', e.xml_ns) 
    2830        if title: 
    2931            d.title = title.xml_text 
     32 
     33        instructions = e.get_child('instructions', e.xml_ns) 
     34        if instructions: 
     35            d.instructions = instructions.xml_text 
    3036 
    3137        fields = e.get_children('field', e.xml_ns) 
     
    3844 
    3945        return d 
    40     from_element = classmethod(from_element) 
    4146 
    42     def to_element(cls, d, parent=None): 
     47    @staticmethod 
     48    def to_element(d, parent=None): 
    4349        x = E(u'x', attributes={u'type': d.type}, 
    4450              namespace=XMPP_DATA_FORM_NS, parent=parent) 
    4551        for field in d.fields: 
    4652            Field.to_element(field, parent=x) 
    47     to_element = classmethod(to_element) 
     53        for item in d.items: 
     54            Item.to_element(item, parent=x) 
    4855                    
    4956class Field(object): 
     
    6067        return '<Field "%s" (%s) at %s>' % (self.type or '', self.var or '', hex(id(self))) 
    6168     
    62     def from_element(cls, e): 
    63         f = Field() 
    64         f.type = e.get_attribute('type') 
    65         if f.type: f.type = unicode(f.type) 
    66         f.var = e.get_attribute('var') 
    67         if f.var: f.var = unicode(f.var) 
    68         f.label = e.get_attribute('label') 
    69         if f.label: f.label = unicode(f.label) 
    70         required = e.get_child('required') 
     69    @staticmethod 
     70    def from_element(e): 
     71        f = Field(field_type=e.get_attribute_value('type'), 
     72                  var=e.get_attribute_value('var')) 
     73        f.label = e.get_attribute_value('label') 
     74        required = e.get_child('required', e.xml_ns) 
    7175        if required and required == 'true': 
    7276            f.required = True 
    73         desc = e.get_child('desc'
     77        desc = e.get_child('desc', e.xml_ns
    7478        if desc: 
    7579            f.desc = desc.xml_text 
     
    8488 
    8589        return f 
    86     from_element = classmethod(from_element) 
    8790 
    88     def to_element(cls, field, parent=None): 
     91    @staticmethod 
     92    def to_element(field, parent=None): 
    8993        attrs = {} 
    9094        if field.var: attrs[u'var'] = field.var 
     
    9599            E(u'value', content=value, 
    96100              namespace=XMPP_DATA_FORM_NS, parent=f) 
    97     to_element = classmethod(to_element) 
    98101     
    99102class Option(object): 
     
    105108        return '<Option "%s" at %s>' % (self.value, hex(id(self))) 
    106109     
    107     def from_element(cls, e): 
    108         o = Option() 
    109         o.value = e.get_child('value').xml_text 
    110         label = e.get_child('label') 
    111         if label: 
    112             o.label = label.xml_text 
     110    @staticmethod 
     111    def from_element(e): 
     112        o = Option(e.get_child('value', e.xml_ns).xml_text, 
     113                   e.get_attribute_value('label')) 
    113114        return o 
    114     from_element = classmethod(from_element) 
    115115 
     116    @staticmethod 
     117    def to_element(e, parent=None): 
     118        option = E(u'option', namespace=XMPP_DATA_FORM_NS,  
     119                   attributes={u'label': e.label}, parent=parent) 
     120        E(u'value', namespace=XMPP_DATA_FORM_NS,  
     121          content=e.value, parent=option) 
     122        return option 
     123 
     124         
    116125class Item(object): 
    117126    def __init__(self): 
     
    121130        return '<Item at %s>' % (hex(id(self)),) 
    122131     
    123     def from_element(cls, e): 
     132    @staticmethod 
     133    def from_element(e): 
    124134        i = Item() 
    125135        fields = e.get_children('field', e.xml_ns) 
     
    128138 
    129139        return i 
    130     from_element = classmethod(from_element) 
     140 
     141    @staticmethod 
     142    def to_element(e, parent=None): 
     143        item = E(u'item', namespace=XMPP_DATA_FORM_NS, parent=parent) 
     144        for field in e.fields: 
     145            Field.to_element(field, parent=item) 
     146        return item 
  • oss/headstock/headstock/api/discovery.py

    r654 r660  
    1 #!/usr/bin/env python 
    21# -*- coding: utf-8 -*- 
    3  
    42 
    53from headstock.lib.utils import generate_unique 
  • oss/headstock/headstock/api/registration.py

    r450 r660  
    1 #!/usr/bin/env python 
    21# -*- coding: utf-8 -*- 
    32 
    4 from headstock.protocol.extension.inbandregistration import InBandRegistration 
    53from headstock.lib.utils import generate_unique 
     4from headstock.protocol.core.jid import JID 
    65from headstock.api.dataform import Data, Field 
    7 from headstock.api.storage import Entity 
    8 from bridge.common import XMPP_IBR_NS, XMPP_DATA_FORM_NS 
     6from headstock.api import Entity 
     7from headstock.api.error import Error 
     8from bridge.common import XMPP_IBR_NS, XMPP_CLIENT_NS, XMPP_DATA_FORM_NS 
    99from bridge import Element as E 
    1010 
    11 __all__ = ['RegistrationInfo', 'RegistrationInfoDataForm', 'Registration'] 
     11__all__ = ['Registration'] 
    1212 
    13 class RegistrationInfo(object): 
    14     def __init__(self): 
    15         self.stanza_id = None 
     13class Registration(Entity): 
     14    def __init__(self, from_jid=None, to_jid=None, type=u'get', stanza_id=None): 
     15        Entity.__init__(self, from_jid, to_jid, type, stanza_id) 
     16        self.x = None 
    1617        self.registered = False 
    17         self.fields = {} 
    18         
    19     def __repr__(self): 
    20         return '<RegistrationInfo at %s>' % (hex(id(self))) 
     18        self.remove = False 
     19        self.infos = {} 
    2120 
    22 class RegistrationInfoDataForm(object): 
    23     def __init__(self): 
    24         self.stanza_id = None 
    25         self.registered = False 
    26         self.form = Data(form_type=u'form') 
    27         self.form.fields.append(Field(field_type=u'hidden', 
    28                                       var=u'FORM_TYPE', values=[XMPP_IBR_NS])) 
    29         
    30     def __repr__(self)
    31         return '<RegistrationInfoDataForm at %s>' % (hex(id(self))
     21    @staticmethod 
     22    def from_element(e): 
     23        registration = Registration(JID.parse(e.get_attribute_value('from')), 
     24                                    JID.parse(e.get_attribute_value('to')), 
     25                                    type=e.get_attribute_value('type'), 
     26                                    stanza_id=e.get_attribute_value('id')) 
     27         
     28        error = e.get_child('error', XMPP_CLIENT_NS) 
     29        if error
     30            registration.error = Error.from_element(error
    3231 
    33 class Registration(object): 
    34     def __init__(self, session): 
    35         self.session = session 
     32        query = e.get_child('query', XMPP_IBR_NS) 
    3633 
    37     @classmethod 
    38     def from_element(cls, e): 
    39         instructions = e.get_child('instructions', XMPP_IBR_NS) 
    40         if instructions: 
    41             instructions = instructions.xml_text 
     34        for c in query.xml_children: 
     35            if not isinstance(c, E): 
     36                continue 
     37             
     38            if c.xml_ns == XMPP_DATA_FORM_NS: 
     39                registration.x = Date.from_element(c) 
     40            elif c.xml_ns == XMPP_IBR_NS: 
     41                if c.xml_name == 'remove': 
     42                    registration.remove = True 
     43                elif c.xml_name == 'registered': 
     44                    registration.registered = True 
     45                else: 
     46                    registration.infos[c.xml_name] = c.xml_text 
    4247 
    43         stanza_id = e.xml_parent.get_attribute('id') 
    44         use_data_form = e.get_child('x', XMPP_DATA_FORM_NS) 
    45         if use_data_form: 
    46             ri = RegistrationInfoDataForm() 
    47             ri.stanza_id = unicode(stanza_id) 
    48             ri.form = Data.from_element(use_data_form) 
    49             if e.has_child('registered', XMPP_IBR_NS): 
    50                 ri.registered = True 
    51         else: 
    52             ri = RegistrationInfo() 
    53             ri.stanza_id = unicode(stanza_id) 
    54             for child in e.xml_children: 
    55                 if child.xml_ns == XMPP_IBR_NS: 
    56                     ri.fields[child.xml_name] = child.xml_text 
     48        return registration 
     49         
    5750 
    58             if 'instructions' in ri.fields: 
    59                 del ri.fields['instructions'] 
     51    @staticmethod 
     52    def to_element(e): 
     53        iq = Entity.to_element(e) 
     54        query = E(u'query', namespace=XMPP_IBR_NS, parent=iq) 
     55         
     56        if e.remove: 
     57            E(u'remove', namespace=XMPP_IBR_NS, parent=query) 
     58         
     59        if e.registered: 
     60            E(u'registered', namespace=XMPP_IBR_NS, parent=query) 
    6061 
    61             if 'registered' in ri.fields: 
    62                 ri.registered = True 
    63                 del ri.fields['registered'] 
     62        for info in e.infos: 
     63           E(info, namespace=XMPP_IBR_NS, parent=query, 
     64             content=e.infos[info])  
    6465 
    65         return ri, instructions 
     66        if e.x: 
     67            Data.to_element(x, parent=query) 
    6668 
    67     def ask_registration_fields(self): 
    68         iq = InBandRegistration.create_ibr_query(stanza_id=generate_unique()) 
    69         self.session.stream.propagate(element=iq) 
    70  
    71     def registration_fields_requested(self, ibr, e): 
    72         children = [E(u'instructions', namespace=XMPP_IBR_NS, 
    73                       content=u'Choose a username and password to register with this server'), 
    74                     E(u'username', namespace=XMPP_IBR_NS), 
    75                     E(u'password', namespace=XMPP_IBR_NS), 
    76                     E(u'email', namespace=XMPP_IBR_NS)] 
    77         iq = InBandRegistration.create_ibr_result(elements=children, stanza_id=generate_unique()) 
    78         self.stream.propagate(element=iq) 
    79              
    80     def registration_submitted(self, ibr, e): 
    81         ri, instructions = self._from_element(e) 
    82         e = Entity.lookup_by_username(ri.fields.get('username', None)) 
    83         if e != None: 
    84             query = E(u'query', namespace=XMPP_IBR_NS) 
    85             E(u'username', content=ri.fields.get('username', u''), namespace=XMPP_IBR_NS, parent=query) 
    86             E(u'password', content=ri.fields.get('password', u''), namespace=XMPP_IBR_NS, parent=query) 
    87             E(u'email', content=ri.fields.get('email', u''), namespace=XMPP_IBR_NS, parent=query) 
    88              
    89             iq = StanzaError.create_conflict(from_jid=self.stream.node_name, stanza_id=ri.stanza_id, 
    90                                              children = [query]) 
    91             self.stream.propagate(element=iq) 
    92             return 
    93  
    94         e = Entity() 
    95         e.username = ri.fields.get('username', u'') 
    96         e.password = ri.fields.get('password', u'') 
    97         e.email = ri.fields.get('email', u'') 
    98         self.storage.save(e) 
     69        return iq 
    9970         
    100         iq = Iq.create_result_iq(stanza_id=generate_unique()) 
    101         self.stream.propagate(element=iq) 
    102  
    103     def registration_success(self, ibr, e): 
    104         if callable(self.registered_successfully): 
    105             self.registered_successfully() 
    106              
    107     def unregistration_success(self, ibr, e): 
    108         pass 
    109              
    110     def registration_fields_received(self, ibr, e): 
    111         ri, instructions = self._from_element(e) 
    112           
    113     def send_registration_details(self, ri): 
    114         iq = InBandRegistration.create_ibr_registration(stanza_id=generate_unique()) 
    115         query = iq.get_child('query', XMPP_IBR_NS) 
    116          
    117         if isinstance(ri, RegistrationInfo): 
    118             for field in ri.fields: 
    119                 E(field, content=ri.fields[field], namespace=XMPP_IBR_NS, 
    120                   prefix=query.xml_prefix, parent=query) 
    121             self.session.stream.propagate(element=iq) 
    122         elif isinstance(ri, RegistrationInfoDataForm): 
    123             Data.to_element(ri.form, parent=query) 
    124             self.session.stream.propagate(element=iq) 
    125          
    126     def cancel_registration(self, from_jid): 
    127         iq = InBandRegistration.create_ibr_unregistration(from_jid=from_jid, 
    128                                                           stanza_id=generate_unique()) 
    129         self.session.stream.propagate(element=iq) 
    130          
    131     def change_password(self, to_jid, username, password): 
    132         iq = InBandRegistration.create_ibr_change_password(to_jid=to_jid, 
    133                                                            stanza_id=generate_unique(), 
    134                                                            username=username, 
    135                                                            password=password) 
    136         self.session.stream.propagate(element=iq) 
    137  
    138     def conflict_detected(self, error, e): 
    139         ri, instructions = Registration.from_element(e) 
  • oss/headstock/headstock/example/simplechat/simplechat.py

    r659 r660  
    3838from headstock.protocol.core.roster import RosterDispatcher, RosterNull 
    3939from headstock.protocol.core.message import MessageDispatcher, MessageEchoer 
     40from headstock.protocol.extension.register import RegisterDispatcher 
    4041from headstock.protocol.extension.activity import ActivityDispatcher 
    4142from headstock.protocol.extension.discovery import DiscoveryDispatcher 
     
    4849from headstock.api import Entity 
    4950from headstock.api.activity import Activity 
     51from headstock.api.registration import Registration 
    5052from headstock.lib.utils import generate_unique 
    5153 
    5254from bridge import Element as E 
    5355from bridge.common import XMPP_CLIENT_NS, XMPP_ROSTER_NS, \ 
    54     XMPP_LAST_NS, XMPP_DISCO_INFO_NS 
     56    XMPP_LAST_NS, XMPP_DISCO_INFO_NS, XMPP_IBR_NS 
    5557 
    5658__all__ = ['Client'] 
     
    387389     
    388390 
     391class RegistrationHandler(component): 
     392    Inboxes = {"inbox"   : "headstock.api.registration.Registration", 
     393               "error"   : "headstock.api.registration.Registration", 
     394               "control" : "Shutdown the client stream",} 
     395     
     396    Outboxes = {"outbox" : "headstock.api.registration.Registration", 
     397                "signal" : "Shutdown signal", 
     398                "log"    : "log",} 
     399     
     400    def __init__(self, username, password): 
     401        super(RegistrationHandler, self).__init__() 
     402        self.username = username 
     403        self.password = password 
     404        self.registration_id = None 
     405 
     406    def main(self): 
     407        while 1: 
     408            if self.dataReady("control"): 
     409                mes = self.recv("control") 
     410                 
     411                if isinstance(mes, shutdownMicroprocess) or isinstance(mes, producerFinished): 
     412                    self.send(producerFinished(), "signal") 
     413                    break 
     414 
     415            if self.dataReady("inbox"): 
     416                r = self.recv('inbox') 
     417                if r.registered: 
     418                    print "'%s' is already a registered username." % self.username 
     419                elif self.registration_id == r.stanza_id: 
     420                    print "'%s' is now a registered user."\ 
     421                        "Please restart the client without the register flag." % self.username 
     422                else: 
     423                    if 'username' in r.infos and 'password' in r.infos: 
     424                        self.registration_id = generate_unique() 
     425                        r = Registration(type=u'set', stanza_id=self.registration_id) 
     426                        r.infos[u'username'] = self.username 
     427                        r.infos[u'password'] = self.password 
     428                        self.send(r, 'outbox') 
     429                 
     430            if self.dataReady("error"): 
     431                r = self.recv('error') 
     432                print r.error 
     433 
     434            if not self.anyReady(): 
     435                self.pause() 
     436   
     437            yield 1 
     438 
    389439class Client(component): 
    390     Inboxes = {"inbox"    : "", 
    391                "jid": "", 
    392                "control"  : "Shutdown the client stream", 
    393                
     440    Inboxes = {"inbox"      : "", 
     441               "jid"        : "", 
     442               "streamfeat" : "", 
     443               "control"    : "Shutdown the client stream"
    394444     
    395445    Outboxes = {"outbox"  : "", 
    396446                "forward" : "", 
    397447                "log"     : "", 
     448                "doauth"  : "", 
    398449                "signal"  : "Shutdown signal", 
    399                
     450                "doregistration" : ""
    400451 
    401452    def __init__(self, username, password, domain, resource=u"headstock-client1",  
    402                  server=u'localhost', port=5222, usetls=False): 
     453                 server=u'localhost', port=5222, usetls=False, register=False): 
    403454        super(Client, self).__init__()  
    404455        self.jid = JID(username, domain, resource) 
     456        self.username = username 
    405457        self.password = password 
    406458        self.server = server 
     
    410462        self.domain = domain 
    411463        self.usetls = usetls 
     464        self.register = register 
    412465 
    413466    def passwordLookup(self, jid): 
     
    416469    def shutdown(self): 
    417470        self.send(Presence.to_element(Presence(self.jid, type=u'unavailable')), 'forward') 
     471        self.send('OUTGOING : </stream:stream>', 'log') 
     472        self.send('</stream:stream>', 'outbox')  
     473 
     474    def abort(self): 
    418475        self.send('OUTGOING : </stream:stream>', 'log') 
    419476        self.send('</stream:stream>', 'outbox')  
     
    454511        Pipeline(ConsoleReader(), PublishTo('CONSOLE')).activate() 
    455512 
    456         # Add two outboxes ro the ClientSteam to support specific features. 
     513        # Add two outboxes ro the ClientSteam to support specific extensions. 
     514        ClientStream.Outboxes["%s.query" % XMPP_IBR_NS] = "Registration" 
    457515        ClientStream.Outboxes["%s.query" % XMPP_LAST_NS] = "Activity" 
    458516        ClientStream.Outboxes["%s.query" % XMPP_DISCO_INFO_NS] = "Discovery" 
     
    471529                               activityhandler = ActivityHandler(), 
    472530                               rosterhandler = RosterHandler(self.jid), 
     531                               registerhandler = RegistrationHandler(self.username, self.password), 
    473532                               msgdummyhandler = DummyMessageHandler(), 
    474533                               presencehandler = PresenceHandler(), 
     
    478537                               discodisp = DiscoveryDispatcher(), 
    479538                               activitydisp = ActivityDispatcher(), 
     539                               registerdisp = RegisterDispatcher(), 
    480540                               pjid = PublishTo("JID"), 
    481541                               pbound = PublishTo("BOUND"), 
     
    496556                                           ("xmpp", "jid"): ("pjid", "inbox"), 
    497557                                           ("xmpp", "bound"): ("pbound", "inbox"), 
    498  
     558                                           ("xmpp", "features"): ("client", "streamfeat"), 
     559                                           ("client", "doauth"): ("xmpp", "auth"), 
     560                                            
     561                                           # Registration 
     562                                           ("xmpp", "%s.query" % XMPP_IBR_NS): ("registerdisp", "inbox"), 
     563                                           ("registerdisp", "log"): ('logger', "inbox"), 
     564                                           ("registerdisp", "xmpp.error"): ("registerhandler", "error"), 
     565                                           ("registerdisp", "xmpp.result"): ("registerhandler", "inbox"), 
     566                                           ("registerhandler", "outbox"): ("registerdisp", "forward"), 
     567                                           ("client", "doregistration"): ("registerdisp", "forward"), 
     568                                           ("registerdisp", "outbox"): ("xmpp", "forward"), 
     569                                            
    499570                                           # Presence  
    500571                                           ("xmpp", "%s.presence" % XMPP_CLIENT_NS): ("presencedisp", "inbox"), 
     
    562633                    break 
    563634 
     635            if self.dataReady("streamfeat"): 
     636                feat = self.recv('streamfeat') 
     637                if feat.register and self.register: 
     638                    self.send(Registration(), 'doregistration') 
     639                elif self.register and not feat.register: 
     640                    print "The server does not support in-band registration. Closing connection." 
     641                    self.abort() 
     642                else: 
     643                    self.send(feat, 'doauth') 
     644                 
    564645            if self.dataReady("jid"): 
    565646                self.jid = self.recv('jid') 
     
    587668        parser.add_option("-u", "--username", dest="username", 
    588669                          help="XMPP username", action="store") 
     670        parser.set_defaults(username=None) 
    589671        parser.add_option("-p", "--password", action="store", dest="password", 
    590672                          help="XMPP password") 
     673        parser.set_defaults(password=None) 
     674        parser.add_option("-r", "--register", action="store_true", dest="register", 
     675                          help="Register the user if the server supports it") 
     676        parser.set_defaults(register=False) 
    591677        parser.add_option("-t", "--usetls", dest="usetls", action="store_true", 
    592678                           help="Use TLS") 
     
    603689                        unicode(options.domain), 
    604690                        server=host, port=int(port), 
    605                         usetls=options.usetls) 
     691                        usetls=options.usetls, 
     692                        register=options.register) 
    606693        client.run() 
    607694 
  • oss/headstock/headstock/protocol/core/stream.py

    r654 r660  
    1414from bridge import Attribute as A 
    1515from bridge.common import XML_NS, XML_PREFIX, XMPP_CLIENT_NS, XMPP_STREAM_NS, XMPP_STREAM_PREFIX,\ 
    16      XMPP_SASL_NS, XMPP_SASL_PREFIX, XMPP_AUTH_NS, XMPP_TLS_NS, XMPP_CLIENT_NS,
     16     XMPP_SASL_NS, XMPP_SASL_PREFIX, XMPP_AUTH_NS, XMPP_TLS_NS, XMPP_CLIENT_NS, XMPP_IBR_NS,
    1717     XMPP_BIND_NS, XMPP_SESSION_NS, XMPP_DISCO_ITEMS_NS, XMPP_ROSTER_NS, xmpp_bind_as_attr 
    1818from bridge.common import ANY_NAMESPACE 
     
    2626from headstock.lib.auth.digest import challenge_to_dict, compute_digest_response 
    2727from headstock.lib.utils import generate_unique, extract_from_stanza 
     28from headstock.api.stream import StreamFeatures 
    2829 
    2930__all__ = ['ClientStream', 'StreamError', 'SaslError'] 
     
    113114             
    114115class ClientStream(component): 
    115     Inboxes = {"inbox"   : "bridge.Element instance", 
    116                "control" : "Shutdown the client stream", 
    117                "forward": "bridge.Element instance to be sent out to the client", 
     116    Inboxes = {"inbox"     : "bridge.Element instance", 
     117               "control"   : "Shutdown the client stream", 
     118               "forward"   : "bridge.Element instance to be sent out to the client", 
     119               "auth"      : "Perform authentication", 
    118120               "proceedtls": "", 
    119121               "tlssuccess": "", 
     
    127129                "starttls": "", 
    128130                "jid"    : "", 
     131                "features": "", 
    129132                "bound"  : "indicates the client has been successfully bound to an XMPP server", 
    130133                "terminated": "Indicates the stream has been terminated by the peer", 
     
    195198        self.log(e) 
    196199        self.status = CONNECTED 
    197         mechanisms = e.get_child('mechanisms', ns=XMPP_SASL_NS) 
    198         support_tls = e.get_child('starttls', ns=XMPP_TLS_NS) 
    199         if support_tls and self.use_tls: 
     200        feat = StreamFeatures.from_element(e) 
     201        if feat.tls and self.use_tls: 
    200202            tls = E(u'starttls', namespace=XMPP_TLS_NS) 
    201203            self.propagate(element=tls) 
    202         elif mechanisms: 
    203             self._handle_mechanisms(mechanisms
    204              
     204        elif feat.mechanisms: 
     205            self.send(feat, 'features'
     206                 
    205207    def _handle_tls(self): 
    206208        self._reset_stream_header(omit_decl=True) 
     
    225227        self.propagate(element=response) 
    226228 
    227     def _handle_mechanisms(self, e): 
    228         self.log(e) 
    229         mechanisms = [m.xml_text for m in e.xml_children if m.xml_name == 'mechanism'] 
     229    def _handle_auth(self, feat): 
    230230        mechanism = None 
    231231 
    232232        # Always favour DIGEST-MD5 if supported by receiving entity 
    233         if u'DIGEST-MD5' in mechanisms: 
     233        if u'DIGEST-MD5' in feat.mechanisms: 
    234234            mechanism = u'DIGEST-MD5' 
    235235            token = None 
    236         elif u'PLAIN' in mechanisms: 
     236        elif u'PLAIN' in feat.mechanisms: 
    237237            mechanism = u'PLAIN' 
    238238            email = '%s@%s' % (self.jid.node, self.jid.domain) 
    239239            password = self.password_lookup(self.jid) 
    240240            token = generate_credential(email, self.jid.node, password) 
    241         elif u'X-GOOGLE-TOKEN' in mechanisms: 
     241        elif u'X-GOOGLE-TOKEN' in feat.mechanisms: 
    242242            mechanism = u'X-GOOGLE-TOKEN' 
    243243            password = self.password_lookup(self.jid) 
    244244            token = perform_authentication(self.jid.node, password) 
    245         elif u'ANONYMOUS' in mechanisms:             
     245        elif u'ANONYMOUS' in feat.mechanisms:             
    246246            mechanism = u'ANONYMOUS' 
    247247            token = None 
     
    320320                self._handle_tls() 
    321321                yield 1 
     322 
     323            if self.dataReady("auth"): 
     324                feat = self.recv('auth') 
     325                self._handle_auth(feat) 
    322326 
    323327            if self.dataReady("forward"): 
     
    354358                        self._handle_jid(e) 
    355359                        self.send('', 'bound') 
     360                    elif (e.xml_ns == XMPP_IBR_NS) and (e.xml_name == 'query'): 
     361                        self.send(e, "%s.%s" % (e.xml_ns, e.xml_name)) 
    356362                elif (e.xml_ns == XMPP_STREAM_NS) and (e.xml_name == 'error'): 
    357363                    self.send(e, "error") 
  • oss/headstock/headstock/protocol/extension/discovery.py

    r654 r660  
    1 #!/usr/bin/env python 
    21# -*- coding: utf-8 -*- 
    32