1 module userauth.services.persona;
2 
3 import userauth.userauth;
4 
5 import vibe.core.log;
6 import vibe.http.client;
7 import vibe.stream.memory;
8 import vibe.templ.diet;
9 
10 
11 class PersonaAuthService : UserAuthService {
12 	string generateAuthMixin(HTTPServerRequest req, string path_prefix)
13 	{
14 		logDebug("logged in: %s %s", req.session.id !is null, req.cookies);
15 		auto dst = new MemoryOutputStream;
16 		string authUserEmail;
17 		if (req.session) authUserEmail = req.session.get!string("email");
18 		parseDietFileCompat!("userauth-persona-auth-mixin.dt",
19 			string, "path_prefix",
20 			string, "authUserEmail")(dst, path_prefix, authUserEmail);
21 		return cast(string)dst.data();
22 	}
23 
24 	void registerRoutes(URLRouter router, string path_prefix)
25 	{
26 		// NOTE: need to be at root directory because the cookie has to be available
27 		// on all pages
28 		router.post("/persona-login", &login);
29 		router.post("/persona-logout", &logout);
30 	}
31 
32 	private void login(HTTPServerRequest req, HTTPServerResponse res)
33 	{
34 		enforceHTTP("assertion" in req.form, HTTPStatus.BadRequest, "'assertion' field is missing.");
35 
36 		auto cres = requestHTTP("https://verifier.login.persona.org/verify", (scope creq){
37 				creq.method = HTTPMethod.POST;
38 				creq.writeJsonBody(["assertion": req.form["assertion"], "audience": "http://localhost:8080/"]);
39 			});
40 
41 		enforceHTTP(cres.statusCode == HTTPStatus.OK, HTTPStatus.Unauthorized, "Auth assertion could not be validated.");
42 
43 		auto jres = cres.readJson();
44 		enforceHTTP(jres.status.get!string == "okay", HTTPStatus.Unauthorized, "Auth assertion is invalid.");
45 
46 		Session session = req.session;
47 		if( !session ) session = res.startSession();
48 		session.set("email", jres.email.get!string);
49 		res.writeJsonBody(jres);
50 	}
51 
52 	private void logout(HTTPServerRequest req, HTTPServerResponse res)
53 	{
54 		if( req.session ) res.terminateSession();
55 		res.writeJsonBody(["message": "Successfully logged out."]);
56 	}
57 }