Password and User settings Form implemented
This commit is contained in:
parent
b63cfaa741
commit
f31771b588
72
forms.py
72
forms.py
@ -1,7 +1,9 @@
|
|||||||
from django import forms
|
from django import forms
|
||||||
from django.contrib.auth.models import User
|
from django.contrib.auth.models import User
|
||||||
from django.contrib.auth.forms import UserCreationForm, UserChangeForm
|
from django.contrib.auth.forms import UserCreationForm, UserChangeForm, PasswordChangeForm
|
||||||
from .models import UserProfile
|
from django.utils.translation import gettext as _
|
||||||
|
from .models import UserProfile, get_userprofile
|
||||||
|
from users import emails
|
||||||
|
|
||||||
|
|
||||||
class UserRegistrationForm(UserCreationForm):
|
class UserRegistrationForm(UserCreationForm):
|
||||||
@ -24,6 +26,72 @@ class UserProfileFormLanguageOnly(forms.ModelForm):
|
|||||||
fields = ['language_code']
|
fields = ['language_code']
|
||||||
|
|
||||||
|
|
||||||
|
class UserPasswordChangeForm(PasswordChangeForm):
|
||||||
|
email = forms.EmailField()
|
||||||
|
first_name = forms.CharField(max_length=150)
|
||||||
|
last_name = forms.CharField(max_length=150)
|
||||||
|
field_order = ["email", "first_name", "last_name", "old_password", "new_password1", "new_password2"]
|
||||||
|
|
||||||
|
def __init__(self, request):
|
||||||
|
self.request = request
|
||||||
|
#
|
||||||
|
data = request.POST or {'email': request.user.email, 'first_name': request.user.first_name, 'last_name': request.user.last_name}
|
||||||
|
#
|
||||||
|
super().__init__(request.user, data)
|
||||||
|
self.fields['old_password'].widget.attrs.update({'autofocus': False})
|
||||||
|
self.fields['old_password'].required = False
|
||||||
|
|
||||||
|
def clean_old_password(self):
|
||||||
|
"""
|
||||||
|
Validation of old_password field only, if set.
|
||||||
|
"""
|
||||||
|
old_password = self.cleaned_data["old_password"]
|
||||||
|
if old_password and not self.user.check_password(old_password):
|
||||||
|
raise forms.ValidationError(
|
||||||
|
self.error_messages["password_incorrect"],
|
||||||
|
code="password_incorrect",
|
||||||
|
)
|
||||||
|
return old_password
|
||||||
|
|
||||||
|
def clean(self):
|
||||||
|
"""
|
||||||
|
Validation of new_passwords only if old_password field is set.
|
||||||
|
"""
|
||||||
|
clean_data = forms.Form.clean(self)
|
||||||
|
old_password = clean_data.get('old_password')
|
||||||
|
#
|
||||||
|
if old_password:
|
||||||
|
self.validate_passwords("new_password1", "new_password2")
|
||||||
|
self.validate_password_for_user(self.user, "new_password2")
|
||||||
|
return forms.Form.clean(self)
|
||||||
|
|
||||||
|
def save(self, commit=True):
|
||||||
|
changed = False
|
||||||
|
for key in self.fields:
|
||||||
|
new = self.data.get(key)
|
||||||
|
try:
|
||||||
|
old = getattr(self.user, key)
|
||||||
|
except AttributeError:
|
||||||
|
pass # Is a password field
|
||||||
|
else:
|
||||||
|
if new != old:
|
||||||
|
if key == 'email':
|
||||||
|
emails.send_validation_mail(self.user, self.request)
|
||||||
|
up = get_userprofile(self.user)
|
||||||
|
up.mail_pending = new
|
||||||
|
up.save()
|
||||||
|
else:
|
||||||
|
changed = True
|
||||||
|
setattr(self.user, key, new)
|
||||||
|
if self.data.get('new_password1'):
|
||||||
|
changed = True
|
||||||
|
self.user.set_password(self.data.get('new_password1'))
|
||||||
|
#
|
||||||
|
if changed:
|
||||||
|
self.user.save()
|
||||||
|
return changed
|
||||||
|
|
||||||
|
|
||||||
class UserActivationForm(UserChangeForm):
|
class UserActivationForm(UserChangeForm):
|
||||||
password = None
|
password = None
|
||||||
|
|
||||||
|
18
migrations/0004_userprofile_mail_pending.py
Normal file
18
migrations/0004_userprofile_mail_pending.py
Normal file
@ -0,0 +1,18 @@
|
|||||||
|
# Generated by Django 5.1.2 on 2024-10-27 17:50
|
||||||
|
|
||||||
|
from django.db import migrations, models
|
||||||
|
|
||||||
|
|
||||||
|
class Migration(migrations.Migration):
|
||||||
|
|
||||||
|
dependencies = [
|
||||||
|
('users', '0003_userprofile_mail_validated'),
|
||||||
|
]
|
||||||
|
|
||||||
|
operations = [
|
||||||
|
migrations.AddField(
|
||||||
|
model_name='userprofile',
|
||||||
|
name='mail_pending',
|
||||||
|
field=models.EmailField(max_length=254, null=True),
|
||||||
|
),
|
||||||
|
]
|
@ -30,6 +30,7 @@ class UserProfile(models.Model):
|
|||||||
timezone = models.CharField(max_length=150, default='UTC', choices=[(t, t) for t in pytz.common_timezones])
|
timezone = models.CharField(max_length=150, default='UTC', choices=[(t, t) for t in pytz.common_timezones])
|
||||||
language_code = models.CharField(max_length=150, default='en', choices=settings.LANGUAGES)
|
language_code = models.CharField(max_length=150, default='en', choices=settings.LANGUAGES)
|
||||||
mail_validated = models.BooleanField(default=False)
|
mail_validated = models.BooleanField(default=False)
|
||||||
|
mail_pending = models.EmailField(null=True)
|
||||||
|
|
||||||
def export_key(self):
|
def export_key(self):
|
||||||
return self.user.username
|
return self.user.username
|
||||||
|
@ -4,7 +4,14 @@
|
|||||||
{% block content %}
|
{% block content %}
|
||||||
<form action="" method="post">
|
<form action="" method="post">
|
||||||
{% csrf_token %}
|
{% csrf_token %}
|
||||||
{% include 'users/profile_formdata.html' %}
|
|
||||||
|
{% get_current_language as LANGUAGE_CODE %}
|
||||||
|
<h1>{% trans "Language and Timezone" %}</h1>
|
||||||
|
{{ form_userprofile.as_p }}
|
||||||
|
|
||||||
|
<h1>{% trans "Userdata and Password" %}</h1>
|
||||||
|
{{ form_userchange.as_p }}
|
||||||
|
|
||||||
<input type="submit" value="{% trans "Save" %}" class="button" />
|
<input type="submit" value="{% trans "Save" %}" class="button" />
|
||||||
</form>
|
</form>
|
||||||
|
|
||||||
|
@ -1,6 +0,0 @@
|
|||||||
{% load i18n %}
|
|
||||||
|
|
||||||
{% get_current_language as LANGUAGE_CODE %}
|
|
||||||
<h1>{% trans "Language and Timezone" %}</h1>
|
|
||||||
{{ form_userprofile.as_p }}
|
|
||||||
</select>
|
|
81
views.py
81
views.py
@ -11,7 +11,7 @@ from django.contrib.auth.models import User
|
|||||||
from django.utils.encoding import force_str
|
from django.utils.encoding import force_str
|
||||||
from django.utils.http import urlsafe_base64_decode
|
from django.utils.http import urlsafe_base64_decode
|
||||||
from django.utils.translation import gettext as _
|
from django.utils.translation import gettext as _
|
||||||
from .forms import UserRegistrationForm, UserProfileForm, UserActivationForm
|
from .forms import UserRegistrationForm, UserProfileForm, UserActivationForm, UserPasswordChangeForm
|
||||||
import logging
|
import logging
|
||||||
from .models import get_userprofile
|
from .models import get_userprofile
|
||||||
from themes import Context
|
from themes import Context
|
||||||
@ -28,37 +28,28 @@ def password_recovery(request):
|
|||||||
return redirect(request.GET.get('next') or '/')
|
return redirect(request.GET.get('next') or '/')
|
||||||
|
|
||||||
|
|
||||||
def profile_post_actions(request, context):
|
|
||||||
if request.POST:
|
|
||||||
form = context.get('form_userprofile')
|
|
||||||
if form.is_valid():
|
|
||||||
form.save()
|
|
||||||
return redirect(request.GET.get('next') or '/')
|
|
||||||
|
|
||||||
|
|
||||||
def profile_pre_actions(request, context, form_to_be_used=UserProfileForm):
|
|
||||||
profile = get_userprofile(request.user)
|
|
||||||
if request.POST:
|
|
||||||
form = form_to_be_used(request.POST, instance=profile)
|
|
||||||
else:
|
|
||||||
form = form_to_be_used(instance=profile)
|
|
||||||
context['form_userprofile'] = form
|
|
||||||
|
|
||||||
|
|
||||||
@login_required
|
@login_required
|
||||||
def profile(request):
|
def profile(request):
|
||||||
context = Context(request) # needs to be executed first because of time mesurement
|
context = Context(request) # needs to be executed first because of time mesurement
|
||||||
profile_pre_actions(request, context)
|
profile = get_userprofile(request.user)
|
||||||
response = profile_post_actions(request, context)
|
if request.POST:
|
||||||
if response is not None:
|
form_userprofile = UserProfileForm(request.POST, instance=profile)
|
||||||
return response
|
form_userchange = UserPasswordChangeForm(request)
|
||||||
|
if form_userprofile.is_valid() and form_userchange.is_valid():
|
||||||
|
form_userprofile.save()
|
||||||
|
form_userchange.save()
|
||||||
|
return redirect(request.GET.get('next') or '/')
|
||||||
else:
|
else:
|
||||||
context_adaption(
|
form_userprofile = UserProfileForm(instance=profile)
|
||||||
context,
|
form_userchange = UserPasswordChangeForm(request)
|
||||||
request,
|
context_adaption(
|
||||||
_('Profile for %(username)s') % {'username': request.user.username},
|
context,
|
||||||
)
|
request,
|
||||||
return render(request, 'users/profile.html', context=context)
|
_('Profile for %(username)s') % {'username': request.user.username},
|
||||||
|
form_userprofile=form_userprofile,
|
||||||
|
form_userchange=form_userchange,
|
||||||
|
)
|
||||||
|
return render(request, 'users/profile.html', context=context)
|
||||||
|
|
||||||
|
|
||||||
def register(request):
|
def register(request):
|
||||||
@ -158,20 +149,30 @@ def validate(request, uidb64, token):
|
|||||||
myuser = None
|
myuser = None
|
||||||
|
|
||||||
if myuser is not None and generate_token.check_token(myuser, token):
|
if myuser is not None and generate_token.check_token(myuser, token):
|
||||||
# Store mail validation to user profile
|
up = get_userprofile(myuser)
|
||||||
profile = get_userprofile(myuser)
|
if up.mail_pending:
|
||||||
profile.mail_validated = True
|
# change of email-address
|
||||||
profile.save()
|
myuser.email = up.mail_pending
|
||||||
if not parameter.get(parameter.USERS_ADMIN_ACTIVATION):
|
|
||||||
# Activate user
|
|
||||||
myuser.is_active = True
|
|
||||||
myuser.save()
|
myuser.save()
|
||||||
messages.success(request, _("Your Account has been activated."))
|
up.mail_pending = None
|
||||||
return redirect('users-login')
|
up.save()
|
||||||
else:
|
messages.success(request, _("Your new email address is now active."))
|
||||||
emails.send_activation_mail(myuser, request)
|
|
||||||
messages.success(request, _("Your Email has been validated. Wait for the administrator to activate your account"))
|
|
||||||
return redirect("/")
|
return redirect("/")
|
||||||
|
else:
|
||||||
|
# Store mail validation to user profile
|
||||||
|
profile = get_userprofile(myuser)
|
||||||
|
profile.mail_validated = True
|
||||||
|
profile.save()
|
||||||
|
if not parameter.get(parameter.USERS_ADMIN_ACTIVATION):
|
||||||
|
# Activate user
|
||||||
|
myuser.is_active = True
|
||||||
|
myuser.save()
|
||||||
|
messages.success(request, _("Your Account has been activated."))
|
||||||
|
return redirect('users-login')
|
||||||
|
else:
|
||||||
|
emails.send_activation_mail(myuser, request)
|
||||||
|
messages.success(request, _("Your Email has been validated. Wait for the administrator to activate your account"))
|
||||||
|
return redirect("/")
|
||||||
else:
|
else:
|
||||||
context_adaption(
|
context_adaption(
|
||||||
context,
|
context,
|
||||||
|
Loading…
x
Reference in New Issue
Block a user