Implementing User Authentication in Django


Reading time: 20 minutes | Coding time: 10 minutes

Authentication is the mechanism of associating an incoming request with a set of identifying credentials, such as the user the request came from, or the token that it was signed with.

Django is used for rapid development. Django comes with a built-in user authentication system, which handles:

  • objects like users, groups, user-permissions
  • some cookie-based user sessions.

Django’s User authentication not only authenticates (verifying the user identity) the user but also authorizes him (determines what permissions user have).

Authentication supported in Django

Django supports three types of authentication:

  1. Basic Authentication
  2. Session Authentication
  3. Token Authentication

Within the settings.py file find the INSTALLED_APPS tuple and check that django.contrib.auth and django.contrib.contenttypes are listed, so that it looks like the code below:

INSTALLED_APPS = (
   'django.contrib.auth',
   'django.contrib.contenttypes',
   'django.contrib.sessions',
   'django.contrib.admin')
  • django.contrib.auth provides Django with access to the authentication system

  • django.contrib.contenttypes is used by the authentication application to track models installed in your database.

Middlewares in the Django framework which operates on request and transfers it to the view and before passing it to the template engine, it starts operating on a response.

There are 2 Middlewares that are used for managing authenication requests:

MIDDLEWARE = [
'django.contrib.sessions.middleware.SessionMiddleware',
'django.contrib.auth.middleware.AuthenticationMiddleware',]

The User Model

The core of Django’s authentication system is the User object, located at django.contrib.auth.models.User. A User object represents each of the people interacting with a Django application.

User objects are used to allow aspects of the authentication system like:

  • access restriction
  • registration of new user profiles
  • the association of creators with site content

The User model comes complete with five primary attributes. They are:

  1. Username
  2. password
  3. Email address
  4. First name
  5. Lastname

Creating Users

The simplest, and least error prone way to create and manage users is through the Django admin. Django also provides built in views and forms to allow users to log in and out and change their own password. We will be looking at user management via the admin and generic user forms a bit later in this chapter, but first, let’s look at how we would handle user authentication directly.
The most direct way to create users is to use the included create_user() helper function:

>>> from django.contrib.auth.models import User
>>> user = User.objects.create_user('gautam', 'gautam@xyz.com','secretpassword')# At this point, user is a User object that has already been saved to the database. You can continue to change its attributes
# if you want to change other fields.
>>> user.last_name = 'lastname'
>>> user.save()

Logging In and Logout

Django provides two functions to perform these actions in django.contrib.auth: authenticate() and login()

To authenticate a given username and password, use authenticate(). It takes two keyword arguments:

  • username
  • password

and it returns a User object if the password is valid for the given username. If the password is invalid, authenticate() returns None:

  • authenticate() only verifies a user’s credentials.
  • To log in a user, use login(). It takes an HttpRequest object and a User object and saves the user’s ID in the session, using Django’s session framework
from django.contrib.auth import login,authenicate

def login_view(request):
    username = request.POST.get('username', '')
    password = request.POST.get('password', '')
    user = authenticate(username=username, password=password)
    if user is not None and user.is_active:
        # Correct password, and the user is marked "active"
        login(request, user)
        # Redirect to a success page.
        return HttpResponseRedirect("/account/loggedin/")
    else:
        # Show an error page
        return HttpResponseRedirect("/account/invalid/")

To log out a user, use django.contrib.auth.logout() within your view. It takes an HttpRequest object and has no return value:

from django.contrib import auth

def logout_view(request):
    auth.logout(request)
    # Redirect to a success page.
    return HttpResponseRedirect("/account/loggedout/")

Working of Auth

The auth middleware is it sets request.user to a LazyUser. Like request.session, request.user is lazy: the user won’t be loaded until request.user is accessed.

When request.user is accessed LazyUser calls django.contrib.auth.get_user(), passing in the request; get_user() pulls info out of the session and, if the user is authenticated, returns the appropriate User instance.

>>> from django.contrib.sessions.models import Session
>>> s = Session.objects.get(pk='d638d3e640d2133c8cc0b73d0e88c6b3')
>>> s.get_decoded()
{'_auth_user_backend': 'django.contrib.auth.backends.ModelBackend',
 '_auth_user_id': 1}

So you can see that a properly authenticated user gets two pieces of information stored in the session:

(a) which backend was used to authenticate that user and
(b) what the user’s ID is.