Registering a Django User via React


Although everything is explained from scratch, a lot of fundamental parts are not explain thoroughly, meaning they might be hard to understand for someone who has not at least had a little exposure to both Django and React.

Creating a New Django Project

We will begin by setting up the Python development environment using Virtual Environment and then activate it right away. Execute the following commands in a new directory:

python3 -m venv venv
source ./venv/bin/activate
Notice the “(venv)” after executing the last command. This indicates that our environment is active.

Next, we need to install Django and start a new project, which I called “auth” in this case:

pip install Django==2.2.7
django-admin startproject auth .

After executing these commands, you should see that Django has created a new project folder for us. To run our server, we first need to apply the database migrations which will create the default database schema and then run the server:

python manage.py migrate
python manage.py runserver

Your server should now be running at http://127.0.0.1:8000/!

Adding Rest Framework Dependencies

The following command will install everything we need to get user authentication working using the django rest framework:

pip install django-allauth==0.40.0

The Django REST framework gives us access to a multitude of features, such as the generation of json payloads, which are needed to create an effective rest api. The django-all-auth package allows us to handle authentication (login, registration, etc.) via the REST api, which is essential for most web apps. Next, we will need to configure our django project settings to use these new endpoints. Let’s edit our installed apps in the django settings.py script:

INSTALLED_APPS = [
    'django.contrib.admin',
    'django.contrib.auth',
    'django.contrib.contenttypes',
    'django.contrib.sessions',
    'django.contrib.messages',
    'django.contrib.staticfiles',
    #new apps
    'django.contrib.sites',
    'rest_framework',
    'rest_framework.authtoken',
    'rest_auth',
    'rest_auth.registration',
    'allauth',
    'allauth.account',
    'allauth.socialaccount',
]
# new settings variables
EMAIL_BACKEND = 'django.core.mail.backends.console.EmailBackend'
SITE_ID = 1

For our REST API to work, we need to set a site id. We also define the email backend to display any emails that we send to our console. We also want to add the generated api endpoints to our urls.py:

from django.contrib import admin
from django.urls import path, include #new import
urlpatterns = [
    path('admin/', admin.site.urls),
    #new urls
    path('api/', include('rest_framework.urls')),
    path('api/rest-auth/', include('rest_auth.urls')),
    path('api/rest-auth/registration/', include('rest_auth.registration.urls')),
]

Now, do migrations and run our server:

python manage.py migrate
python manage.py runserver

We now have the API endpoints from the rest framework available. We can even access some of the urls for it! Enter the following url in your browser: http://127.0.0.1:8000/api/rest-auth/registration/. You should see something like this:

We can already register users with this auto-generated GUI. However, our next step will be to use an independent react frontend.

Enabling Cross Origin Requests

Right now, our Django backend does not accept requests coming from different origins (for valid security reasons). Because our React app will be hosted on a different url (or origin), we want to change our app’s Cross-Origin Resource Sharing (CORS) settings. As always, there is a Django package for this that we want to add:

pip install django-cors-headers

We want to make the following changes to our settings.py to give our React app permissions to interact with the Django api:

INSTALLED_APPS = [
    ...
    'corsheaders', # new app

    'users.apps.UsersConfig',
    'publications.apps.PublicationsConfig',
]

MIDDLEWARE = [
    'corsheaders.middleware.CorsMiddleware', # new middleware
     ...
]
# new whitelist
CORS_ORIGIN_WHITELIST = [
     'http://localhost:3000',
]
# new rest permissions
REST_FRAMEWORK = {
    'DEFAULT_PERMISSION_CLASSES': [
        'rest_framework.permissions.AllowAny'
    ]
}

Creating the React App

I’m assuming you are familiar with create-react-app. If you are not, read this article. Let’s begin by creating the app and also installing axios, a small framework that replaces the default fetch API for making requests:

npx create-react-app django-auth-app
yarn add axios

Now that we have our start app, we want to create the form. Looking back at the Django registration endpoint, we can identify that we need to send a POST request with the following attributes: username, email (which is optional), password1 and password2. Let’s create a basic form in our App.js file:

import React, { useState } from "react";
import axios from "axios";

function App() {
  const [formValues, setFormValues] = useState({
    username: "",
    email: "",
    password1: "",
    password2: ""
  });
  const handleInputChange = event => {
    const target = event.target;
    const value = target.type === "checkbox" ? target.checked : target.value;
    const name = target.name;
    setFormValues({
      ...formValues,
      [name]: value
    });
  };
  const submitForm = event => {
    event.preventDefault();
    axios.post("http://localhost:8000/api/rest-auth/registration/", formValues);
  };
  return (
    <div className="App">
      <form onSubmit={submitForm}>
        <input
          type="text"
          placeholder="john doe"
          value={formValues.username}
          name="username"
          onChange={handleInputChange}
        />
        <input
          type="password"
          value={formValues.password1}
          name="password1"
          placeholder="password1"
          onChange={handleInputChange}
        />
        <input
          type="password"
          value={formValues.password2}
          name="password2"
          placeholder="password2"
          onChange={handleInputChange}
        />
        <input
          type="email"
          value={formValues.email}
          name="email"
          placeholder="email"
          onChange={handleInputChange}
        />
        <input type="submit" value="submit" />
      </form>
    </div>
  );
}

export default App;

Registering a new user is simple now – we need to fill in the form with a proper email, two identical passwords and a new username. I noticed that the password seems to require at least one uppercase letter and a number, otherwise I get a “bad request” error.

Submitting my form is successful and I get the following output in my console that is running the Django server:

Hello from example.com!

You’re receiving this e-mail because user testuser has given yours as an e-mail address…

You should also see a link in the email. Clicking on the link opens an error page – we have yet to configure the view that the user sees when clicking on their token. However, that is out of the scope of this tutorial! Important is only that our user is successfully registered, regardless of whether their email is confirmed or not. If you want me to extend the tutorial to feature logins or configuration of this confirmation email view, please leave a comment!

Newsletter
Please enter a valid email!
Please agree to the terms!