lila/app/controllers/User.scala

174 lines
6.3 KiB
Scala
Raw Normal View History

2013-03-20 08:23:41 -06:00
package controllers
2013-09-11 04:38:16 -06:00
import play.api.mvc._, Results._
import lila.api.Context
2013-03-20 08:23:41 -06:00
import lila.app._
import lila.app.mashup.GameFilterMenu
2013-06-28 05:52:52 -06:00
import lila.common.LilaCookie
import lila.db.api.$find
2013-12-24 06:58:54 -07:00
import lila.game.GameRepo
2013-03-20 08:23:41 -06:00
import lila.security.Permission
2013-05-08 09:41:12 -06:00
import lila.user.tube.userTube
2014-02-17 02:12:19 -07:00
import lila.user.{ User => UserModel, UserRepo }
import lila.rating.PerfType
2013-06-28 05:52:52 -06:00
import views._
2013-03-20 08:23:41 -06:00
object User extends LilaController {
2013-05-08 09:41:12 -06:00
private def env = Env.user
private def gamePaginator = Env.game.paginator
2013-03-20 08:23:41 -06:00
private def forms = lila.user.DataForm
2014-04-17 06:10:08 -06:00
private def relationApi = Env.relation.api
2013-05-08 09:41:12 -06:00
2014-02-17 02:12:19 -07:00
def show(username: String) = Open { implicit ctx =>
filter(username, none, 1)
}
2014-02-17 02:12:19 -07:00
def showMini(username: String) = Open { implicit ctx =>
OptionFuResult(UserRepo named username) { user =>
2014-04-17 03:34:55 -06:00
GameRepo nowPlaying user.id zip
2014-04-17 06:10:08 -06:00
(ctx.userId ?? { relationApi.blocks(user.id, _) }) zip
2014-05-03 01:39:20 -06:00
(ctx.isAuth ?? { Env.pref.api.followable(user.id) }) zip
2014-04-22 17:28:19 -06:00
(ctx.userId ?? { relationApi.relation(_, user.id) }) map {
case (((game, blocked), followable), relation) =>
Ok(html.user.mini(user, game, blocked, followable, relation))
.withHeaders(CACHE_CONTROL -> "max-age=5")
2014-04-17 03:34:55 -06:00
}
2013-12-24 06:58:54 -07:00
}
2013-05-20 22:12:10 -06:00
}
2013-05-08 09:41:12 -06:00
2014-02-17 02:12:19 -07:00
def showFilter(username: String, filterName: String, page: Int) = Open { implicit ctx =>
filter(username, filterName.some, page)
2013-05-20 22:12:10 -06:00
}
2014-02-17 02:12:19 -07:00
def online = Open { implicit req =>
2014-04-23 12:04:52 -06:00
val max = 1000
2014-08-06 02:56:21 -06:00
UserRepo.byIdsSortRating(env.onlineUserIdMemo.keys, max) map { html.user.online(_, max) }
}
2014-04-22 17:22:57 -06:00
private def filter(
username: String,
filterOption: Option[String],
page: Int,
status: Results.Status = Results.Ok)(implicit ctx: Context) =
2013-05-08 09:41:12 -06:00
Reasonable(page) {
2014-02-17 02:12:19 -07:00
OptionFuResult(UserRepo named username) { u =>
(u.enabled || isGranted(_.UserSpy)).fold({
if (lila.common.HTTPRequest.isSynchronousHttp(ctx.req))
userShow(u, filterOption, page)
else
userGames(u, filterOption, page)
} map { status(_) },
UserRepo isArtificial u.id map { artificial =>
NotFound(html.user.disabled(u, artificial))
})
}
2013-05-04 17:12:53 -06:00
}
2013-03-20 07:24:47 -06:00
private def userShow(u: UserModel, filterOption: Option[String], page: Int)(implicit ctx: Context) = for {
info Env.current.userInfo(u, ctx)
filterName = filterOption | "all"
filters = GameFilterMenu(info, ctx.me, filterName)
2014-02-17 02:12:19 -07:00
pag (filters.query.fold(Env.bookmark.api.gamePaginatorByUser(u, page)) { query =>
gamePaginator.recentlyCreated(query, filters.cachedNb)(page)
})
2014-04-17 06:10:08 -06:00
relation <- ctx.userId ?? { relationApi.relation(_, u.id) }
2014-04-22 17:22:57 -06:00
notes <- ctx.me ?? { me =>
relationApi friends me.id flatMap { env.noteApi.get(u, me, _) }
}
2014-05-03 01:39:20 -06:00
followable <- ctx.isAuth ?? { Env.pref.api followable u.id }
2014-05-26 06:49:43 -06:00
blocked <- ctx.userId ?? { relationApi.blocks(u.id, _) }
} yield html.user.show(u, info, pag, filters, relation, notes, followable, blocked)
2013-05-08 09:41:12 -06:00
private def userGames(u: UserModel, filterOption: Option[String], page: Int)(implicit ctx: Context) = {
val filterName = filterOption | "all"
val current = GameFilterMenu.currentOf(GameFilterMenu.all, filterName)
val query = GameFilterMenu.queryOf(current, u, ctx.me)
val cachedNb = GameFilterMenu.cachedNbOf(u, current)
query.fold(Env.bookmark.api.gamePaginatorByUser(u, page)) { query =>
gamePaginator.recentlyCreated(query, cachedNb)(page)
} map { html.user.games(u, _, filterName) }
}
2014-08-02 11:33:46 -06:00
def list = Open { implicit ctx =>
val nb = 10
for {
bullet env.cached topPerf PerfType.Bullet.key
blitz env.cached topPerf PerfType.Blitz.key
classical env.cached topPerf PerfType.Classical.key
chess960 env.cached topPerf PerfType.Chess960.key
kingOfTheHill env.cached topPerf PerfType.KingOfTheHill.key
threeCheck env.cached topPerf PerfType.ThreeCheck.key
2014-08-02 11:33:46 -06:00
nbAllTime env.cached topNbGame nb map2 { (user: UserModel) =>
user -> user.count.game
}
nbWeek Env.game.cached activePlayerUidsWeek nb flatMap { pairs =>
UserRepo.byOrderedIds(pairs.map(_._1)) map (_ zip pairs.map(_._2))
}
tourneyWinners Env.tournament.winners scheduled nb
online env.cached topOnline 30
} yield html.user.list(
tourneyWinners = tourneyWinners,
online = online,
bullet = bullet,
blitz = blitz,
classical = classical,
chess960 = chess960,
kingOfTheHill = kingOfTheHill,
threeCheck = threeCheck,
nbWeek = nbWeek,
nbAllTime = nbAllTime)
2013-05-08 09:41:12 -06:00
}
2013-03-20 08:23:41 -06:00
2014-02-17 02:12:19 -07:00
def mod(username: String) = Secure(_.UserSpy) { implicit ctx =>
me => OptionFuOk(UserRepo named username) { user =>
2014-01-27 06:38:23 -07:00
Env.evaluation.evaluator find user zip
(Env.security userSpy user.id) map {
2014-02-17 02:12:19 -07:00
case (eval, spy) => html.user.mod(user, spy, eval)
}
}
}
2014-02-17 02:12:19 -07:00
def evaluate(username: String) = Secure(_.UserEvaluate) { implicit ctx =>
me => OptionFuResult(UserRepo named username) { user =>
Env.evaluation.evaluator.generate(user.id, true) inject Redirect(routes.User.show(username).url + "?mod")
2014-04-22 17:22:57 -06:00
}
}
def writeNote(username: String) = AuthBody { implicit ctx =>
me => OptionFuResult(UserRepo named username) { user =>
implicit val req = ctx.body
env.forms.note.bindFromRequest.fold(
err => filter(username, none, 1, Results.BadRequest),
text => env.noteApi.write(user, text, me) inject Redirect(routes.User.show(username).url + "?note")
)
}
}
2014-02-17 02:12:19 -07:00
def opponents(username: String) = Open { implicit ctx =>
OptionFuOk(UserRepo named username) { user =>
2014-05-03 01:39:20 -06:00
lila.game.BestOpponents(user.id, 50) flatMap { ops =>
2014-05-21 12:56:50 -06:00
ctx.isAuth.fold(
Env.pref.api.followables(ops map (_._1.id)),
fuccess(List.fill(50)(true))
) flatMap { followables =>
(ops zip followables).map {
case ((u, nb), followable) => ctx.userId ?? { myId =>
relationApi.relation(myId, u.id)
} map { lila.relation.Related(u, nb, followable, _) }
}.sequenceFu map { relateds =>
html.user.opponents(user, relateds)
}
2014-05-03 01:39:20 -06:00
}
}
}
}
2014-02-17 02:12:19 -07:00
def autocomplete = Open { implicit ctx =>
get("term", ctx.req).filter(_.nonEmpty).fold(BadRequest("No search term provided").fuccess: Fu[Result]) { term =>
2013-05-06 15:52:48 -06:00
JsonOk(UserRepo usernamesLike term)
}
}
2013-03-20 08:23:41 -06:00
}