2010-06-10 16 views
5

Próbuję uzyskać formularz logowania, który mam w django, aby zezwolić tylko na trzy próby logowania przed przekierowaniem na stronę "pomocy dotyczącej logowania". Obecnie używam wbudowanego widoku "django.contrib.auth.views.login" z niestandardowym szablonem. Jak zmusić go do przekierowania na inną stronę po n nieudanych próbach logowania?Jak ograniczyć liczbę ponownych prób logowania w Django

Odpowiedz

-8

Możesz zapisać sesję, jeśli użytkownik nie mógł się zalogować.

request.SESSION['login_tries'] = 1 

a jeśli nie, aby zalogować się ponownie

request.SESSioN['login_tries'] = 2 

Jeśli sesja staje się równa kwocie logowania próbuje chcesz je mieć tho, następnie coś zrobić.

+8

Sesja będzie istnieć tylko wtedy, gdy klient wysyła nagłówki Cookie, które nie będą robić brute force atakujący. Lepiej połączyć próby logowania z konkretnym kontem użytkownika lub konkretnym klientem (lub oboma). –

10

W rzeczywistości istnieje projekt, który zapewnia oprogramowanie pośrednie Django do wykonania właśnie tego, o nazwie django-axes. Po prostu zainstaluj go zgodnie z dostarczonymi instrukcjami, a następnie ustaw AXES_LOGIN_FAILURE_LIMIT na liczbę prób zalogowania, które chcesz, zanim zostanie utworzony rekord dla nieudanych prób logowania. Nadal musisz sprawdzić ten rekord, gdy chcesz kogoś zablokować.

+0

Dzięki Daniel. Wybrałem odpowiedź Dotty'ego, ponieważ była bliższa metodzie, której użyłem w końcu. Częścią problemu był mój brak doświadczenia z Pythonem i Django i jako taki nie miałem wystarczającej wiedzy, by zadać właściwe pytanie. Myślę, że twoja odpowiedź byłaby równie dobra, jeśli nie lepsza, gdybym chciała czegoś z tak wieloma funkcjami, i mógłbym dobrze skończyć z jego użyciem, gdy lepiej poznałem framework. –

+1

Bez obaw, chciałem tylko poinformować, że istnieje już rozwiązanie, które mogłoby potencjalnie zadziałać. Nie wiedziałem, że to istnieje, więc też nauczyłem się czegoś w tym procesie! –

0

używam django-brake i memcached

@ratelimit(field='email', method='POST', rate='5/m') 
@ratelimit(field='email', method='POST', rate='10/h') 
@ratelimit(field='email', method='POST', rate='20/d') 
def login_failure(request, login_form): 
    """ 
    Increment cache counters, 403 if over limit. 
    """ 
    was_limited = getattr(request, 'limited', False) 
    if was_limited: 
     limits = getattr(request, 'limits', []) 
     login_form.full_clean() 
     login_form._errors.setdefault(NON_FIELD_ERRORS, ErrorList())\ 
      .append('accout locked, try '+ str(limits[0]['period']) + ' seconds later') 
     return render(request, 'user/login.html', {'form': login_form}) 


def login(request): 

    if request.method == 'GET': 
     next = request.GET.get('next', '') 
     return render(request, 'user/login.html', {'next': next}) 
    elif request.method == 'POST': 
     login_form = LoginForm(request.POST) 

     # check first 
     from brake.utils import get_limits 
     limits = get_limits(request, 'login_failure', 'email', [60, 3600, 86400]) 
     if limits: 
      login_form.full_clean() 
      login_form._errors.setdefault(NON_FIELD_ERRORS, ErrorList())\ 
       .append('accout locked, try '+ str(limits[0]['period']) + ' seconds later') 
      return render(request, 'user/login.html', {'form': login_form}) 

     if login_form.is_valid(): 

       email = login_form.cleaned_data['email'] 
       submit_pwd = login_form.cleaned_data['password'] 

       user = authenticate(username=email, password=submit_pwd) 

       if user is None: 
        # 
        res = login_failure(request, login_form) 
        if res is None: 
         login_form._errors.setdefault(NON_FIELD_ERRORS, ErrorList()).append('password wrong') 
         res = render(request, 'user/login.html', {'form': login_form}) 
        return res 

       ... 
       login etc... 
     else: 

     ... 
Powiązane problemy