Skip to content

Instantly share code, notes, and snippets.

@stephanos
Created May 14, 2012 16:28
Show Gist options
  • Select an option

  • Save stephanos/2694917 to your computer and use it in GitHub Desktop.

Select an option

Save stephanos/2694917 to your computer and use it in GitHub Desktop.
play promise
def login =
Action(parse.urlFormEncoded) {
implicit req =>
val body = req.body
// validate timestamp (not older than 5 minutes)
val tstamp = body("timestamp").head
if (new DateTime((tstamp + "000").toLong).isBefore(new DateTime().minusMinutes(5)))
Forbidden("timestamp invalid")
else {
// validate token
val resId = body("id").head
val token = body("token").head
if (token == tokenOf(resId, tstamp)) {
// find app
appSrv.findById(code2id(resId)) match {
case Some(app) =>
// update app info via Heroku (async)
val updateApp = Akka.future(updateAppInfo(app))
// find or create user
val email = body("email").head
val loginUser = Akka.future(findOrCreateUser(email, app.id))
Async {
for {
app <- updateApp
user <- loginUser
} yield {
// log user in (including nav-data cookie)
val navdata = body("nav-data").head
authenticate(Redirect("https://www.crashnote.com/", status = 200), user, partner)
.withCookies(Cookie("heroku-nav-data", navdata, secure = true))
}
}
case None =>
// oh oh: resource / app not found
Redirect("http://www.crashnote.com/404", status = 404)
}
} else {
Forbidden("token invalid")
}
}
}
//~ INTERNALS =============================================================================
private def updateAppInfo(app: AppDoc): Unit =
(app.auth.value.ref.value) map {
hid =>
fetchAppInfo(hid) onRedeem (
_ match {
case Left(resp) => {
val json = JsonParser.parse(resp.body)
val JString(name) = json \ "name"
if (app.config.value.name.value != name)
appSrv.rename(app.id, name)
}
case Right(_) => // ignore error
})
}
private def findOrCreateUser(email: String, appId: Int): UserDoc = {
userSrv.findUserByMail(email).getOrElse({
// not found? -> create user
authRegisterSrv.createUser(email.split('@').head, email,
pass = Some(""), partner = Some(partner)).map {
u =>
try
// add user to app (as admin)
teamMemberSrv.addTeamMember(appId, Some(email), Some(u.id),
TeamRole.T_OWNER, MemberState.ACCEPTED)
catch {
case e: UserException => // ... already there
}
u
}.get
})
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment