Commit 3e13bc798b277823e4bb3ab0992fbb6fa5eb99ec
1 parent
dab8f064
Exists in
master
and in
39 other branches
Refactorign signup process
Showing
8 changed files
with
87 additions
and
177 deletions
Show diff stats
src/accounts/forms.py
1 | 1 | # -*- coding: utf-8 -*- |
2 | 2 | |
3 | 3 | from django import forms |
4 | -from django.contrib.auth.models import User | |
4 | +from django.contrib.auth import get_user_model | |
5 | 5 | from django.contrib.auth.forms import UserCreationForm as UserCreationForm_ |
6 | 6 | from django.utils.translation import ugettext_lazy as _ |
7 | 7 | |
8 | 8 | from super_archives.models import MailingList |
9 | -from super_archives.validators import UniqueValidator | |
10 | 9 | |
11 | 10 | |
12 | -LISTS_NAMES = [] | |
13 | -for list_ in MailingList.objects.iterator(): | |
14 | - choice = (list_.name, list_.name) | |
15 | - LISTS_NAMES.append(choice) | |
11 | +User = get_user_model() | |
16 | 12 | |
17 | 13 | |
18 | -class UserCreationForm(UserCreationForm_): | |
19 | - first_name = forms.CharField(max_length=30, label=_(u'Name'), | |
20 | - widget=forms.TextInput(attrs={'class':'form-control'})) | |
21 | - last_name = forms.CharField(max_length=30, label=_(u'Last name'), | |
22 | - widget=forms.TextInput(attrs={'class':'form-control'})) | |
23 | - email = forms.EmailField(validators=[UniqueValidator(User, 'email')], | |
24 | - widget=forms.TextInput(attrs={'class':'form-control'})) | |
25 | - lists = forms.MultipleChoiceField(label=u'Listas', | |
26 | - required=False, | |
27 | - widget=forms.CheckboxSelectMultiple, | |
28 | - choices=LISTS_NAMES) | |
29 | - | |
14 | +class NewUserForm(forms.ModelForm): | |
15 | + class Meta: | |
16 | + model = User | |
17 | + fields = ('first_name', 'last_name', 'email', 'username') | |
30 | 18 | |
31 | 19 | def __init__(self, *args, **kwargs): |
32 | - super(UserCreationForm, self).__init__(*args, **kwargs) | |
33 | - self.fields.pop('password1') | |
34 | - self.fields.pop('password2') | |
35 | - | |
36 | - | |
37 | -class UserUpdateForm(UserCreationForm): | |
38 | - institution= forms.CharField(max_length=120, label=_(u'Institution'), required=False, | |
39 | - widget=forms.TextInput(attrs={'class':'form-control'})) | |
40 | - role = forms.CharField(max_length=60, label=_(u'Role'), required=False, | |
41 | - widget=forms.TextInput(attrs={'class':'form-control'})) | |
42 | - twitter = forms.URLField(label=_(u'Twitter'), required=False, | |
43 | - widget=forms.TextInput(attrs={'class':'form-control'})) | |
44 | - facebook = forms.URLField(label=_(u'Facebook'), required=False, | |
45 | - widget=forms.TextInput(attrs={'class':'form-control'})) | |
46 | - google_talk = forms.EmailField(label=_(u'Google Talk'), required=False, | |
47 | - widget=forms.TextInput(attrs={'class':'form-control'})) | |
48 | - webpage = forms.URLField(label=_(u'Personal Website/Blog'), required=False, | |
49 | - widget=forms.TextInput(attrs={'class':'form-control'})) | |
20 | + super(NewUserForm, self).__init__(*args, **kwargs) | |
21 | + for field in self.fields.values(): | |
22 | + field.widget.attrs.update({'class': 'form-control'}) | |
23 | + field.required = True | |
50 | 24 | |
51 | - def __init__(self, *args, **kwargs): | |
52 | - super(UserUpdateForm, self).__init__(*args, **kwargs) | |
53 | - self.fields.pop('username') | |
54 | - self.fields.pop('first_name') | |
55 | - self.fields.pop('last_name') | |
56 | - self.fields.pop('email') | |
57 | - self.fields.pop('lists') | |
25 | + | |
26 | +class ListsForm(forms.Form): | |
27 | + LISTS_NAMES = ((list.name, list.name) for list in MailingList.objects.all()) | |
28 | + lists = forms.MultipleChoiceField(label=_(u'Mailing lists'), | |
29 | + required=False, | |
30 | + widget=forms.CheckboxSelectMultiple, | |
31 | + choices=LISTS_NAMES) | ... | ... |
src/accounts/models.py
... | ... | @@ -4,13 +4,13 @@ from django.contrib.auth.models import AbstractUser |
4 | 4 | |
5 | 5 | |
6 | 6 | class User(AbstractUser): |
7 | - institution = models.CharField(max_length=128, null=True) | |
8 | - role = models.CharField(max_length=128, null=True) | |
9 | - twitter = models.CharField(max_length=128, null=True) | |
10 | - facebook = models.CharField(max_length=128, null=True) | |
11 | - google_talk = models.EmailField(null=True) | |
12 | - webpage = models.CharField(max_length=256, null=True) | |
13 | - verification_hash = models.CharField(max_length=32, null=True) | |
7 | + institution = models.CharField(max_length=128, null=True, blank=True) | |
8 | + role = models.CharField(max_length=128, null=True, blank=True) | |
9 | + twitter = models.CharField(max_length=128, null=True, blank=True) | |
10 | + facebook = models.CharField(max_length=128, null=True, blank=True) | |
11 | + google_talk = models.EmailField(null=True, blank=True) | |
12 | + webpage = models.CharField(max_length=256, null=True, blank=True) | |
13 | + verification_hash = models.CharField(max_length=32, null=True, blank=True) | |
14 | 14 | |
15 | 15 | # We need to have `email` field set as unique but Django does not |
16 | 16 | # support field overriding (at least not until 1.6). | ... | ... |
src/accounts/templates/accounts/account_message.html
src/accounts/templates/accounts/email_signup-email-confirmation.html
... | ... | @@ -1,9 +0,0 @@ |
1 | -{% load i18n %} | |
2 | - | |
3 | -{% trans "Welcome to the Colab!" %} | |
4 | - | |
5 | -{% trans "To activate your account, please confirm your mail's activation by accessing the following link:" %} | |
6 | - | |
7 | -<a href="http://{{ server_name }}{% url 'email_verification' hash %}"> | |
8 | - http://{{ server_name }}{% url 'email_verification' hash %} | |
9 | -</a> |
src/accounts/urls.py
... | ... | @@ -5,10 +5,9 @@ from .views import UserProfileDetailView |
5 | 5 | |
6 | 6 | |
7 | 7 | urlpatterns = patterns('', |
8 | - url(r'^$', 'accounts.views.signup', name='signup'), | |
8 | + #url(r'^$', 'accounts.views.signup', name='signup'), | |
9 | 9 | |
10 | - url(r'^verify/(?P<hash>[\w]{32})/$', | |
11 | - 'accounts.views.verify_email', name='email_verification'), | |
10 | + url(r'^register/$', 'accounts.views.signup', name='signup'), | |
12 | 11 | |
13 | 12 | url(r'^(?P<username>[\w@+.-]+)/?$', |
14 | 13 | UserProfileDetailView.as_view(), name='user_profile'), | ... | ... |
src/accounts/views.py
1 | 1 | #!/usr/bin/env python |
2 | 2 | # encoding: utf-8 |
3 | 3 | |
4 | -import uuid | |
5 | -from colab.deprecated import signup as signup_ | |
4 | +from django.contrib import messages | |
6 | 5 | |
7 | -from django.template import RequestContext | |
8 | 6 | from django.contrib.auth import get_user_model |
9 | 7 | from django.views.generic import DetailView |
10 | 8 | from django.utils.translation import ugettext as _ |
11 | -from django.shortcuts import render, get_object_or_404 | |
9 | +from django.shortcuts import render, redirect | |
12 | 10 | |
13 | 11 | from colab.deprecated import solrutils |
12 | +from colab.deprecated import signup as signup_ | |
14 | 13 | |
15 | -from .forms import UserCreationForm | |
16 | 14 | from super_archives.models import EmailAddress, Message |
17 | - | |
18 | - | |
19 | -# helper | |
20 | -def get_field_set(form): | |
21 | - fieldsets = ( | |
22 | - (_('Personal Information'), ( | |
23 | - form['first_name'], | |
24 | - form['last_name'], | |
25 | - form['email'], | |
26 | - form['username'], | |
27 | - ) | |
28 | - ), | |
29 | - (_('Subscribe to mail lists'), ( | |
30 | - form['lists'], | |
31 | - ) | |
32 | - ), | |
33 | - ) | |
34 | - return fieldsets | |
35 | - | |
36 | - | |
37 | -def signup(request): | |
38 | - | |
39 | - # If the request method is GET just return the form | |
40 | - if request.method == 'GET': | |
41 | - form = UserCreationForm() | |
42 | - return render(request, 'accounts/signup-form.html', | |
43 | - {'form': form, 'fieldsets': get_field_set(form)}) | |
44 | - | |
45 | - # If the request method is POST try to store data | |
46 | - form = UserCreationForm(request.POST) | |
47 | - | |
48 | - # If there is validation errors give the form back to the user | |
49 | - if not form.is_valid(): | |
50 | - return render(request, 'accounts/signup-form.html', | |
51 | - {'form': form, 'fieldsets': get_field_set(form)}) | |
52 | - | |
53 | - user = User( | |
54 | - username=form.cleaned_data.get('username'), | |
55 | - email=form.cleaned_data.get('email'), | |
56 | - first_name=form.cleaned_data.get('first_name'), | |
57 | - last_name=form.cleaned_data.get('last_name'), | |
58 | - is_active=False, | |
59 | - ) | |
60 | - user.set_password(form.cleaned_data.get('password1')) | |
61 | - user.save() | |
62 | - | |
63 | - profile = UserProfile( | |
64 | - user=user, | |
65 | - institution=form.cleaned_data.get('institution'), | |
66 | - role=form.cleaned_data.get('role'), | |
67 | - twitter=form.cleaned_data.get('twitter'), | |
68 | - facebook=form.cleaned_data.get('facebook'), | |
69 | - google_talk=form.cleaned_data.get('google_talk'), | |
70 | - webpage=form.cleaned_data.get('webpage'), | |
71 | - verification_hash=uuid.uuid4().get_hex(), | |
72 | - ) | |
73 | - profile.save() | |
74 | - | |
75 | - signup_.send_verification_email(request, user) | |
76 | - | |
77 | - mailing_lists = form.cleaned_data.get('lists') | |
78 | - if mailing_lists: | |
79 | - signup_.send_email_lists(user, mailing_lists) | |
80 | - | |
81 | - | |
82 | - # Check if the user's email have been used previously | |
83 | - # in the mainling lists to link the user to old messages | |
84 | - email_addr, created = EmailAddress.objects.get_or_create(address=user.email) | |
85 | - if created: | |
86 | - email_addr.real_name = user.get_full_name() | |
87 | - | |
88 | - email_addr.user = user | |
89 | - email_addr.save() | |
90 | - | |
91 | - template_data = { | |
92 | - 'msg': _(u'Registration completed successfully. Please visit your email address to validate it.'), | |
93 | - 'msg_css_class': 'alert-success', | |
94 | - } | |
95 | - | |
96 | - return render(request, 'accounts/account_message.html', template_data) | |
97 | - | |
98 | - | |
99 | -def verify_email(request, hash): | |
100 | - """Verify hash and activate user's account""" | |
101 | - | |
102 | - profile = get_object_or_404(UserProfile, verification_hash=hash) | |
103 | - | |
104 | - profile.verification_hash = 'verified' | |
105 | - profile.save() | |
106 | - | |
107 | - profile.user.is_active = True | |
108 | - profile.user.save() | |
109 | - | |
110 | - template_data = { | |
111 | - 'msg': _(u'E-mail validated correctly.'), | |
112 | - 'msg_css_class': 'alert-success', | |
113 | - } | |
114 | - | |
115 | - return render(request, 'accounts/account_message.html', template_data) | |
15 | +from .forms import NewUserForm, ListsForm | |
116 | 16 | |
117 | 17 | |
118 | 18 | class UserProfileDetailView(DetailView): |
... | ... | @@ -141,5 +41,43 @@ class UserProfileDetailView(DetailView): |
141 | 41 | query = query.order_by('-received_time') |
142 | 42 | context['emails'] = query[:10] |
143 | 43 | |
44 | + context.update(kwargs) | |
144 | 45 | return super(UserProfileDetailView, self).get_context_data(**context) |
145 | 46 | |
47 | + | |
48 | +def signup(request): | |
49 | + # If the request method is GET just return the form | |
50 | + if request.method == 'GET': | |
51 | + user_form = NewUserForm() | |
52 | + lists_form = ListsForm() | |
53 | + return render(request, 'registration/registration_form.html', | |
54 | + {'user_form': user_form, 'lists_form': lists_form}) | |
55 | + | |
56 | + user_form = NewUserForm(request.POST) | |
57 | + lists_form = ListsForm(request.POST) | |
58 | + | |
59 | + if not user_form.is_valid() or not lists_form.is_valid(): | |
60 | + return render(request, 'registration/registration_form.html', | |
61 | + {'user_form': user_form, 'lists_form': lists_form}) | |
62 | + | |
63 | + user = user_form.save() | |
64 | + | |
65 | + mailing_lists = lists_form.cleaned_data.get('lists') | |
66 | + if mailing_lists: | |
67 | + signup_.send_email_lists(user, mailing_lists) | |
68 | + | |
69 | + # Check if the user's email have been used previously | |
70 | + # in the mainling lists to link the user to old messages | |
71 | + email_addr, created = EmailAddress.objects.get_or_create(address=user.email) | |
72 | + if created: | |
73 | + email_addr.real_name = user.get_full_name() | |
74 | + | |
75 | + email_addr.user = user | |
76 | + email_addr.save() | |
77 | + | |
78 | + messages.success(request, _('Your profile has been created!')) | |
79 | + messages.warning(request, _('You must login to validated your profile. ' | |
80 | + 'Profiles not validated are deleted in 24h.')) | |
81 | + | |
82 | + return redirect('user_profile', username=user.username) | |
83 | + | ... | ... |
src/colab/custom_settings.py
... | ... | @@ -23,7 +23,6 @@ INSTALLED_APPS = INSTALLED_APPS + ( |
23 | 23 | 'cliauth', |
24 | 24 | 'django_browserid', |
25 | 25 | 'conversejs', |
26 | - 'registration', | |
27 | 26 | |
28 | 27 | # Own apps |
29 | 28 | 'super_archives', |
... | ... | @@ -145,6 +144,14 @@ STATIC_ROOT = os.path.join(BASE_DIR, '..', 'www', 'static') |
145 | 144 | |
146 | 145 | AUTH_USER_MODEL = 'accounts.User' |
147 | 146 | |
147 | +from django.contrib.messages import constants as messages | |
148 | +MESSAGE_TAGS = { | |
149 | + messages.INFO: 'alert-info', | |
150 | + messages.SUCCESS: 'alert-success', | |
151 | + messages.WARNING: 'alert-warning', | |
152 | + messages.ERROR: 'alert-danger', | |
153 | +} | |
154 | + | |
148 | 155 | |
149 | 156 | ### Proxy configuration |
150 | 157 | SOCKS_SERVER = None | ... | ... |
src/colab/deprecated/templates/base.html
... | ... | @@ -47,8 +47,6 @@ |
47 | 47 | <div class="row"> |
48 | 48 | </div> |
49 | 49 | |
50 | - {% block header %}{% endblock %} | |
51 | - | |
52 | 50 | <nav class="navbar navbar-default navbar-fixed-top" role="navigation"> |
53 | 51 | <div class="navbar-header"> |
54 | 52 | <button type="button" class="navbar-toggle" data-toggle="collapse" data-target=".navbar-main"> |
... | ... | @@ -119,6 +117,17 @@ |
119 | 117 | </div> |
120 | 118 | </nav> |
121 | 119 | |
120 | + {% block messages %} | |
121 | + {% for message in messages %} | |
122 | + <div class="alert alert-dismissable {{ message.tags }}"> | |
123 | + <button type="button" class="close" data-dismiss="alert" aria-hidden="true">×</button> | |
124 | + {{ message }} | |
125 | + </div> | |
126 | + {% endfor %} | |
127 | + {% endblock %} | |
128 | + | |
129 | + {% block header %}{% endblock %} | |
130 | + | |
122 | 131 | <div> |
123 | 132 | {% block main-content %} {% endblock %} |
124 | 133 | </div> | ... | ... |