diff --git a/app/password.py b/app/password.py index d8afd66..5153c8f 100644 --- a/app/password.py +++ b/app/password.py @@ -7,11 +7,11 @@ from flask import ( from flask_wtf import FlaskForm from wtforms import ( StringField, PasswordField, - SubmitField + SubmitField, EmailField ) from wtforms.validators import ( ValidationError, DataRequired, - EqualTo, Length, Regexp + EqualTo, Length, Regexp, Email ) bp = Blueprint('password', __name__, url_prefix='/password') @@ -37,14 +37,15 @@ class ChangePasswordForm(FlaskForm): # "(?=.*[@$!%*#?&])", message="Password must contain a special character" #),], ], - render_kw={"onkeyup": f"validate_form({minlength})"}) + render_kw={"onkeyup": f"validate_username_form({minlength})"}) confirm_password = PasswordField( label=('Confirm Password'), validators=[DataRequired(message='* Required'), EqualTo('newpassword')], - render_kw={"onkeyup": f"validate_confirm({minlength})"}) + render_kw={"onkeyup": f"validate_username_form({minlength})"}) - submit = SubmitField(label=('Change my password'), render_kw={"onclick": f"validate_form({minlength})"}) + submit = SubmitField(label=('Change my password'), render_kw={"disabled": "true", + "onclick": f"validate_username_form({minlength})"}) # Validators def validate_username(self, username): @@ -54,7 +55,15 @@ class ChangePasswordForm(FlaskForm): raise ValidationError( f"Character {char} is not allowed in an username.") -@bp.route('/change', methods=('GET', 'POST')) +class ResetPasswordForm(FlaskForm): + email = EmailField(label=('Email address'), + validators=[DataRequired(), Email()], + render_kw={"onkeyup": f"validate_email()"}) + + submit = SubmitField(label=('Change my password'), render_kw={"disabled": "true", + "onclick": f"validate_email()"}) + +@bp.route('/change', methods=["GET", "POST"]) def change(): form = ChangePasswordForm() if form.validate_on_submit(): @@ -71,3 +80,7 @@ def change(): client.unbind() return render_template('change.html', form=form) + +@bp.route('/reset', methods=["GET"]) +def reset(): + return render_template('reset.html') \ No newline at end of file diff --git a/app/ui/static/css/main.css b/app/ui/static/css/main.css index 9e4542f..c69a498 100644 --- a/app/ui/static/css/main.css +++ b/app/ui/static/css/main.css @@ -15,6 +15,17 @@ body { background-attachment: fixed; } +#main-block > div { + box-shadow: 1px 1px 10px black; + border-radius: .50rem; + background: #4e4e4e; + margin: 1em; +} + +#main-block > div > *:first-child { + margin: 1em; +} + .vcenter { position: absolute; left: 50%; @@ -65,7 +76,7 @@ a:hover>span { } #password-msg li::before { - content: "☑ "; + content: "OK - "; } .errorinput { @@ -78,7 +89,7 @@ a:hover>span { } li.errormsg::before { - content: "☒ " !important; + content: "KO - " !important; } @@ -91,9 +102,4 @@ li.errormsg::before { border-color: #5cb85c; box-shadow: 0 0 0 .10rem rgba(92, 184, 92, 0.50); -webkit-box-shadow: 0 0 0 .10rem rgba(92, 184, 92, 0.50); -} - -#change-form { - background: #4e4e4e; - border-radius: .50rem; -} +} \ No newline at end of file diff --git a/app/ui/static/js/validate.js b/app/ui/static/js/validate.js index 8d7feeb..cf18633 100644 --- a/app/ui/static/js/validate.js +++ b/app/ui/static/js/validate.js @@ -1,8 +1,34 @@ -function validate_form(minlength) { +function validate_username_form(minlength) { var user = validate_username(); var pass = validate_password(minlength); - return validate_confirm() && pass && user; + if (validate_confirm() && pass && user) { + disable_submit(false); + return true; + } + + disable_submit(true); + return false; +} + +function disable_submit(status) { + document.getElementById("submit").disabled = status; +} + +function validate_email() { + var email = document.getElementById("email"); + var re = /^(([^<>()[\]\\.,;:\s@\"]+(\.[^<>()[\]\\.,;:\s@\"]+)*)|(\".+\"))@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\])|(([a-zA-Z\-0-9]+\.)+[a-zA-Z]{2,}))$/; + + if (re.test(email.value) != true) { + disable_submit(true); + email.classList.add("errorinput"); + return false; + } + + + disable_submit(false); + email.classList.remove("errorinput"); + return true; } function validate_confirm() { @@ -25,15 +51,16 @@ function validate_username() { var username = document.getElementById("username"); var forbidden = /[*?!'\^+%\&/()=}{\$#;,\\"]+/; - if (username.value.length > 64 || forbidden.test(username.value) == true) - { + if (username.value.length > 64 || forbidden.test(username.value) == true) { document.getElementById("username-msg").classList.add("errormsg"); username.classList.add("errorinput"); + disable_submit(true); return false; } document.getElementById("username-msg").classList.remove("errormsg"); username.classList.remove("errorinput"); + disable_submit(false); return true; } @@ -43,8 +70,7 @@ function validate_password(minlength) { // Target element var password = document.getElementById("newpassword"); // Check the length - if (password.value.length < minlength) - { + if (password.value.length < minlength) { status = false; document.getElementById("minlen").classList.add("errormsg"); } @@ -71,11 +97,10 @@ function validate_password(minlength) { } else document.getElementById("upper").classList.remove("errormsg"); + // Change the color of the inputbox if (status == false) - { password.classList.add("errorinput"); - } else password.classList.remove("errorinput"); diff --git a/app/ui/templates/base.html b/app/ui/templates/base.html index 4ad51cb..649fb1b 100644 --- a/app/ui/templates/base.html +++ b/app/ui/templates/base.html @@ -5,20 +5,20 @@ - AlxCzl - LDAP Interface + AlxCzl - {% block title %}{% endblock title %} - + - + {% for message in get_flashed_messages() %}
{{ message }}
{% endfor %} -
- {% block main_block %}{% endblock main_block %} +
+ {% block main_block %}{% endblock main_block %}
{% block script_block %}{% endblock script_block %} diff --git a/app/ui/templates/change.html b/app/ui/templates/change.html index 529d1bd..198d6e1 100644 --- a/app/ui/templates/change.html +++ b/app/ui/templates/change.html @@ -1,48 +1,53 @@ {% extends 'base.html' %} +{% block title %}Password change{% endblock %} + {% block main_block %} -
+
+
+

Password change

+
{{ form.csrf_token() }} -
+
{{ form.username.label }} -
- The username can contain at most 64 characters and cannot contain one of the following characters : [*?!'^+%&/()=}{$#;,\" -
{{ form.username(class="form-control") }} + + The username can contain at most 64 characters and cannot contain one of the following characters : + [*?!'^+%&/()=}{$#;,\" +
-
+
{{ form.currentpassword.label }} {{ form.currentpassword(class="form-control") }}
-
+
{{ form.newpassword.label }} -
- The new password should contain at least : + {{ form.newpassword(class="form-control") }} + + The new password should at least contain the following:
  • {{ form.minlength }} characters
  • 1 numeric digit [0-9]
  • 1 lowercase character [a-z]
  • 1 uppercase character [A-Z]
-
- {{ form.newpassword(class="form-control") }} +
-
+
{{ form.confirm_password.label }} -
- Passwords must match -
{{ form.confirm_password(class="form-control") }} + + Passwords must match +
-
-
- {{ form.submit(class="btn btn-primary")}} -
+ {{ form.submit(class="btn btn-primary")}} + I forgot my password
+
{% endblock main_block %} {% block script_block %} -{% endblock script_block %} +{% endblock script_block %} \ No newline at end of file diff --git a/app/ui/templates/reset.html b/app/ui/templates/reset.html new file mode 100644 index 0000000..e4c8e25 --- /dev/null +++ b/app/ui/templates/reset.html @@ -0,0 +1,20 @@ +{% extends 'base.html' %} + +{% block title %}Password reset{% endblock %} + +{% block main_block %} +
+
+

Password reset

+
+
Sorry, password self-reset isn't available on my intranet for security reasons.
+ Just contact me and I'll send you a message containing a new password. +
+ I just need to change it +
+
+{% endblock main_block %} + +{% block script_block %} + +{% endblock script_block %} diff --git a/requirements.txt b/requirements.txt index 89e7f5c..071afd4 100644 --- a/requirements.txt +++ b/requirements.txt @@ -9,4 +9,5 @@ typing_extensions==4.0.0 Werkzeug==2.0.2 zipp==3.6.0 ldap3 -Flask-WTF==1.0.0 \ No newline at end of file +Flask-WTF==1.0.0 +email-validator \ No newline at end of file