Forgot password functionality build in Python / Django Rest Framework

Related tags

Djangoforgot-password
Overview

Password Recover

Recover password functionality with e-mail sender usign Django Email Backend

How to start project.

  • Create a folder in your machine
  • Create a virtual environment
    • python3 -m venv venv
  • Start the virtual environment
    • . venv/bin/activate (Linux)
    • venv/Scripts/Activate (Windows)
  • Inside your venv folder clone the project
    • git clone https://github.com/alexlopesbr/forgot-password.git
  • In your-new-folder/venv/forgot-password
    • pip install -r requirements.txt to install the project's dependencies
    • python manage.py migrate to generate your database
    • python3 manage.py createsuperuser to create the admin
    • python3 manage.py runserver to start the server
  • Open your browser and go to http://127.0.0.1:8000/admin/
  • Login with the admin credentials
    • Now you can see you user and some info in admin panel

Using the functionality

We have two POST requests:

{{localhost}}/core/user/forgot-password/ Send an e-mail with a link to recover the password.

body of the request:

    {
        "email": "email from you user created"
    }

{{localhost}}/core/user/change-forgotten-password/ Allows you to enter the new password.

body of the request:

    {
        "email": "email from you user created",
        "forgot_password_hash": "inside the redefine you passwod button sended to your email",
        "new_password": "set a new password"
    }

You can use Postman or Insomnia to test the requests.
Note: When you start your server the localhost generaly is http://127.0.0.1:8000/.


Some instructions and informations

root

setings.py

BASE_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))

BASE_URL = 'sandbox.com'

EMAIL_BACKEND = 'django.core.mail.backends.smtp.EmailBackend'
EMAIL_HOST = 'smtp.gmail.com'
EMAIL_HOST_USER = '[email protected]'
EMAIL_HOST_PASSWORD = 'your-key'
EMAIL_PORT = 587
EMAIL_USE_TLS = True

First step, set some configures in settings.py. Don't forget to set the EMAIL_HOST_USER and the EMAIL_HOST_PASSWORD.


core

views.py

from core.models import User
from rest_framework.response import Response
from .services import send_forgot_password_email
from .exceptions import ForgotPasswordInvalidParams
from rest_framework.permissions import AllowAny
from rest_framework.decorators import action

@action(detail=False, methods=['post'], url_path='forgot-password', permission_classes=[AllowAny])
def forgot_password(self, request):
    if 'email' not in request.POST:
        raise ForgotPasswordInvalidParams
    send_forgot_password_email(request.POST['email'])
    return Response({'worked': True})

@action(detail=False, methods=['post'], url_path='change-forgotten-password', permission_classes=[AllowAny])
def change_forgotten_password(self, request):
    email = request.POST.get('email', None)
    forgot_password_hash = request.POST['forgot_password_hash']
    new_password = request.POST['new_password']
    User.change_password(email, forgot_password_hash, new_password)
    return Response({'worked': True})

Here we create a request called forgot-password to send an email with a link to change the password.
In this case, we are calling the send_forgot_password_email function. (see the function details below)

We also create a change-forgotten-password request to change the password. Here we need to send the email, the hash and the new password.

Obs. the hash is an inplicit parameter that is generated by the send_forgot_password_email function.

forgot_password_hash and new_password fields are set in core.models.py

services.py

from core.models import User
from emails.services import send_email_forgot_password
from core.exceptions import UserDoesNotExist
from django.utils import timezone
from datetime import timedelta
import re
import urllib.parse

def send_forgot_password_email(email):
    try:
        user = User.objects.get(email=email)
    except User.DoesNotExist:
        raise UserDoesNotExist
    now = timezone.now()
    user.forgot_password_hash = re.sub(r'\D', '', str(now))
    user.forgot_password_expire = now + timedelta(hours=24)
    user.save()
    link = 'https://forgot-password.com/change-password?email=%s&hash=%s' % (
        urllib.parse.quote(user.email), user.forgot_password_hash)
    send_email_forgot_password(user.email, link)

In this function we gererate a hash with a simple timezone.now() that will be atribuate to forgot_password_hash. This will be our validator.
We also set the forgot_password_expire field with the same timezone.now() plus the timedelta of 24 hours. So we give to user 24 hours to change the password.
We can bring another informations like the name of the user, but we don't use it in this exemple.

In the send_email_forgot_password function we send the email with the link to change the password.


emails

services.py

from django.core.mail import EmailMessage
from django.conf import settings


def open_and_return(my_file):
    with open(settings.BASE_DIR + '/emails/templates/' + my_file, 'r', encoding="utf-8") as file:
        data = file.read()
    return data


def send_email_forgot_password(email, link):
    template = open_and_return("forgot-password.html").format(link)

    msg = EmailMessage(
        u'Email forgot password received',
        template,
        to=[email, ],
        from_email=settings.EMAIL_HOST_USER
    )

    msg.content_subtype = 'html'
    msg.send()

The last step is sending the email with the link to user to change the password.

