Skip to content
Snippets Groups Projects
Commit 964a29a9 authored by Julian's avatar Julian
Browse files

Replaced manual oauth implementation with python-requests-oauthlib

parent bf4f9331
No related branches found
No related tags found
No related merge requests found
...@@ -2,16 +2,16 @@ from functools import wraps ...@@ -2,16 +2,16 @@ from functools import wraps
import secrets, json import secrets, json
import urllib.parse import urllib.parse
from flask import Flask, session, request, redirect, abort, render_template, url_for, flash, Response from flask import Flask, session, request, redirect, abort, url_for, Response
import requests from requests_oauthlib import OAuth2Session
app = Flask(__name__) app = Flask(__name__)
app.secret_key = b'my secret' app.secret_key = b'my secret'
app.config['SESSION_COOKIE_NAME'] = 'oauth-session' app.config['SESSION_COOKIE_NAME'] = 'oauth-session'
app.config['OAUTH2_AUTH_URL'] = 'http://localhost:5001/oauth2/authorize' app.config['OAUTH2_AUTH_URL'] = 'https://localhost:5001/oauth2/authorize'
app.config['OAUTH2_TOKEN_URL'] = 'http://localhost:5001/oauth2/token' app.config['OAUTH2_TOKEN_URL'] = 'https://localhost:5001/oauth2/token'
app.config['OAUTH2_USERINFO_URL'] = 'http://localhost:5001/oauth2/userinfo' app.config['OAUTH2_USERINFO_URL'] = 'https://localhost:5001/oauth2/userinfo'
@app.route("/auth") @app.route("/auth")
def auth(): def auth():
...@@ -21,37 +21,58 @@ def auth(): ...@@ -21,37 +21,58 @@ def auth():
resp.headers['REMOTE_USER'] = session['user'] resp.headers['REMOTE_USER'] = session['user']
return resp return resp
def get_oauth(**kwargs):
return OAuth2Session(request.headers['X-CLIENT-ID'],
redirect_uri=request.headers['X-REDIRECT-URI'],
scope=request.headers['X-SCOPE'], **kwargs)
@app.route("/login") @app.route("/login")
def login(): def login():
client_id = request.headers['X-CLIENT-ID'] client = get_oauth()
scope = request.headers['X-SCOPE'] url, state = client.authorization_url(app.config['OAUTH2_AUTH_URL'])
redirect_uri = request.headers['X-REDIRECT-URI'] session['state'] = state
session['oauth-state'] = secrets.token_urlsafe() session['url'] = request.values.get('url', '/')
session['oauth-ref'] = request.values.get('url', '/') return redirect(url)
return redirect(app.config['OAUTH2_AUTH_URL']+'?'+urllib.parse.urlencode({'response_type': 'code', 'client_id': client_id, 'scope': scope, 'state': session['oauth-state'], 'redirect_uri': redirect_uri}))
@app.route("/callback") @app.route("/callback")
def callback(): def callback():
client_id = request.headers['X-CLIENT-ID'] client = get_oauth(state=session.pop('state'))
client_secret = request.headers['X-CLIENT-SECRET'] token = client.fetch_token(app.config['OAUTH2_TOKEN_URL'], client_secret=request.headers['X-CLIENT-SECRET'], authorization_response=request.url, verify=False)
redirect_uri = request.headers['X-REDIRECT-URI'] userinfo = client.get(app.config['OAUTH2_USERINFO_URL']).json()
code = request.values['code'] session['user'] = userinfo['email']
if session.pop('oauth-state') != request.values['state']: return redirect(session.pop('url'))
abort(500)
r = requests.request('POST', app.config['OAUTH2_TOKEN_URL'], data={'grant_type': 'authorization_code', 'code': code, 'redirect_uri': redirect_uri, 'client_id': client_id, 'client_secret': client_secret})
if r.status_code != 200:
abort(403)
data = r.json()
r = requests.request('GET', app.config['OAUTH2_USERINFO_URL'], headers={'Authorization': 'Bearer %s'%data['access_token']})
if r.status_code != 200:
abort(403)
session['user'] = r.json()['email']
return redirect(session.pop('oauth-ref'))
@app.route("/logout") @app.route("/logout")
def logout(): def logout():
session.clear() session.clear()
return 'Ok', 200 return 'Ok', 200
@app.route("/status")
def status():
resp = Response('''Proxy Configuration Status
For this proxy service to work properly, the OAuth client crendentials must
be injected in by the webserver as HTTP-headers:
X-CLIENT-ID: %s
X-CLIENT-SECRET: %s
X-REDIRECT-URI: %s
If you accessed this ressource with the URL
https://mydomain/mysubpath/info
then the redirect URI must be set to:
https://mydomain/mysubpath/callback
This exact redirect URI must also be registered with the OAuth server as
a valid redirect_uri for the client_id.
'''%(request.headers.get('X-CLIENT-ID', '(unset)'),
'(set)' if request.headers.get('X-CLIENT-SECRET') else '(unset)',
request.headers.get('X-REDIRECT-URI', '(unset)')))
resp.mimetype = 'text/plain; charset=utf-8'
return resp
if __name__ == '__main__': if __name__ == '__main__':
app.run(port=5002) app.run(debug=True, host='localhost', port=5002, ssl_context='adhoc')
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment