ungleich-user/dal/dal/views.py

253 lines
11 KiB
Python

from django.shortcuts import render
from django.views.generic import View
from django.contrib.auth import authenticate, login
from django.contrib.auth.models import User
from django.http import HttpResponse, HttpResponseRedirect
from django.core.validators import email_re
from django.urls import reverse_lazy
# Check to see if the username is already taken
# Helper function, not to be set up as a view
# First checks the DB, since ldap parks users there
# After that, check LDAP directly if the user just never
# logged in
def check_user_exists(username):
if User.objects.filter(username=username).exists():
return True
# TODO: Needs to look up the LDAP
else return False
# The index page
# If there's a session open, it will give the user the options he/she/it can do, if not,
# it will show a landing page explaining what this is and prompt them to login
class Index(View):
# Basic binary choice, if it is an authenticated user, go straight to the options page,
# if not, then show the landing page
def get(self, request):
if request.user.is_authenticated:
return render(request, 'useroptions.html', { 'user': request.user } )
return render(request, 'landing.html')
# Basically does the same as the GET request, just with trying to login the user beforehand
# Shows an errorpage if authentication fails, since just looping to the landing page
# would be frustrating
def post(self, request):
username = request.POST.get('username')
password = request.POST.get('password')
user = authenticate(request, username=username, password=password)
if user is not None:
login(request, user)
return render(request, 'useroptions.html', { 'user': user } )
return render(request, 'loginfailed.html')
# Registering a user
class Register(View):
# Someone wants to register, throw up the page for that
def get(self, request):
return render(request, 'registeruser.html')
# Someone filled out the register page, do some basic checks and throw it at nameko
def post(self, request):
# message for the error template
service = 'register an user'
# urlname for 'go back' on the errorpage
urlname = 'register'
username = request.POST.get('username')
# Check to see if username is already taken
if check_user_exists(username):
return render(request, 'registererror.html', { 'urlname': urlname, 'service': service, 'error': 'User already exists.' } )
# isalnum() may be a bit harsh, but is the most logical choice to make sure it's a username we
# can use
elif not username.isalnum():
return render(request, 'registererror.html', { 'urlname': urlname, 'service': service, 'error': 'Username has to be alphanumeric.' } )
password1 = request.POST.get('password1')
password2 = request.POST.get('password2')
# check if the supplied passwords match
if password1 != password2:
return render(request, 'registererror.html', { 'urlname': urlname, 'service': service,
'error': 'Your passwords didn\'t match. Please supply the same password twice.' } )
email = request.POST.get('email')
# Is the emailaddress valid?
if not email_re.match(email):
return render(request, 'registererror.html', { 'urlname': urlname, 'service': service, 'error': 'The supplied email address is invalid.' } )
firstname = request.POST.get('firstname')
lastname = request.POST.get('lastname')
if firstname == "" or not firstname or lastname == "" or not lastname
return render(request, 'registererror.html', { 'urlname': urlname, 'service': service, 'error': 'Please enter your firstname and lastname.' } )
# throw it to nameko to create the user
if self.create_user(username, password1, firstname, lastname, email):
return render(request, 'usercreated.html', { 'user': username } )
return render(request, 'error.html', { 'urlname': urlname, 'service': service, 'error': 'Unknown error while creating the user.' } )
def create_user(self, username, password, firstname, lastname, email):
#TODO: write nameko function to create a user
return True
# Change user data for logged in users
class ChangeData(View):
# provide the form for the change request
def get(self, request):
if not request.user.is_authenticated:
return render(request, 'mustbeloggedin.html')
user = request.user
login(request, user)
# get basic data (firstname, lastname, email)
(firstname, lastname, email) = self.get_data(user)
# The template puts the old data as standard in the fields
return render(request, 'changeuserdata.html', { 'user': user, 'firstname': firstname, 'lastname': lastname, 'email': email } )
# get the change request
def post(self, request):
# variables for the error page
service = 'change user data'
urlname = 'change_data'
if not request.user.is_authenticated:
return render(request, 'mustbeloggedin.html')
user = request.user
firstname = request.POST.get('firstname')
lastname = request.POST.get('lastname')
email = request.POST.get('email')
# Some sanity checks for the supplied data
if firstname == "":
return render(request, 'error.html', { 'urlname': urlname, 'service': service, 'error': 'Please enter a firstname.' } )
elif lastname == "":
return render(request, 'error.html', { 'urlname': urlname, 'service': service, 'error': 'Please enter a lastname.' } )
elif email == "":
return render(request, 'error.html', { 'urlname': urlname, 'service': service, 'error': 'Please enter an email.' } )
elif not email_re.match(email):
return render(request, 'error.html', { 'urlname': urlname, 'service': service, 'error': 'The supplied email address is invalid.' } )
# Trying to change the data
if self.change_data(firstname, lastname, email):
return render(request, 'changeddata.html', { 'user': user, 'firstname': firstname, 'lastname': lastname, 'email': email } )
return render(request, 'error.html', { 'urlname': urlname, 'service': service, 'error': 'An unknown error occurred.' } )
# TODO: call nameko to get basic data from user
def get_data(self, user):
return ("a", "b", "c")
# TODO: call nameko to change user data and think about return value
def change_data(self, firstname, lastname, email):
return True
# Resets the password for a user
# Will need to send a confirmation email to the user and we will need a backend
# to confirm the request came from someone who has access to the email
# Out of scope except for creating the workflow
class ResetPassword(View):
# Presents the form with some information
def get(self, request):
return render(request, 'resetpassword.html')
# gets the data from confirming the reset request and checks if it was not a misclick
# (by having the user type in his username
def post(self, request):
urlname = 'reset_password'
service = 'send a password reset request'
user = request.POST.get('user')
if check_user_exists(user):
# TODO: Get a good backend for reset requests
# Sending the reset request
email = self.send_resetrequest(user)
return render(request, 'send_resetrequest.html', { 'user': user, 'email': email } )
return render(request, 'error.html', { 'urlname': urlname, 'service': service, 'error': 'The user does not exist.' } )
def send_resetrequest(self, user):
#TODO: call nameko to get the associated email and send a confirmation mail
return "test@example.com"
# The logged in user can change the password here
class ChangePassword(View):
# Presents the page for a logged in user
def get(self, request):
if not request.user.is_authenticated:
return render(request, 'mustbeloggedin.html')
return render(request, 'changepassword.html', { 'user': request.user } )
# Does some checks on the supplied data and changes the password
def post(self, request):
# Variables for the error page
urlname = 'change_password'
service = 'change the password'
if not request.user.is_authenticated:
return render(request, 'mustbeloggedin.html')
login(request, request.user)
user = request.user
oldpassword = request.POST.get('oldpassword')
check = authenticate(request, username=user, password=oldpassword)
# Is the right password for the user supplied?
if check is None:
return render(request, 'error.html', { 'urlname': urlname, 'service': service, 'error': 'Wrong password for the user.' } )
password1 = request.POST.get('password1')
password2 = request.POST.get('password2')
# Are both passwords from the form the same?
if password1 != password2:
return render(request, 'error.html', { 'urlname': urlname, 'service': service,
'error': 'Please check if you typed the same password both times for the new password' } )
# Trying to change the password
if self.change_password(user, oldpassword, password1):
return render(request, 'changedpassword.html', { 'user': user } )
else:
return render(request, 'error.html', { 'urlname': urlname, 'service': service, 'error': 'Unknown error while changing the password!' } )
# Changes the password for the supplied user
def change_password(self, user, oldpassword, password):
#TODO: write nameko function to change a password
return True
class DeleteAccount(View):
def get(self, request):
return render(request, 'deleteaccount.html')
def post(self, request):
# Variables for error page
urlname = 'account_delete'
service = 'delete an account'
# Does the user exist?
username = request.POST.get('username')
if not check_user_exists(username):
return render(request, 'error.html', { 'urlname': urlname, 'service': service, 'error': 'Unknown user.' } )
# Do user and password match?
password = request.POST.get('password')
check = authenticate(request, username=username, password=password)
if check is None:
return render(request, 'error.html', { 'urlname': urlname, 'service': service, 'error': 'Wrong password for user.' } )
# Try to delete the user
if self.delete_user(username):
return render(request, 'deleteduser.html', { 'user': username } )
return render(request, 'error.html', { 'urlname': urlname, 'service': service, 'error': 'Unknown error while trying to delete the user.' } )
def delete_user(self, username):
#TODO: nameko call to delete the user
return True