open_and_return function opens the template and returns the content.
This template is in emails/templates/forgot-password.html and will be used to lets our email message prettier.
In template = open_and_return("forgot-password.html").format(link) we replace the link with the link that was setted in the send_forgot_password_email function.

More information about sending emails in Django documentation

Owner
alexandre Lopes
Graduated in Biological Sciences and now back end developer, I build API's in Python / Django Rest Framework but I confess that I love front end too.
alexandre Lopes
Django-powered application about blockchain (bitcoin)

Django-powered application about blockchain (bitcoin)

Igor Izvekov 0 Jun 23, 2022
A Django Webapp performing CRUD operations on Library Database.

CRUD operations - Django Library Database A Django Webapp performing CRUD operations on Library Database. Tools & Technologies used: Django MongoDB HT

1 Dec 05, 2021
English dictionary using Django based on freecodecamp

English Dictionary Hi there, i made this english dictionary using Django based on freecodecamp.org tutorial :) Table of Contents Preview Technologies

Aline Alencar 3 May 09, 2022
A modern looking portfolio build with Django.

Django Portfolio A portfolio template using html/css/js in the frontend and Django as the backend framework. Cool features: smooth scrolling responsiv

1 Jan 19, 2022
Management commands to help backup and restore your project database and media files

Django Database Backup This Django application provides management commands to help backup and restore your project database and media files with vari

687 Jan 04, 2023
Fully reponsive Chat Application built with django, javascript, materialUi, bootstrap4, html and css.

Chat app (Full Stack Frameworks with Django Project) Fully reponsive Chat Application built with django, javascript, materialUi, bootstrap4, html and

1 Jan 19, 2022
simple project management tool for educational purposes

Taskcamp This software is used for educational and demonstrative purposes. It's a simple project management tool powered by Django Framework Install B

Ilia Dmitriev 6 Nov 08, 2022
Social Media Network Focuses On Data Security And Being Community Driven Web App

privalise Social Media Network Focuses On Data Security And Being Community Driven Web App The Main Idea: We`ve seen social media web apps that focuse

Privalise 8 Jun 25, 2021
Full-featured django project start tool.

django-start-tool Introduction django-start-tool is a full-featured replacement for django-admin startproject which provides cli for creating the same

Georgy Gnezdilov 0 Aug 30, 2022
This website serves as an online database (hosted via SQLLite) for fictional businesses in the area to store contact information (name, email, phone number, etc.) for fictional customers.

Django-Online-Business-Database-Project this project is still in progress Overview of Website This website serves as an online database (hosted via SQ

1 Oct 30, 2021
Faker is a Python package that generates fake data for you.

Faker is a Python package that generates fake data for you. Whether you need to bootstrap your database, create good-looking XML documents, fill-in yo

Daniele Faraglia 15.2k Jan 01, 2023
✋ Auto logout a user after specific time in Django

django-auto-logout Auto logout a user after specific time in Django. Works with Python 🐍 ≥ 3.7, Django 🌐 ≥ 3.0. ✔️ Installation pip install django-a

Georgy Bazhukov 21 Dec 26, 2022
Mobile Detect is a lightweight Python package for detecting mobile devices (including tablets).

Django Mobile Detector Mobile Detect is a lightweight Python package for detecting mobile devices (including tablets). It uses the User-Agent string c

Botir 6 Aug 31, 2022
Automated image processing for Django. Currently v4.0

ImageKit is a Django app for processing images. Need a thumbnail? A black-and-white version of a user-uploaded image? ImageKit will make them for you.

Matthew Dapena-Tretter 2.1k Dec 17, 2022
wagtail_tenants is a Django/Wagtail app to provide multitenancy to your wagtail project.

wagtail-tenants wagtail_tenants is a Django/Wagtail app to provide multitenancy to your wagtail project. You are able to run a main Wagtail Site and f

<bbr> 11 Nov 20, 2022
Plug and play continuous integration with django and jenkins

django-jenkins Plug and play continuous integration with Django and Jenkins Installation From PyPI: $ pip install django-jenkins Or by downloading th

Mikhail Podgurskiy 941 Oct 22, 2022
A CTF leaderboard for the submission of flags during a CTF challenge. Built using Django.

🚩 CTF Leaderboard The goal of this project is to provide a simple web page to allow the participants of an CTF to enter their found flags. Also the l

Maurice Bauer 2 Jan 17, 2022
Automatically reload your browser in development.

django-browser-reload Automatically reload your browser in development. Requirements Python 3.6 to 3.10 supported. Django 2.2 to 4.0 supported. Are yo

Adam Johnson 254 Jan 04, 2023
Актуальный сборник шаблонов для создания проектов и приложений на Django

О чем этот проект Этот репозиторий с шаблонами для быстрого создания Django проекта. В шаблоне проекта настроены следующий технологий: Django gunicorn

Denis Kustov 16 Oct 20, 2022
Django Advance DumpData

Django Advance Dumpdata Django Manage Command like dumpdata but with have more feature to Output the contents of the database from given fields of a m

EhsanSafir 7 Jul 25, 2022