2011-08-12 50 views
0

我試圖提供一個用戶註冊表,而不需要手動輸入用戶名。我設置了一個身份驗證後端,以便用戶可以使用電子郵件地址進行身份驗證,並且這是可行的,因爲我可以使用Django管理員用戶登錄。這個想法是,我的應用程序會創建一個電子郵件地址的SHA1散列,以存儲爲Django用戶名,用戶永遠不會看到這個。用Django註冊自動生成一個Django用戶名

我從我的註冊html模板中刪除了用戶名字段,但我不知道應該如何或在哪裏以編程方式生成用戶名。我認爲它應該在RegistrationForm的clean_username方法中,但是當我使用不帶username字段的模板時,該方法不會被調用。

任何幫助肯定會被讚賞。

+0

創建的用戶名你在哪裏驗證你的視圖中的表單? –

+0

我將不得不修改django註冊視圖,因爲我沒有寫視圖。我將如何設置用戶名。我可以生成電子郵件的散列,但不知道我會如何處理散列。 – Raj

+0

一種可能的方式是,不要對django註冊做任何事情,只是隱藏模板上的用戶名字段,當提交之前用戶提交表單調用javascript函數並生成用戶名並在post中設置其值時,一個想法可以生成用戶名是採取電子郵件的左側部分並進行更改。 –

回答

1

我得到它的工作。我不想直接修改註冊的視圖方法和默認註冊後端。我更喜歡在自己的代碼中進行這些更改,並且仍在努力進行這些更改,但這確實有效。

我是這樣做的:

  1. 創建一個自定義的註冊後端稱爲RegBackend生成基於電子郵件地址的SHA1哈希值,然後存儲hexdigest作爲用戶名,最後返回一個User對象。在urls.py與我在步驟中創建的新RegBackend

  2. 地圖寄存器1

  3. 改性Django的登記的視圖寄存器方法,這樣的形式驗證創建隨機用戶名,但沒存留隨機用戶名。我複製了request.POST字典並將此隨機用戶名設置爲副本的一個名爲data ['username']的字典鍵。然後,我在創建form_class的實例時使用數據變量。在窗體上調用is_valid()將返回false,因爲我從模板中刪除了用戶名,但Django需要用戶名才能註冊,所以我需要爲它提供

而SHA1哈希是40.奇怪的是,自定義登記後端沒有抱怨,並且可以存儲我沒有使用SHA1哈希用於隨機用戶名因爲Django的用戶名只能是在長度爲30個字符sha1散列,但由於提交時的長度,表單會產生錯誤。

_ init _。PY(I複製的現有DefaultBackend並與SHA1部分改性)

from django.conf import settings 
from django.contrib.sites.models import RequestSite 
from django.contrib.sites.models import Site 

from registration import signals 
from registration.forms import RegistrationForm 
from registration.models import RegistrationProfile 

import hashlib 

class RegBackend(object): 

def register(self, request, **kwargs): 

hash_user = hashlib.sha1() 
hash_user.update(kwargs['email']) 

    username, email, password = hash_user.hexdigest(), kwargs['email'], kwargs['password1'] 

    if Site._meta.installed: 
     site = Site.objects.get_current() 
    else: 
     site = RequestSite(request) 
    new_user = RegistrationProfile.objects.create_inactive_user(username, email, 
                   password, site) 
    signals.user_registered.send(sender=self.__class__, 
           user=new_user, 
           request=request) 
    return new_user 

    #omitted other code from DefaultBackend that I didn't modify 

urls.py

url(r'^register/$', register, {'backend': 'registration.backends.default.RegBackend', 'form_class': UserRegistrationForm}, name='registration_register'), 

登記/ views.py

def register(request, backend, success_url=None, form_class=None, 
      disallowed_url='registration_disallowed', 
      template_name='registration/registration_form.html', 
      extra_context=None): 

    backend = get_backend(backend) 
    if not backend.registration_allowed(request): 
     return redirect(disallowed_url) 
    if form_class is None: 
     form_class = backend.get_form_class(request) 

    if request.method == 'POST': 
     # I added the next two lines 
     data = request.POST.copy() 
     data['username'] = ''.join([choice(letters) for i in xrange(30)]) 
     form = form_class(data=data, files=request.FILES) 
     if form.is_valid(): 
      new_user = backend.register(request, **form.cleaned_data) 
      if success_url is None: 
       to, args, kwargs = backend.post_registration_redirect(request, new_user) 
       return redirect(to, *args, **kwargs) 
      else: 
       return redirect(success_url) 

    else: 
     form = form_class() 

    if extra_context is None: 
     extra_context = {} 
    context = RequestContext(request) 
    for key, value in extra_context.items(): 
     context[key] = callable(value) and value() or value 

    return render_to_response(template_name, 
           {'form': form}, 
           context_instance=context) 
0

你可能會想子類RegistrationForm,然後重寫clean方法(我不喜歡,雖然,自潔淨方法有一個明確的目的,見https://docs.djangoproject.com/en/dev/topics/forms/modelforms/#overriding-the-clean-method

一個更簡單的解決辦法可能是提示用戶輸入他們的電子郵件地址,然後處理該表單以生成用戶名,並將該值作爲額外的上下文傳遞給register視圖。然後,不要刪除用戶名字段,而是將哈希值分配給它並隱藏在模板中。這樣,你就不必亂搞django註冊本身。

有關extra_context參數的更多信息,請參閱https://bitbucket.org/ubernostrum/django-registration/src/fad7080fe769/registration/views.py