Justin O Barber
Justin O Barber

Reputation: 11591

LDAP in Django: required to pass unicode password as string

I wrote a python script to change passwords in AD that works well from a command line. Now I am transferring that script to Django in order to make a change password page. Everything seems to work except one thing: for some reason, I keep getting a TypeError in Django that suggests a string rather than a unicode object should be passed to AD. Of course, when I do this, AD protests because the password is no longer in unicode. I'm guessing that I am overlooking something simple, but I cannot figure out what.

Below is the views.py code that I think should work (and that does work in the command line version). I added unicode() to the passwords just to indicate that they are in fact unicode, although they are definitely unicode before these lines.

import ldap
def changePassword(request):
    t = ldap.initialize(server) 
    . . .
    t.simple_bind_s('**********', '****')
    . . .
    mod_attrs = [(ldap.MOD_DELETE, 'unicodePwd', [unicode(oldPassword)]), 
                (ldap.MOD_ADD, 'unicodePwd', [unicode(newPassword)])]
    t.modify_s(dn, mod_attrs)

The error:

('expected a string in the list', u'pass!word')

     Request Method:   POST
      Request URL:     http://127.0.0.1:8000/index/
     Django Version:   1.4.2
     Exception Type:   TypeError
    Exception Value:
                       ('expected a string in the list', u'pass!word')

   Exception Location: /usr/lib/python2.7/dist-packages/ldap/ldapobject.py
                       in _ldap_call, line 96
   Python Executable:  /usr/bin/python
     Python Version:   2.7.3

The modified version does not raise an exception but also does not change the password (because the password is not passed in unicode):

mod_attrs = [(ldap.MOD_DELETE, 'unicodePwd', [str(oldPassword)]), 
            (ldap.MOD_ADD, 'unicodePwd', [str(newPassword)])]
t.modify_s(dn, mod_attrs)

Does anyone know what might lead to this unicode issue? If I could prevent the exception in Django and keep the unicode, I think this code would work.

Thanks in advance for any insight you might be able to offer.

Upvotes: 4

Views: 1963

Answers (1)

András Aszódi
András Aszódi

Reputation: 9660

This seems to be a problem with the Python LDAP module in general. A quick fix is to convert all Unicode strings with str(). I could store attributes including passwords this way in an OpenLDAP directory. I was using python.ldap directly, not through Django.

Upvotes: 4

Related Questions