2011-06-26 100 views
0

我想在登錄表單中添加驗證碼字段。 因此,我編寫了一個authentication_form,其中添加了一個charField以生成驗證碼,並將驗證碼保存到request.session。 但是當我發送登錄表單請求時,我發現在我的authentication_form中,我無法比較會話的驗證碼和clean_data["verifycode"], 因爲請求在Null的時候調用了我的authentication_form。Django具有驗證碼字段的自定義登錄表單,請求爲NULL

class MyAuthenticationForm(AuthenticationForm): 
    verifyimg = forms.CharField(label="verifycode", widget=vericonf.CaptchaWidget) 


    def __init__(self, request=None, *args, **kwargs): 
     self.request = request 
     kwargs_new = {'error_class': DivErrorList} 
     kwargs.update(kwargs_new) 
     #elf.error_class = DivErrorList 
     super(MyAuthenticationForm, self).__init__(*args, **kwargs) 


    def as_div(self): 
     "Returns this form rendered as HTML div." 
     return self._html_output(
      normal_row=u'<div%(html_class_attr)s style="float:left;"><div class="formlabel">%(label)s</div><div class="formfield">%(field)s%(help_text)s</div><div class="formerror">%(errors)s</div></div>', 
      error_row=u'<div>%s</div>', 
      row_ender=u'</div></div>', 
      help_text_html=u'<div style="float:left;"><span class="helptext">%s</span></div>', 
      errors_on_separate_row=False) 

    def clean_verifyimg(self): 
     pass 

    def clean(self): 
     vericode = "" 
     username = self.cleaned_data.get('username') 
     password = self.cleaned_data.get('password') 

     if self.request and self.request.session and self.request.session.get("verifyimg"): 
      vericode = self.request.session.get("verifyimg") 

     print vericode ###HERE request.session is Null then I can't compare vericode and verify now.How to do it? 

     verify = self.cleaned_data.get('verifyimg') 
     print verify 

     if username and password: 
      self.user_cache = authenticate(username=username, password=password) 
      if self.user_cache is None: 
       raise forms.ValidationError(
        _("Please enter a correct username and password. Note that both fields are case-sensitive.")) 
      elif not self.user_cache.is_active: 
       raise forms.ValidationError(_("This account is inactive.")) 
     if verify and vericode: 
      if verify != vericode: 
       raise forms.ValidationError("verify code is wrong.pls Try again!") 

     self.check_for_test_cookie() 

     return self.cleaned_data 

回答

1

的這裏的問題是,當Django login view doesn't pass 'request' to 'authentication_form'「request.method」是「POST」和「AuthenticationForm」需要一個「請求」關鍵字參數。

我已經解決了這個樣子:

把我的代碼放到一個視圖包裝「django.contrib.auth.login」。

你仍然可以使用你的 'MyAuthenticationForm' 設置你的urls.py這樣

url(r'^accounts/login/$', 
     'myapp.views.custom_login', 
     {'template_name': 'registration/login.html', 
     'authentication_form': MyAuthenticationForm 
     }, 
     name='auth_login'), 

,並在您views.py puting這

def custom_login(request, *args, **kwargs): 
    if request.method == 'POST': 
     form = MyAuthenticationForm(data=request.POST, request=request) 
     # Here you take care of your form validation and interaction with request 

    return login(request, *args, **kwargs) 

注意 '數據' 和 '要求'參數,必須是關鍵字參數。

相關問題