from flask import redirect, url_for, request, flash from flask_login import login_user, logout_user, login_required, current_user from urllib.parse import urlparse, urljoin from app import app from app.forms.login import LoginForm from app.models.user import Member from app.models.priv import Group from app.utils.render import render from app.utils.send_mail import send_validation_mail from app.utils.check_csrf import check_csrf import datetime @app.route('/connexion', methods=['GET', 'POST']) def login(): # If something failed, return abort("Message") def _abort(msg): flash(msg, 'error') if request.referrer: return redirect(request.referrer) return redirect(url_for('index')) if current_user.is_authenticated: return redirect(url_for('index')) form = LoginForm() lateral = LoginForm(prefix="menu_") if lateral.validate_on_submit(): form = lateral if form.validate_on_submit(): member = Member.query.filter_by(name=form.username.data).first() # Check if member can login if member is not None and "No login" in [g.name for g in member.groups]: return _abort('Cet utilisateur ne peut pas se connecter') # Check if password is ok if member is None or not member.check_password(form.password.data): return _abort('Pseudo ou mot de passe invalide') # Check if user is activated if member.email_confirmed == False: # Send another mail send_validation_mail(member.name, member.email) return _abort(f"Email non confirmé. Un mail de confirmation a de nouveau été envoyé à l'adresse {member.email}") # Login & update time-based trophies login_user(member, remember=form.remember_me.data, duration=datetime.timedelta(days=7)) member.update_trophies("on-login") app.v5logger.info(f"<{member.name}> has logged in") # Redirect safely (https://huit.re/open-redirect) def is_safe_url(target): ref_url = urlparse(request.host_url) test_url = urlparse(urljoin(request.host_url, target)) return test_url.scheme in ('http', 'https') and \ ref_url.netloc == test_url.netloc next = request.args.get('next') if next and is_safe_url(next): return redirect(next) if request.referrer: return redirect(request.referrer) return redirect(url_for('index')) return render('account/login.html', form=form) @app.route('/deconnexion') @login_required @check_csrf def logout(): name = current_user.name logout_user() flash('Déconnexion réussie', 'info') app.v5logger.info(f"<{name}> has logged out") if request.referrer: return redirect(request.referrer) return redirect(url_for('index'))