Repository: CiviWiki/OpenCiviWiki

Issue:
Create reset password view under the accounts app.
Currently, when the user wants to reset the password, they go to a Django admin page, which has a different look.  Newly implemented registration and login views have been created under the '/accounts/' path. This task is to replace the current reset password page with a page that looks like the registration and login pages.


Discussion:
@brylie can you please assign this task to me. I created it to complete the work done on the user registration/login section. This task is to migrate the current reset password page into the new '/accounts/' path.
Thanks @a7madnassar!
@brylie I have the reset password functionality working. But I have to wait for the Celery pull request I just submitted to be accepted. Once you merge my last Celery removal changes. I will submit another pull request for the password reset flow.

Thanks
@a7madnassar I just merged the Celery PR :-)
@brylie cool, I will submit another PR for this soon. Thanks

Resolving patch:
diff --git a/project/accounts/views.py b/project/accounts/views.py
--- a/project/accounts/views.py
+++ b/project/accounts/views.py
@@ -14,6 +14,7 @@
 from django.utils.http import int_to_base36
 from django.utils.crypto import salted_hmac
 from django.utils.http import urlsafe_base64_encode
+from django.urls import reverse_lazy
 
 from api.models.account import Account
 
@@ -76,3 +77,24 @@ def form_valid(self, form):
         self._login(user)
 
         return super(RegisterView, self).form_valid(form)
+
+
+class PasswordResetView(auth_views.PasswordResetView):
+    template_name = 'accounts/users/password_reset.html'
+    email_template_name = 'accounts/users/password_reset_email.html'
+    subject_template_name = 'accounts/users/password_reset_subject.txt'
+    from_email = settings.EMAIL_HOST_USER
+    success_url = reverse_lazy('accounts_password_reset_done')
+
+
+class PasswordResetDoneView(auth_views.PasswordResetDoneView):
+    template_name = 'accounts/users/password_reset_done.html'
+
+
+class PasswordResetConfirmView(auth_views.PasswordResetConfirmView):
+    template_name = 'accounts/users/password_reset_confirm.html'
+    success_url = reverse_lazy('accounts_password_reset_complete')
+
+
+class PasswordResetCompleteView(auth_views.PasswordResetCompleteView):
+    template_name = 'accounts/users/password_reset_complete.html'
diff --git a/project/core/settings.py b/project/core/settings.py
--- a/project/core/settings.py
+++ b/project/core/settings.py
@@ -175,3 +175,23 @@
 APPEND_SLASH = False
 
 DEFAULT_AUTO_FIELD = 'django.db.models.AutoField'
+
+LOGIN_REDIRECT_URL = '/'
+
+AUTH_PASSWORD_VALIDATORS = [
+    {
+        'NAME': 'django.contrib.auth.password_validation.UserAttributeSimilarityValidator',
+    },
+    {
+        'NAME': 'django.contrib.auth.password_validation.MinimumLengthValidator',
+        'OPTIONS': {
+            'min_length': 8,
+        }
+    },
+    {
+        'NAME': 'django.contrib.auth.password_validation.CommonPasswordValidator',
+    },
+    {
+        'NAME': 'django.contrib.auth.password_validation.NumericPasswordValidator',
+    },
+]
diff --git a/project/core/urls.py b/project/core/urls.py
--- a/project/core/urls.py
+++ b/project/core/urls.py
@@ -24,7 +24,8 @@
 
 from api import urls as api
 from accounts import urls as accounts_urls
-from accounts.views import RegisterView
+from accounts.views import (RegisterView, PasswordResetView, PasswordResetDoneView,
+                            PasswordResetConfirmView, PasswordResetCompleteView)
 from frontend_views import urls as frontend_views
 
 
@@ -43,6 +44,28 @@
         name='accounts_login',
     ),
 
+    path(
+        'accounts/password_reset',
+        PasswordResetView.as_view(),
+        name='accounts_password_reset',
+    ),
+
+    path(
+        'accounts/password_reset_done',
+        PasswordResetDoneView.as_view(),
+        name='accounts_password_reset_done',
+    ),
+    path(
+        'accounts/password_reset_confirm/<uidb64>/<token>',
+        PasswordResetConfirmView.as_view(),
+        name='accounts_password_reset_confirm',
+    ),
+
+    path(
+        'accounts/password_reset_complete',
+        PasswordResetCompleteView.as_view(),
+        name='accounts_password_reset_complete',
+    ),
     url(
         "^inbox/notifications/",
         include("notifications.urls", namespace="notifications"),


Test patch: