Implementation of OpenID Connect's OP (aka identity provider, login server)
MIT License
Under development, please do not use yet.
This django application provides an implementation of OpenID Connect identity server (OpenID provider). You can use it, for example, for building centralized authorization server to which clients connect via the OpenID or OAuth2.0 protocol.
This library is compatible with python-social-auth package that can be used as an OpenID client to access this server.
The following features of the OpenID Connect specification are implemented:
This library prefers Python 3.6 as it depends on secrets
module.
If running in python 3.5, a backported version of secrets
module
from python 3.6.1 is used.
TODO: add pip
cd /tmp
mkdir test
cd test
virtualenv --python=python3.6 venv-server
source venv-server/bin/activate
pip install django-openid-op
django-admin startproject authorization_server
(cd authorization_server; django-admin startapp web)
authorization_server/authorization_server/settings.py
file and append the following lines to the end of the file:
INSTALLED_APPS += [
'openid_connect_op',
'web'
]
APPEND_SLASH = False
Run python authorization_server/manage.py migrate
Create keys that will be used to sign tokens:
python authorization_server/manage.py create_jwt_keys
python authorization_server/manage.py runserver
google-chrome http://localhost:8000/
authorization_server/authorization_server/urls.py
# added ", include" here
from django.conf.urls import url, include
from django.contrib import admin
urlpatterns = [
url(r'^admin/', admin.site.urls),
# added these lines
url('^', include('openid_connect_op.urls')),
url('^', include('django.contrib.auth.urls')),
]
This will create the following urls:
/.well-known/openid-configuration
- URL that returns configuration of this OpenID provider according to RFC 5785/openid/jwks
- returns the public key that clients may use to validate received information/openid/authorize
, /openid/token
- OpenID authorization and token endpoints/openid/userinfo
- OpenID user information endpoint/openid/register
- Dynamic client registration serviceStart the server and try to point Postman or browser to http://localhost:8000/.well-known/openid-configuration
and http://localhost:8000/openid/jwks
to check that the step above works.
mkdir -p authorization_server/web/templates/registration
nano authorization_server/web/templates/registration/login.html
and put there standard logging template from django docs:
<html>
<body>
{% if form.errors %}
<p>Your username and password didn't match. Please try again.</p>
{% endif %}
{% if next %}
{% if user.is_authenticated %}
<p>Your account doesn't have access to this page. To proceed,
please login with an account that has access.</p>
{% else %}
<p>Please login to see this page.</p>
{% endif %}
{% endif %}
<form method="post" action="{% url 'login' %}">
{% csrf_token %}
<table>
<tr>
<td>{{ form.username.label_tag }}</td>
<td>{{ form.username }}</td>
</tr>
<tr>
<td>{{ form.password.label_tag }}</td>
<td>{{ form.password }}</td>
</tr>
</table>
<input type="submit" value="login" />
<input type="hidden" name="next" value="{{ next }}" />
</form>
</body>
</html>
python authorization_server/manage.py createsuperuser
Username (leave blank to use 'simeki'): admin
Email address: [email protected]
Password:
Password (again):
Superuser created successfully.
Try to log in at http://localhost:8000/login
.
Congratulations, you have successfully set up an OpenID Connect authentication server.
virtualenv --python=python3.6 venv-client
source venv-client/bin/activate
pip install django social-auth-app-django
django-admin startproject web_server
(cd web_server; django-admin startapp web)
python authorization_server/manage.py register_openid_client \
--redirect-url 'http://localhost:9000/complete/openid/' \
--server-name 'My test server' \
--auth-type post
> Registration successfull, please configure the server with:
> Client ID (KEY in settings.py): aaaaaaa
> Client Secret (SECRET in settings.py): bbbbbb
web_server/web_server/settings.py
file and append the following lines to the end of the file:
AUTHENTICATION_BACKENDS = (
'web.backends.OpenIdConnect',
'django.contrib.auth.backends.ModelBackend',
)
INSTALLED_APPS += [
'social_django',
'web'
]
# url where authorization_server lives
OIDC_ENDPOINT = 'http://127.0.0.1:8000'
KEY = 'aaaaaaa'
SECRET = 'bbbbbb'
LOGIN_URL = '/login/openid/'
web_server/web/backends.py
:from django.conf import settings
from social_core.backends.open_id_connect import OpenIdConnectAuth
class OpenIdConnect(OpenIdConnectAuth):
OIDC_ENDPOINT = settings.OIDC_ENDPOINT
name = 'openid'
mkdir -p web_server/web/templates
nano web_server/web/templates/base.html
<html>
<body>
{% block content %} {% endblock %}
</body>
</html>
nano web_server/web/templates/index.html
{% extends "base.html" %}
{% block content %}
<h1>Hello!</h1>
{% if not user.is_anonymous %}
<p>
Your name is {{ user.first_name }} {{ user.last_name }}, username {{ user.username }}, email {{ user.email }}
</p>
{% else %}
<p>
Would you like to <a href="/login/openid/?next=/">log in</a>?
</p>
{% endif %}
{% endblock %}
nano web_server/web/views.py
from django.views.generic import TemplateView
class IndexView(TemplateView):
template_name = 'index.html'
nano web_server/web_server/urls.py
from django.conf.urls import url
from django.contrib import admin
import web.views
urlpatterns = [
url(r'^admin/', admin.site.urls),
url(r'^/$', web.views.IndexView.as_view()),
]
http://localhost:9000/login/openid/
python web_server/manage.py runserver localhost:9000
See docs and API at http://django-openid-op.readthedocs.io/en/latest/