added a lot of auth code

This commit is contained in:
2019-03-21 16:17:25 +01:00
parent bef3c6dc9b
commit 0469b8dbb5
13 changed files with 220 additions and 23 deletions

View File

@@ -1,6 +1,44 @@
# Copyright (c) 2019. Tobias Kurze
"""
Base module for auth aspects.
Also this module contains mainly code for login through HTML pages served by the backend.
If frontend pages are build by frontend code (JS, etc.) authentication should consider using api functions.
(For more info, see api.auth_api.py.)
"""
from flask import Blueprint
from werkzeug.routing import BuildError
auth_bp = Blueprint('auth', __name__, url_prefix='/auth', template_folder='templates')
from backend.auth.config import AUTH_PROVIDERS, DEFAULT_PROVIDER
from backend.auth.oidc import OIDCAuthentication
from backend.auth.oidc_config import OIDC_PROVIDERS
from backend.auth.oidc_config import PROVIDERS
oidc_auth = OIDCAuthentication(OIDC_PROVIDERS)
oidc_auth = OIDCAuthentication(PROVIDERS)
from .basic_auth import *
def auth_decorator(): # custom decorator
pass
@auth_bp.route('/login', methods=['GET', 'POST'])
def login():
try:
prov = AUTH_PROVIDERS[DEFAULT_PROVIDER]
except KeyError:
return "No known default provider specified!"
url = prov["url"]
try:
url = url_for(prov["url"], next=request.endpoint)
except BuildError as e:
pass
#logger.log("Can't create endpoint for '{}' (specified provider: {}).".format(e.endpoint, DEFAULT_PROVIDER))
return redirect(url)
@auth_bp.route('/login_select', methods=['GET'])
def login_select():
return render_template('login_select.html', providers=AUTH_PROVIDERS)

14
auth/basic_auth.py Normal file
View File

@@ -0,0 +1,14 @@
# Route for handling the login page logic
from flask import request, redirect, render_template, url_for
from backend.auth import auth_bp
@auth_bp.route('/base_login', methods=['GET', 'POST'])
def base_login():
error = None
if request.method == 'POST':
if request.form['username'] != 'admin' or request.form['password'] != 'admin':
error = 'Invalid Credentials. Please try again.'
else:
return redirect("/")
return render_template('login.html', error=error)

17
auth/config.py Normal file
View File

@@ -0,0 +1,17 @@
from typing import Dict, List
AUTH_PROVIDERS: Dict[str, Dict[str, str]] = {
"KIT OIDC":
{
"type": "oidc",
"url": "auth.oidc"
},
"Base Login":
{
"type": "login_form",
"url": "auth.base_login"
},
}
DEFAULT_PROVIDER: str = "Base Login"
#DEFAULT_PROVIDER: str = "KIT OIDC"

View File

@@ -1,6 +1,15 @@
# Copyright (c) 2019. Tobias Kurze
"""
OIDC login auth module
"""
import flask
from flask import jsonify
from flask_pyoidc.flask_pyoidc import OIDCAuthentication
from backend.auth.oidc_config import PROVIDER_NAME
from flask_pyoidc.user_session import UserSession
from .import auth_bp
from .oidc_config import PROVIDER_NAME, OIDC_PROVIDERS
def oidc_auth_default_provider(self):
@@ -9,3 +18,15 @@ def oidc_auth_default_provider(self):
OIDCAuthentication.oidc_auth_orig = OIDCAuthentication.oidc_auth
OIDCAuthentication.oidc_auth = oidc_auth_default_provider
oidc_auth = OIDCAuthentication(OIDC_PROVIDERS)
@auth_bp.route('/oidc', methods=['GET', 'POST'])
@oidc_auth.oidc_auth()
def oidc():
pass
user_session = UserSession(flask.session)
access_token = user_session.access_token
#login_user(user)
return jsonify(id_token=flask.session['id_token'], access_token=flask.session['access_token'])

View File

@@ -11,4 +11,4 @@ PROVIDER_NAME = 'kit_oidc'
PROVIDER_CONFIG = ProviderConfiguration(issuer=PROVIDER_URL,
client_metadata=CLIENT_METADATA)
PROVIDERS = {PROVIDER_NAME: PROVIDER_CONFIG}
OIDC_PROVIDERS = {PROVIDER_NAME: PROVIDER_CONFIG}

23
auth/templates/login.html Normal file
View File

@@ -0,0 +1,23 @@
<html>
<head>
<title>Flask Intro - login page</title>
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<link href="static/bootstrap.min.css" rel="stylesheet" media="screen">
</head>
<body>
<div class="container">
<h1>Please login</h1>
<br>
<form action="" method="post">
<input type="text" placeholder="Username" name="username" value="{{
request.form.username }}">
<input type="password" placeholder="Password" name="password" value="{{
request.form.password }}">
<input class="btn btn-default" type="submit" value="Login">
</form>
{% if error %}
<p class="error"><strong>Error:</strong> {{ error }}
{% endif %}
</div>
</body>
</html>

View File

@@ -0,0 +1,21 @@
<html>
<head>
<title>Flask Intro - login page</title>
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<link href="static/bootstrap.min.css" rel="stylesheet" media="screen">
</head>
<body>
<div class="container">
<h1>Please select login method</h1>
<br>
<ul>
{% for provider in providers %}
<li><a href="{{url_for(providers[provider].url)}}">{{ provider }} ({{ providers[provider].type }})</a></li>
{% endfor %}
</ul>
{% if error %}
<p class="error"><strong>Error:</strong> {{ error }}
{% endif %}
</div>
</body>
</html>