persona: in your browsers, killing your passwords
DESCRIPTION
Introduction to Persona, a new cross-browser login system for the web that's built entirely in Javascript. Powered by node.js on the backend, it pushes most of the crypto to the browser in order to create a secure and privacy-sensitive experience.TRANSCRIPT
François Marier – @fmarier
Persona:in your browsers,killing your passwords
Username:francois
Password:****************
X
Sign in
security
bcrypt
bcrypt
per-user salt
bcrypt
per-user salt
site secret
bcrypt
per-user salt
site secret
password & lockout policies
bcrypt
per-user salt
site secret
password & lockout policies
secure recovery
bcrypt
per-user salt
site secret
password & lockout policies
secure recovery
20122012
passwordpassword
guidelines
guidelines
conversionrate
# hits
signup
# hits
signup signup_complete
# hits
signup signup_complete
l o s t cust-omers
existing solutions
client certificates
centralized authorities
so...
storing passwords is hard
so...
storing passwords is hard
no suitable alternatives
decentralized
privacy-sensitivedecentralized
privacy-sensitive
simple
decentralized
privacy-sensitive
simpleopen source
decentralized
in your browser
how does it work?
getting a proof of email ownership
authenticate?
authenticate?
public key
authenticate?
public key
signed public key
you have a signed statement from yourprovider that you own your email address
logging into a 3rd party site
Valid for: 2 minutes
wikipedia.org
assertion
Valid for: 2 minutes
wikipedia.org
check audience
assertion
Valid for: 2 minutes
wikipedia.org
check audiencecheck expiry
assertion
Valid for: 2 minutes
wikipedia.org
check audiencecheck expirycheck signature
assertion
assertion
Valid for: 2 minutes
wikipedia.org
public key
assertion
Valid for: 2 minutes
wikipedia.org
assertion
session cookie
achievingthat vision
email providers
browser vendors
email providers
fallback identity provider:
login.persona.org
persona.org account
client-sessionsjwcryto
computer-cluster nodemailer
connect & express uglify
bcrypt ejs underscore
convict winston vows
“A Node.JS Holiday Season”https://hacks.mozilla.org/
proxy identity provider:
support for all email providers
browser vendors
navigator.id.*
js
support for allmodern browsers
>= 8
LIFD
LocallyIsolatedFeatureDomain
wanted: trusted coderunning in the browser
browserid.org
login.persona.org
browserid.org
login.persona.org
localStorage
localStorage.setItem("key", serializedKey);
var serializedKey = localStorage.getItem("key");
storage tied tologin.persona.org
window.postMessage()
https://login.persona.org
localStorage
jschannel
jschannel
questions?
https://login.persona.org
localStorage
live demo
using it on your site
<script src=”https://login.persona.org/include.js”></script></body></html>
navigator.id.watch({ loggedInEmail: “[email protected]”, onlogin: function (assertion) { $.post('/login', {assertion: assertion}, function (data) { // do something } ); }, onlogout: function () { window.location = '/logout'; }});
navigator.id.watch({ loggedInUser: “[email protected]”, onlogin: function (assertion) { $.post('/login', {assertion: assertion}, function (data) { // do something } ); }, onlogout: function () { window.location = '/logout'; }});
navigator.id.watch({ loggedInUser: null, onlogin: function (assertion) { $.post('/login', {assertion: assertion}, function (data) { // do something } ); }, onlogout: function () { window.location = '/logout'; }});
navigator.id.watch({ loggedInUser: null, onlogin: function (assertion) { $.post('/login', {assertion: assertion}, function (data) { // do something } ); }, onlogout: function () { window.location = '/logout'; }});
navigator.id.watch({ loggedInUser: null, onlogin: function (assertion) { $.post('/login', {assertion: assertion}, function (data) { window.location = '/'; } ); }, onlogout: function () { window.location = '/logout'; }});
navigator.id.request()
navigator.id.watch({ loggedInUser: null, onlogin: function (assertion) { $.post('/login', {assertion: assertion}, function (data) { window.location = '/'; } ); }, onlogout: function () { window.location = '/logout'; }});
navigator.id.watch({ loggedInUser: null, onlogin: function (assertion) { $.post('/login', {assertion: assertion}, function (data) { window.location = '/home'; } ); }, onlogout: function () { window.location = '/logout'; }});
var request = https.request({ host: 'verifier.login.persona.org', path: '/verify', method: 'POST', headers: { 'content-type': 'application/x-www-form-urlencoded', 'content-length': body.length }}, onVerifyResponse);
var request = https.request({ host: 'verifier.login.persona.org', path: '/verify', method: 'POST', headers: { 'content-type': 'application/x-www-form-urlencoded', 'content-length': body.length }}, onVerifyResponse);
var body = qs.stringify({ assertion: assertion, audience: 'http://123done.org'});request.write(body);
request.end();
var request = https.request({ host: 'verifier.login.persona.org', path: '/verify', method: 'POST', headers: { 'content-type': 'application/x-www-form-urlencoded', 'content-length': body.length }}, onVerifyResponse);
var body = qs.stringify({ assertion: assertion, audience: 'http://123done.org'});request.write(body);
request.end();
{ status: “okay”,
audience: “http://123done.org”,
expires: 1344849682560,
email: “[email protected]”,
issuer: “login.persona.org”}
{ status: “failed”,
reason: “assertion has expired”}
navigator.id.logout()
navigator.id.watch({ loggedInUser: null, onlogin: function (assertion) { $.post('/login', {assertion: assertion}, function (data) { window.location = '/home'; } ); }, onlogout: function () { window.location = '/logout'; }});
1. load javascript library
1. load javascript library
2. setup login & logout callbacks
1. load javascript library
2. setup login & logout callbacks
3. add login and logout buttons
1. load javascript library
2. setup login & logout callbacks
3. add login and logout buttons
4. verify proof of ownership
framework / CMS plugins
ExpressJungles
MootoolsOlives
Passport
To learn more about Persona:
https://login.persona.org/http://identity.mozilla.com/
https://developer.mozilla.org/docs/Persona/Why_Personahttps://developer.mozilla.org/docs/Persona/Quick_Setup
https://github.com/mozilla/browserid-cookbookhttps://developer.mozilla.org/docs/Persona/Libraries_and_plugins
http://123done.org/https://hacks.mozilla.org/category/a-node-js-holiday-season/
@fmarier http://fmarier.org
© 2012 François Marier <[email protected]>This work is licensed under aCreative Commons Attribution-ShareAlike 3.0 New Zealand License.
Top 500 passwords: http://xato.net/passwords/more-top-worst-passwords/
Parchment: https://secure.flickr.com/photos/27613359@N03/6750396225/
Elephant in room: https://secure.flickr.com/photos/bitboy/246805948/
Beach flower: https://secure.flickr.com/photos/vwingate/4696429215/
Cookie on tray: https://secure.flickr.com/photos/jamisonjudd/4810986199/
Photo credits: