Code


Version 17 (modified by jkocherhans, 8 years ago) (diff)

updated status

Multiple Authentication Backends

As of [3226], multiple authentication backends are now supported in the trunk.

The documentation has been updated and can be found here: http://code.djangoproject.com/browser/django/trunk/docs/authentication.txt


Start: Added by a relative newbie on May 12, 2006

Note: In the multi-auth branch (2892), you need to set AUTHENTICATION_BACKENDS to a tuple, similar to MULTIAUTH_BACKENDS above. the authenticate method looks for this setting in your settings.py file. I have it working and all I have is:

AUTHENTICATION_BACKENDS = (
    "django.contrib.auth.copy_of_backends.LDAPBackend",
)

I made a copy of contrib.auth.backends so the svn can update it without overwriting my LDAPBackend class. Don't know if that is the best way to do it or not, but it works.

I recommend you put it someplace like myapp.auth.LDAPBackend. Maintianing patches to Django is going to be a PITA. --Joseph Kocherhans

I also hacked the contrib.auth.models file to change the check_password function to check against our LDAP server, and added a few small functions to check the type of user account. I know this will break next time I update the source, but I have a copy of that as well. There is surely a better way, but I'm still learning.

You shouldn't have to hack the check_password function at all. It isn't called directly by Django's views anymore... only indirectly via django.contrib.auth.backends.ModelBacked, which you aren't using. -Joseph Kocherhans

End of newbie addition


sample LDAPBackend class

From the same newbie as above on May 12, 2006

This is located in the contrib/auth/copy_of_backends.py file. The two original models are still in the file as well. I just added this one in the middle.

class LDAPBackend:
    """
    Authenticate against our LDAP Database
    """
    def authenticate(self, username=None, password=None):
        # bind and see if the user exists
        if ldap.userExists(username):
            # user exists in our LDAP, see if they exist in Django
            # if not, add them to django's user database since django relies on that
            try:
                user = User.objects.get(username=username)
                if ldap.check_ldap_password(username, password):
                    return user
            except User.DoesNotExist:
                # get the first name, last name, email from ldap
                u = ldap.getUser(username)
                # get user attributes here as well, like mail, fname, lname
                user = User(username=username, password='getmefromldap')
                user.email = mail
                user.first_name = fname
                user.last_name = lname
                user.is_staff = False
                user.is_superuser = False
                user.save()
                return user
        else:
            return None

    def get_user(self, user_id):
        try:
            return User.objects.get(pk=user_id)
        except User.DoesNotExist:
            return None

And it worked! I was able to logon as a user who had no entry in Django, and then it added my entry and away I went. Pretty nice stuff.