0

I'm using django-auth-ldap with following setting because there is no default/global 'admin' user on the ldap server, its only for authenticating users and users themselves may see their user information.

AUTH_LDAP_BIND_AS_AUTHENTICATING_USER=True

in django-ldap-debug.log i get following error when (as logged in user) calling in view LDAPBackend().populate_user(request.user.username)

search_s('uid=vchrizz,ou=Users,dc=funkfeuer,dc=at', 0, '(objectClass=*)') raised NO_SUCH_OBJECT({'desc': 'No such object'},)
search_s('uid=vchrizz,ou=Users,dc=funkfeuer,dc=at', 0, '(objectClass=*)') returned 0 objects: 

only when logging in (using login_required from django.contrib.auth.decorators) it returns a user object it seems:

search_s('uid=vchrizz,ou=Users,dc=funkfeuer,dc=at', 0, '(objectClass=*)') returned 1 objects: uid=vchrizz,ou=users,dc=funkfeuer,dc=at

then i noticed, i need to set

AUTH_LDAP_BIND_DN
AUTH_LDAP_BIND_PASSWORD

to get rid of the error, but first i dont want to specify a user with password (cause bind_as_authenticating_user) and second populate_user() still returns NoneType ...

why? how do i get the returned user information from ldap?

my goal is to display all ldap user information like uidNumber from the ldap-user in my custom /userinfo/ view. http://pastebin.com/VqGiwzFE

thanks, chris

fatiherdem
  • 1,173
  • 6
  • 18
  • 35
Christoph Lösch
  • 645
  • 7
  • 22
  • what i forgot to make it work: `user = auth.authenticate(username="theuser", password="thepass")` naturally i dont want hardcoded user credentials here, so i can replace "theuser" with `request.user.username` but not the password as `request.user.password` is the hashed password. as the password is in /login/ view in POST, i guess its better to get the (authenticated) user object from /login/ view into /userinfo/ view? but how do i do that? – Christoph Lösch Aug 09 '14 at 23:43
  • from [Django-AttributeError 'User' object has no attribute 'backend' (But…it does?)](http://stackoverflow.com/questions/6034763/django-attributeerror-user-object-has-no-attribute-backend-but-it-does) ive read that auth.authenticate() is needed, and i guess i need this: [Re: Modify authentication backend](https://groups.google.com/forum/#!topic/django-auth-ldap/9D_VJYI0L9U) to somehow get the user object from login view to userinfo view? – Christoph Lösch Aug 10 '14 at 00:29

1 Answers1

3

in the end auth.authenticate was missing and i had to rtfm:

Storing additional information about users this is the preferred way to get user information instead the way i was looking for.

settings.py:

AUTH_LDAP_PROFILE_ATTR_MAP = {
    "uid": "uid",
    "cn": "cn",
    "sn": "sn",
    "givenName": "givenName",
    "userPassword": "userPassword",
    "shadowLastChange": "shadowLastChange",
    "shadowMax": "shadowMax",
    "shadowWarning": "shadowWarning",
    "loginShell": "loginShell",
    "uidNumber": "uidNumber",
    "gidNumber": "gidNumber",
    "homeDirectory": "homeDirectory",
    "gecos": "gecos",
    "mail": "mail",
    "l": "l",
    "telephoneNumber": "telephoneNumber",
}
AUTH_PROFILE_MODULE = 'myapp.UserProfile'

models.py:

from django.db import models
from django.contrib.auth.models import User
from django.db.models.signals import post_save

class UserProfile(models.Model):
    # This field is required.
    user = models.OneToOneField(User)
    # Other fields here
    uid = models.CharField(max_length=254)
    cn = models.CharField(max_length=254)
    sn = models.CharField(max_length=254)
    givenName = models.CharField(max_length=254)
    userPassword = models.CharField(max_length=254)
    shadowLastChange = models.IntegerField(null=True)
    shadowMax = models.IntegerField(null=True)
    shadowWarning = models.IntegerField(null=True)
    loginShell = models.CharField(max_length=254)
    uidNumber = models.IntegerField(null=True)
    gidNumber = models.IntegerField(null=True)
    homeDirectory = models.CharField(max_length=254)
    gecos = models.CharField(max_length=254)
    mail = models.EmailField(max_length=254)
    l = models.CharField(max_length=254)
    telephoneNumber = models.CharField(max_length=254)

def create_user_profile(sender, instance, created, **kwargs):
    #if created:
    #    UserProfile.objects.create(user=instance)
    UserProfile.objects.get_or_create(user=instance)

post_save.connect(create_user_profile, sender=User)

views.py:

from django.contrib.auth.decorators import login_required
from django.http import HttpResponseRedirect
from django.shortcuts import render
from myapp.models import UserProfile

@login_required
def userinfo(request):
    try:
        ldapuserprofile = UserProfile.objects.get(uid=request.user.username)
    except UserProfile.DoesNotExist:
        return HttpResponseRedirect('/login/')
    context = {'request': request, 'ldapuser': ldapuserprofile,}
    return render(request, 'myapp/userinfo.html', context)

then in html template its possible to access {{ ldapuser.givenName }}

maybe it helps someone.

thanks, chris

Christoph Lösch
  • 645
  • 7
  • 22