166 lines
5.3 KiB
Scala
166 lines
5.3 KiB
Scala
package controllers
|
|
|
|
import play.api.mvc._
|
|
import play.api.libs.json.Json
|
|
|
|
import lila.api.Context
|
|
import lila.app._
|
|
import lila.swiss.{ Swiss => SwissModel }
|
|
import lila.swiss.Swiss.{ Id => SwissId }
|
|
import views._
|
|
|
|
final class Swiss(
|
|
env: Env,
|
|
tourC: Tournament
|
|
) extends LilaController(env) {
|
|
|
|
private def swissNotFound(implicit ctx: Context) = NotFound(html.swiss.bits.notFound())
|
|
|
|
def show(id: String) = Open { implicit ctx =>
|
|
env.swiss.api.byId(SwissId(id)) flatMap { swissOption =>
|
|
val page = getInt("page").filter(0.<)
|
|
negotiate(
|
|
html = swissOption.fold(swissNotFound.fuccess) { swiss =>
|
|
for {
|
|
version <- env.swiss.version(swiss.id)
|
|
isInTeam <- isCtxInTheTeam(swiss.teamId)
|
|
json <- env.swiss.json(
|
|
swiss = swiss,
|
|
me = ctx.me,
|
|
reqPage = page,
|
|
socketVersion = version.some,
|
|
playerInfo = none,
|
|
isInTeam = isInTeam
|
|
)
|
|
canChat <- canHaveChat(swiss)
|
|
chat <- canChat ?? env.chat.api.userChat.cached
|
|
.findMine(lila.chat.Chat.Id(swiss.id.value), ctx.me)
|
|
.dmap(some)
|
|
_ <- chat ?? { c =>
|
|
env.user.lightUserApi.preloadMany(c.chat.userIds)
|
|
}
|
|
} yield Ok(html.swiss.show(swiss, json, chat))
|
|
},
|
|
api = _ =>
|
|
swissOption.fold(notFoundJson("No such swiss tournament")) { swiss =>
|
|
for {
|
|
socketVersion <- getBool("socketVersion").??(env.swiss version swiss.id dmap some)
|
|
isInTeam <- isCtxInTheTeam(swiss.teamId)
|
|
playerInfo <- get("playerInfo").?? { env.swiss.api.playerInfo(swiss, _) }
|
|
json <- env.swiss.json(
|
|
swiss = swiss,
|
|
me = ctx.me,
|
|
reqPage = page,
|
|
socketVersion = socketVersion,
|
|
playerInfo = playerInfo,
|
|
isInTeam = isInTeam
|
|
)
|
|
} yield Ok(json)
|
|
}
|
|
)
|
|
}
|
|
}
|
|
|
|
private def isCtxInTheTeam(teamId: lila.team.Team.ID)(implicit ctx: Context) =
|
|
ctx.userId.??(u => env.team.cached.teamIds(u).dmap(_ contains teamId))
|
|
|
|
def form(teamId: String) = Auth { implicit ctx => me =>
|
|
Ok(html.swiss.form.create(env.swiss.forms.create, teamId)).fuccess
|
|
}
|
|
|
|
def create(teamId: String) = AuthBody { implicit ctx => me =>
|
|
env.team.teamRepo.isLeader(teamId, me.id) flatMap {
|
|
case false => notFound
|
|
case _ =>
|
|
env.swiss.forms.create
|
|
.bindFromRequest()(ctx.body)
|
|
.fold(
|
|
err => BadRequest(html.swiss.form.create(err, teamId)).fuccess,
|
|
data =>
|
|
tourC.rateLimitCreation(me, false, ctx.req) {
|
|
env.swiss.api.create(data, me, teamId) map { swiss =>
|
|
Redirect(routes.Swiss.show(swiss.id.value))
|
|
}
|
|
}
|
|
)
|
|
}
|
|
}
|
|
|
|
def join(id: String) = AuthBody { implicit ctx => me =>
|
|
NoLameOrBot {
|
|
env.team.cached.teamIds(me.id) flatMap { teamIds =>
|
|
env.swiss.api.join(SwissId(id), me, teamIds.contains) flatMap { result =>
|
|
negotiate(
|
|
html = Redirect(routes.Swiss.show(id)).fuccess,
|
|
api = _ =>
|
|
fuccess {
|
|
if (result) jsonOkResult
|
|
else BadRequest(Json.obj("joined" -> false))
|
|
}
|
|
)
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
def edit(id: String) = Auth { implicit ctx => me =>
|
|
WithEditableSwiss(id, me) { swiss =>
|
|
Ok(html.swiss.form.edit(swiss, env.swiss.forms.edit(swiss))).fuccess
|
|
}
|
|
}
|
|
|
|
def update(id: String) = AuthBody { implicit ctx => me =>
|
|
WithEditableSwiss(id, me) { swiss =>
|
|
implicit val req = ctx.body
|
|
env.swiss.forms
|
|
.edit(swiss)
|
|
.bindFromRequest
|
|
.fold(
|
|
err => BadRequest(html.swiss.form.edit(swiss, err)).fuccess,
|
|
data => env.swiss.api.update(swiss, data) inject Redirect(routes.Swiss.show(id)).flashSuccess
|
|
)
|
|
}
|
|
|
|
}
|
|
def terminate(id: String) = Auth { implicit ctx => me =>
|
|
WithEditableSwiss(id, me) { swiss =>
|
|
env.swiss.api kill swiss inject Redirect(routes.Team.show(swiss.teamId))
|
|
}
|
|
}
|
|
|
|
def standing(id: String, page: Int) = Open { implicit ctx =>
|
|
WithSwiss(id) { swiss =>
|
|
JsonOk {
|
|
env.swiss.standingApi(swiss, page)
|
|
}
|
|
}
|
|
}
|
|
|
|
def player(id: String, userId: String) = Action.async {
|
|
WithSwiss(id) { swiss =>
|
|
env.swiss.api.playerInfo(swiss, userId) flatMap {
|
|
_.fold(notFoundJson()) { player =>
|
|
JsonOk(fuccess(lila.swiss.SwissJson.playerJsonExt(swiss, player)))
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
private def WithSwiss(id: String)(f: SwissModel => Fu[Result]): Fu[Result] =
|
|
env.swiss.api.byId(SwissId(id)) flatMap { _ ?? f }
|
|
|
|
private def WithEditableSwiss(id: String, me: lila.user.User)(
|
|
f: SwissModel => Fu[Result]
|
|
)(implicit ctx: Context): Fu[Result] =
|
|
WithSwiss(id) { swiss =>
|
|
if (swiss.createdBy == me.id && !swiss.isFinished) f(swiss)
|
|
else if (isGranted(_.ManageTournament)) f(swiss)
|
|
else Redirect(routes.Swiss.show(swiss.id.value)).fuccess
|
|
}
|
|
|
|
private def canHaveChat(swiss: SwissModel)(implicit ctx: Context): Fu[Boolean] =
|
|
(swiss.hasChat && ctx.noKid) ?? ctx.userId.?? {
|
|
env.team.api.belongsTo(swiss.teamId, _)
|
|
}
|
|
}
|