How to do it...

To connect Auth0 to your Django project, follow these steps:

  1. Add the social authentication app to INSTALLED_APPS in the settings file, like so:
# myproject/settings/_base.py
INSTALLED_APPS = [
# …
"social_django",
]
  1. Now, add the Auth0 settings required by the social_django app, which will be similar to the following:
# myproject/settings/_base.py
SOCIAL_AUTH_AUTH0_DOMAIN = get_secret("AUTH0_DOMAIN")
SOCIAL_AUTH_AUTH0_KEY = get_secret("AUTH0_KEY")
SOCIAL_AUTH_AUTH0_SECRET = get_secret("AUTH0_SECRET")
SOCIAL_AUTH_AUTH0_SCOPE = ["openid", "profile", "email"]
SOCIAL_AUTH_TRAILING_SLASH = False

Make sure that you define AUTH0_DOMAIN, AUTH0_KEY, and AUTH0_SECRET in your secrets or environment variables. The values for those variables can be found in the settings of your Auth0 app that you created in Step 1 of this recipe's Getting ready section.

  1. We need to create a backend for the Auth0 connection, as shown in the following example:
# myproject/apps/external_auth/backends.py
from urllib import request
from jose import jwt
from social_core.backends.oauth import BaseOAuth2

class Auth0(BaseOAuth2):
"""Auth0 OAuth authentication backend"""

name = "auth0"
SCOPE_SEPARATOR = " "
ACCESS_TOKEN_METHOD = "POST"
REDIRECT_STATE = False
EXTRA_DATA = [("picture", "picture"), ("email", "email")]

def authorization_url(self):
return "https://" + self.setting("DOMAIN") + "/authorize"

def access_token_url(self):
return "https://" + self.setting("DOMAIN") + "/oauth/token"

def get_user_id(self, details, response):
"""Return current user id."""
return details["user_id"]

def get_user_details(self, response):
# Obtain JWT and the keys to validate the signature
id_token = response.get("id_token")
jwks = request.urlopen(
"https://" + self.setting("DOMAIN") + "/.well-
known/jwks.json"
)
issuer = "https://" + self.setting("DOMAIN") + "/"
audience = self.setting("KEY") # CLIENT_ID
payload = jwt.decode(
id_token,
jwks.read(),
algorithms=["RS256"],
audience=audience,
issuer=issuer,
)
first_name, last_name = (payload.get("name") or
" ").split(" ", 1)
return {
"username": payload.get("nickname") or "",
"first_name": first_name,
"last_name": last_name,
"picture": payload.get("picture") or "",
"user_id": payload.get("sub") or "",
"email": payload.get("email") or "",
}
  1. Add the new backend to your AUTHENTICATION_BACKENDS setting, as shown in the following code:
# myproject/settings/_base.py
AUTHENTICATION_BACKENDS = {
"myproject.apps.external_auth.backends.Auth0",
"django.contrib.auth.backends.ModelBackend",
}
  1. We want the social authentication user to be accessible from any template. Therefore, we'll create a context processor for it:
# myproject/apps/external_auth/context_processors.py
def auth0(request):
data = {}
if request.user.is_authenticated:
auth0_user = request.user.social_auth.filter(
provider="auth0",
).first()
data = {
"auth0_user": auth0_user,
}
return data
  1. Next, we need to register it in the settings:
# myproject/settings/_base.py
TEMPLATES = [
{
"BACKEND":
"django.template.backends.django.DjangoTemplates",
"DIRS": [os.path.join(BASE_DIR, "myproject", "templates")],
"APP_DIRS": True,
"OPTIONS": {
"context_processors": [
"django.template.context_processors.debug",
"django.template.context_processors.request",
"django.contrib.auth.context_processors.auth",
"django.contrib.messages.context_processors
.messages"
,
"django.template.context_processors.media",
"django.template.context_processors.static",
"myproject.apps.core.context_processors
.website_url"
,
"myproject.apps.external_auth
.context_processors.auth0"
,

]
},
}
]
  1. Now, let's create views for the index page, dashboard, and logout:
# myproject/apps/external_auth/views.py
from
urllib.parse import urlencode

from django.shortcuts import render, redirect
from django.contrib.auth.decorators import login_required
from django.contrib.auth import logout as log_out
from django.conf import settings


def index(request):
user = request.user
if user.is_authenticated:
return redirect(dashboard)
else:
return render(request, "index.html")


@login_required
def dashboard(request):
return render(request, "dashboard.html")


def logout(request):
log_out(request)
return_to = urlencode({"returnTo":
request.build_absolute_uri("/")})
logout_url = "https://%s/v2/logout?client_id=%s&%s" % (
settings.SOCIAL_AUTH_AUTH0_DOMAIN,
settings.SOCIAL_AUTH_AUTH0_KEY,
return_to,
)
return redirect(logout_url)
  1. Create the index template, as follows:
{# index.html #}
{% extends "base.html" %}
{% load i18n utility_tags %}

{% block content %}
<div class="login-box auth0-box before">
<h3>{% trans "Please log in for the best user experience" %}</h3>
<a class="btn btn-primary btn-lg" href="{% url "social:begin"
backend="auth0" %}">{% trans "Log in" %}</a>
</div>
{% endblock %}
  1. Create a dashboard template accordingly:
{# dashboard.html #}
{% extends "base.html" %}
{% load i18n %}

{% block content %}
<div class="logged-in-box auth0-box logged-in">
<img alt="{% trans 'Avatar' %}" src="{{
auth0_user.extra_data.picture }}"
width="50" height="50" />
<h2>{% blocktrans with name=request.user
.first_name %}Welcome, {{ name }}
{% endblocktrans %}!</h2>

<a class="btn btn-primary btn-logout" href="{% url
"auth0_logout" %}">{% trans "Log out" %}</a>
</div>
{% endblock %}
  1. Update the URL rules:
# myproject/urls.py
from django.conf.urls.i18n import i18n_patterns
from django.urls import path, include

from myproject.apps.external_auth import views as external_auth_views

urlpatterns = i18n_patterns(
path("", external_auth_views.index, name="index"),
path("dashboard/", external_auth_views.dashboard,
name="dashboard"),
path("logout/", external_auth_views.logout,
name="auth0_logout"),
path("", include("social_django.urls")),
# …
)
  1. Finally, add the login URL settings:
LOGIN_URL = "/login/auth0"
LOGIN_REDIRECT_URL = "dashboard"
..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset
18.191.13.255