1

我正在使用 Play Framework (Scala) 和 SecureSocial 对用户进行身份验证。

我希望我的网站允许未登录的用户在他们的会话期间浏览和填充某些用户数据(例如电子邮件地址)。

我有一个自定义 UserService 实现,它将登录用户持久保存到数据库(以及我自己的User实现securesocial.core.Identity Trait的模型对象)

我有一个UnregisteredUser子类,我想在用户未登录时保留在会话中。

请问这方面的最佳做法是什么?

4

1 回答 1

1

我想您的特定目标是在您感兴趣的控制器的每个操作中有效地收集与未注册用户相关的全部数据。问题:我们想检索一个UnregisteredUser直接在会话中收集所有这些数据的构建。

首先,UnregisteredUser使用基本 Play 2 的 api Sessions在会话中随时保存数据:

Ok("Welcome Guest User!").withSession(
  "email" -> "unregisteredUserEmail"  //  assuming a randomly chosen Id since not logged yet
  // many other data here
)

然后,您可以简单地编写一个trait扩展您的实际SecureSocial特征,其中包含:

case class GuestRequest[A](optUnregisteredUser: Option[UnregisteredUser], request: Request[A]) extends WrappedRequest(request)

def GuestAction(f: GuestRequest[AnyContent] => Result): Action[AnyContent] = {
    implicit request => {
      val optUnregisteredUserEmail = session.get("currentUnregisteredUser")
      val unregisteredUser = UnregisteredUser(optUnregisteredUserEmail) 
      f(GuestRequest(optUnregisteredUser, request))
}

在您关心的每个控制器中,您只需执行以下操作:

def addToCard = GuestAction {
    implicit request =>
      val currentUnregisteredUser: UnregisteredUser = optUnregisteredUser.getOrElse(.....)
      //remaining instructions here
  }

- - - - - - - 更新 - - - - - - -

实际上,您可以UserAwareAction从现有SecureSocial特征中使用两种用户样式。因此,您必须UserAwareAction在扩展 SecureSocial 的特征中覆盖,以便组合功能:

    override def UserAwareAction[A](p: BodyParser[A])(f: RequestWithUser[A] => Result) = Action(p) {
        implicit request => {
          val user = for (
            authenticator <- authenticatorFromRequest;
            user <- userServices.findByUserName(authenticator.userName)
          ) yield {
            touch(authenticator)
            user
          }
          if(user.isEmpty){  //meaning user is not logged
            f(RequestWithUser(tryToBuildUnRegisteredUser, request))  //setting your unregisteredUser
          }
          else{
            f(RequestWithUser(user, request))
          }
        }
      }

 private def tryToBuildUnregisteredUser = {
    val optUnregisteredUserEmail = session.get("currentUnregisteredUser")
    optUnregisteredUserEmail match {
      case Some(e) => Some(UnregisteredUser(e)) 
      case _ => None
    }
 }

当然,你可以自由地重构它:)

于 2013-05-13T11:23:45.607 回答