Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Django How to prevent multiple users login using the same credentials

I am developing an Django application using django auth module and would like to prevent multiple login using the same user name and password.

It should prevent multiple logins on different machines using the same user name and password. How do I achieve this in Django?

We have to keep following things in mind:

  1. If user close the browser without logging out
  2. If the session times out
like image 628
AKV Avatar asked Dec 07 '11 00:12

AKV


People also ask

What is user Is_authenticated in Django?

is_authenticated which is always False ). This is a way to tell if the user has been authenticated. This does not imply any permissions and doesn't check if the user is active or has a valid session. Even though normally you will check this attribute on request.

How do I block someone in Django?

Django admin allows access to users marked as is_staff=True . To disable a user from being able to access the admin, you should set is_staff=False . This holds true even if the user is a superuser.


3 Answers

You may try this, it logs out the first user and logs in the second. Add middleware.py in your app directory (same level as models, views etc) and add this code. Useful when the same person is using more than one device. Make sure you add this to your middleware classes: 'myapp.middleware.UserRestrict',

class UserRestrict(object):
    def process_request(self, request):
        """
        Checks if different session exists for user and deletes it.
        """
        if request.user.is_authenticated():
            cache = get_cache('default')
            cache_timeout = 86400
            cache_key = "user_pk_%s_restrict" % request.user.pk
            cache_value = cache.get(cache_key)

            if cache_value is not None:
                if request.session.session_key != cache_value:
                    engine = import_module(settings.SESSION_ENGINE)
                    session = engine.SessionStore(session_key=cache_value)
                    session.delete()
                    cache.set(cache_key, request.session.session_key, 
                              cache_timeout)
            else:
                cache.set(cache_key, request.session.session_key, cache_timeout)
like image 93
Hashim Sayyid Avatar answered Oct 16 '22 11:10

Hashim Sayyid


Out of the box, Django doesn't provide you with a way to prevent concurrent sessions for the same user account, and that isn't a trivial thing to do. However, here's another question with some suggestions about how you might make this happen: How can I detect multiple logins into a Django web application from different locations?

like image 43
Michael C. O'Connor Avatar answered Oct 16 '22 10:10

Michael C. O'Connor


i solve the problem with a new model, a custom decorator and custom login page

1) i created a additional model for users eg:

class SessionKey(models.Model):
    user = models.OneToOneField(User,primary_key=True)
    key = models.CharField(max_length=255)

2) i created custom decorator to check session key is equal or not last key. i changed the original source code django decorators

from functools import wraps
from django.conf import settings
from django.utils.decorators import available_attrs
from django.contrib.auth.decorators import login_required
from django.shortcuts import resolve_url
from users.models import SessionKey #my additional model

def unique_login_required(view_func):
    @wraps(view_func, assigned=available_attrs(view_func))
    def _wrapped_view(request, *args, **kwargs):
        r = False
        ...
        #check session key is equal to last one
        ...
        if r:
            return view_func(request, *args, **kwargs)
        else:
            from django.contrib.auth.views import redirect_to_login
            path = request.build_absolute_uri()
            resolved_login_url = resolve_url(settings.LOGIN_URL)
            return redirect_to_login(path,resolved_login_url)
    return _wrapped_view

3) in custom login page, i updated the session key. last login always updates the stored session key.

finally, in the views, i call my decorator

from users.decorators import unique_login_required
@unique_login_required
def index(request):
...
like image 39
Cem Yıldız Avatar answered Oct 16 '22 10:10

Cem Yıldız