diff --git a/app/controllers/HomeController.scala b/app/controllers/HomeController.scala index 5315e7c..2a1abe8 100644 --- a/app/controllers/HomeController.scala +++ b/app/controllers/HomeController.scala @@ -4,7 +4,7 @@ import javax.inject.* import play.api.* import play.api.mvc.* import authentication.{AuthenticatedAction, AuthenticatedRequest} -import caching.{Etagable, checkFresh} +import caching.{Etagable, CheckFresh} import models.User import play.api.libs.json.Json @@ -20,7 +20,7 @@ import java.util.Base64 @Singleton class HomeController @Inject()(val controllerComponents: ControllerComponents, authenticatedAction: AuthenticatedAction) - extends BaseController with Logging { + extends BaseController with Logging with CheckFresh { /** * Create an Action to render an HTML page. @@ -35,7 +35,7 @@ class HomeController @Inject()(val controllerComponents: ControllerComponents, def userData = authenticatedAction { implicit request: AuthenticatedRequest[AnyContent] => val user = request.user - request.checkFresh(user) { + checkFresh(user) { // TODO: put the max-age somewhere into config Ok(Json.toJson(user)).withHeaders("Etag" -> user.etag, "Cache-Control" -> "private, max-age=15, must-revalidate") } diff --git a/app/controllers/caching/caching.scala b/app/controllers/caching/caching.scala index be1518c..2bac898 100644 --- a/app/controllers/caching/caching.scala +++ b/app/controllers/caching/caching.scala @@ -9,18 +9,18 @@ trait Etagable[A]: extension (a: A) def etag: String -extension [A, R[X] <: Request[X], E: Etagable](request: R[A]) { - def checkFreshAsync(entity: E)(onStale: => Future[Result])(using ec: ExecutionContext): Future[Result] = { - compareEtag(entity).fold(onStale)( +trait CheckFresh { + protected def checkFreshAsync[A, E: Etagable](entity: E)(onStale: => Future[Result])(using request: Request[A], ec: ExecutionContext): Future[Result] = { + compareEtag(request, entity).fold(onStale)( etag => Future.successful(NotModified.withHeaders("ETag" -> etag)) ) } - def checkFresh(entity: E)(onStale: => Result): Result = { - compareEtag(entity).fold(onStale)( + protected def checkFresh[A, E: Etagable](entity: E)(onStale: => Result)(using request: Request[A]): Result = { + compareEtag(request, entity).fold(onStale)( etag => NotModified.withHeaders("ETag" -> etag) ) } - private def compareEtag(entity: E) = request.headers.get("If-None-Match").filter(e => e == entity.etag) + private def compareEtag[A, E: Etagable](request: Request[A], entity: E) = request.headers.get("If-None-Match").filter(e => e == entity.etag) } \ No newline at end of file