Reputation: 266988
I want to use the built in playframework cache API but not sure how to cache this web service request when it has futures.
def getUser(username: String): Future[Option[User]] = {
ws.url("...").get.map { response =>
response.json.validate[User] match {
case JsSuccess(user, _) => Some(user)
case JsError(errors) => {
// log errors
None
}
}
}
}
The cache key will just be the username for now.
How would I use the cache API here?
I wanted to use the getOrElse pattern:
val user: User = cache.getOrElse[User]("item.key") {
User.findById(connectedUser)
}
But the Future and Option is confusing me on how to go about using it.
Upvotes: 0
Views: 675
Reputation: 8413
I would do it like this:
def fromWebservice(username: String): Future[Option[User]] =
ws.url("..").get.map(validate) // validate does the json validate thing
def getUser(username: String): Future[Option[User]] =
cache.getAs[User](username) match {
case Some(x) =>
Future.successful(Some(x))
case None =>
fromWebservice(username).map(_.map { user =>
cache.set(username, user)
x
})
}
As an aside, the Play cache API does not have an API that returns Future
s, but they're working on it: https://github.com/playframework/playframework/issues/5912
Upvotes: 1