mirror of https://github.com/mitsuhiko/flask.git
David Lord
8 years ago
7 changed files with 0 additions and 199 deletions
@ -1,3 +0,0 @@
|
||||
A simple example for integrating [Persona](https://login.persona.org/) into a |
||||
Flask application. In addition to Flask, it requires the |
||||
[requests](www.python-requests.org/) library. |
@ -1,55 +0,0 @@
|
||||
from flask import Flask, render_template, session, request, abort, g |
||||
|
||||
import requests |
||||
|
||||
|
||||
app = Flask(__name__) |
||||
app.config.update( |
||||
DEBUG=True, |
||||
SECRET_KEY='my development key', |
||||
PERSONA_JS='https://login.persona.org/include.js', |
||||
PERSONA_VERIFIER='https://verifier.login.persona.org/verify', |
||||
) |
||||
app.config.from_envvar('PERSONA_SETTINGS', silent=True) |
||||
|
||||
|
||||
@app.before_request |
||||
def get_current_user(): |
||||
g.user = None |
||||
email = session.get('email') |
||||
if email is not None: |
||||
g.user = email |
||||
|
||||
|
||||
@app.route('/') |
||||
def index(): |
||||
"""Just a generic index page to show.""" |
||||
return render_template('index.html') |
||||
|
||||
|
||||
@app.route('/_auth/login', methods=['GET', 'POST']) |
||||
def login_handler(): |
||||
"""This is used by the persona.js file to kick off the |
||||
verification securely from the server side. If all is okay |
||||
the email address is remembered on the server. |
||||
""" |
||||
resp = requests.post(app.config['PERSONA_VERIFIER'], data={ |
||||
'assertion': request.form['assertion'], |
||||
'audience': request.host_url, |
||||
}, verify=True) |
||||
if resp.ok: |
||||
verification_data = resp.json() |
||||
if verification_data['status'] == 'okay': |
||||
session['email'] = verification_data['email'] |
||||
return 'OK' |
||||
|
||||
abort(400) |
||||
|
||||
|
||||
@app.route('/_auth/logout', methods=['POST']) |
||||
def logout_handler(): |
||||
"""This is what persona.js will call to sign the user |
||||
out again. |
||||
""" |
||||
session.clear() |
||||
return 'OK' |
@ -1,52 +0,0 @@
|
||||
$(function() { |
||||
/* convert the links into clickable buttons that go to the |
||||
persona service */ |
||||
$('a.signin').on('click', function() { |
||||
navigator.id.request({ |
||||
siteName: 'Flask Persona Example' |
||||
}); |
||||
return false; |
||||
}); |
||||
|
||||
$('a.signout').on('click', function() { |
||||
navigator.id.logout(); |
||||
return false; |
||||
}); |
||||
|
||||
/* watch persona state changes */ |
||||
navigator.id.watch({ |
||||
loggedInUser: $CURRENT_USER, |
||||
onlogin: function(assertion) { |
||||
/* because the login needs to verify the provided assertion |
||||
with the persona service which requires an HTTP request, |
||||
this could take a bit. To not confuse the user we show |
||||
a progress box */ |
||||
var box = $('<div class=signinprogress></div>') |
||||
.hide() |
||||
.text('Please wait ...') |
||||
.appendTo('body') |
||||
.fadeIn('fast'); |
||||
$.ajax({ |
||||
type: 'POST', |
||||
url: $URL_ROOT + '_auth/login', |
||||
data: {assertion: assertion}, |
||||
success: function(res, status, xhr) { window.location.reload(); }, |
||||
error: function(xhr, status, err) { |
||||
box.remove(); |
||||
navigator.id.logout(); |
||||
alert('Login failure: ' + err); |
||||
} |
||||
}); |
||||
}, |
||||
onlogout: function() { |
||||
$.ajax({ |
||||
type: 'POST', |
||||
url: $URL_ROOT + '_auth/logout', |
||||
success: function(res, status, xhr) { window.location.reload(); }, |
||||
error: function(xhr, status, err) { |
||||
alert('Logout failure: ' + err); |
||||
} |
||||
}); |
||||
} |
||||
}); |
||||
}); |
Before Width: | Height: | Size: 30 KiB |
@ -1,39 +0,0 @@
|
||||
html { |
||||
background: #eee; |
||||
} |
||||
|
||||
body { |
||||
font-family: 'Verdana', sans-serif; |
||||
font-size: 15px; |
||||
margin: 30px auto; |
||||
width: 720px; |
||||
background: white; |
||||
padding: 30px; |
||||
} |
||||
|
||||
h1 { |
||||
margin: 0; |
||||
} |
||||
|
||||
h1, h2, a { |
||||
color: #d00; |
||||
} |
||||
|
||||
div.authbar { |
||||
background: #eee; |
||||
padding: 0 15px; |
||||
margin: 10px -15px; |
||||
line-height: 25px; |
||||
height: 25px; |
||||
vertical-align: middle; |
||||
} |
||||
|
||||
div.signinprogress { |
||||
position: fixed; |
||||
top: 0; |
||||
left: 0; |
||||
right: 0; |
||||
bottom: 0; |
||||
background: rgba(255, 255, 255, 0.8) url(spinner.png) center center no-repeat; |
||||
font-size: 0; |
||||
} |
@ -1,23 +0,0 @@
|
||||
{% extends "layout.html" %} |
||||
{% block title %}Welcome{% endblock %} |
||||
{% block body %} |
||||
<h2>Welcome</h2> |
||||
<p> |
||||
This is a small example application that shows how to integrate |
||||
Mozilla's persona signin service into a Flask application. |
||||
<p> |
||||
The advantage of persona over your own login system is that the |
||||
password is managed outside of your application and you get |
||||
a verified mail address as primary identifier for your user. |
||||
<p> |
||||
In this example nothing is actually stored on the server, it |
||||
just takes over the email address from the persona verifier |
||||
and stores it in a session. |
||||
{% if g.user %} |
||||
<p> |
||||
You are now logged in as <strong>{{ g.user }}</strong> |
||||
{% else %} |
||||
<p> |
||||
To sign in click the sign in button above. |
||||
{% endif %} |
||||
{% endblock %} |
@ -1,27 +0,0 @@
|
||||
<!doctype html> |
||||
<title>{% block title %}{% endblock %} | Flask Persona Example</title> |
||||
<meta http-equiv="X-UA-Compatible" content="IE=Edge"> |
||||
<script src="{{ config.PERSONA_JS }}"></script> |
||||
<script src="//ajax.googleapis.com/ajax/libs/jquery/1.10.1/jquery.min.js"></script> |
||||
<script> |
||||
/* the url root is useful for doing HTTP requests */ |
||||
var $URL_ROOT = {{ request.url_root|tojson }}; |
||||
|
||||
/* we store the current user here so that the persona |
||||
javascript support knows about the current user */ |
||||
var $CURRENT_USER = {{ g.user|tojson }}; |
||||
</script> |
||||
<script src="{{ url_for('static', filename='persona.js') }}"></script> |
||||
<link rel="stylesheet" href="{{ url_for('static', filename='style.css') }}"> |
||||
<header> |
||||
<h1>Mozilla Persona Example</h1> |
||||
<div class="authbar"> |
||||
{% if g.user %} |
||||
Signed in as <em>{{ g.user }}</em> |
||||
(<a href="#" class="signout">Sign out</a>) |
||||
{% else %} |
||||
Not signed in. <a href="#" class="signin">Sign in</a> |
||||
{% endif %} |
||||
</div> |
||||
</header> |
||||
{% block body %}{% endblock %} |
Loading…
Reference in new issue