Code cleaning in handlers; implement result handler
This commit is contained in:
@@ -6,6 +6,10 @@ import javax.servlet.http.HttpServletRequest
|
||||
|
||||
interface PairgothApiHandler: ApiHandler {
|
||||
|
||||
fun getTournament(request: HttpServletRequest): Tournament? = getSelector(request)?.toIntOrNull()?.let { Store.getTournament(it) }
|
||||
fun getTournament(request: HttpServletRequest): Tournament {
|
||||
val tournamentId = getSelector(request)?.toIntOrNull() ?: ApiHandler.badRequest("invalid tournament id")
|
||||
return Store.getTournament(tournamentId) ?: ApiHandler.badRequest("unknown tournament id")
|
||||
}
|
||||
|
||||
|
||||
}
|
@@ -9,18 +9,15 @@ import org.jeudego.pairgoth.model.toJson
|
||||
import org.jeudego.pairgoth.store.Store
|
||||
import javax.servlet.http.HttpServletRequest
|
||||
|
||||
object PairingHandler: ApiHandler {
|
||||
|
||||
private fun getTournament(request: HttpServletRequest): Tournament {
|
||||
val tournamentId = getSelector(request)?.toIntOrNull() ?: badRequest("invalid tournament id")
|
||||
return Store.getTournament(tournamentId) ?: badRequest("unknown tournament id")
|
||||
}
|
||||
object PairingHandler: PairgothApiHandler {
|
||||
|
||||
override fun get(request: HttpServletRequest): Json {
|
||||
val tournament = getTournament(request)
|
||||
val round = getSubSelector(request)?.toIntOrNull() ?: badRequest("invalid round number")
|
||||
val games = tournament.games.getOrNull(round)?.values ?: emptyList()
|
||||
return games.map { it.toJson() }.toJsonArray()
|
||||
val playing = (tournament.games.getOrNull(round)?.values ?: emptyList()).flatMap {
|
||||
listOf(it.black, it.white)
|
||||
}.toSet()
|
||||
return tournament.pairables.values.filter { !it.skip.contains(round) && !playing.contains(it.id) }.toJsonArray()
|
||||
}
|
||||
|
||||
override fun post(request: HttpServletRequest): Json {
|
||||
@@ -29,25 +26,21 @@ object PairingHandler: ApiHandler {
|
||||
val payload = getArrayPayload(request)
|
||||
val allPlayers = payload.size == 1 && payload[0] == "all"
|
||||
if (!allPlayers && tournament.pairing.type == Pairing.PairingType.SWISS) badRequest("Swiss pairing requires all pairable players")
|
||||
val playing = (tournament.games.getOrNull(round)?.values ?: emptyList()).flatMap {
|
||||
listOf(it.black, it.white)
|
||||
}.toSet()
|
||||
val pairables =
|
||||
if (allPlayers)
|
||||
tournament.pairables.values.filter { !it.skip.contains(round) }
|
||||
tournament.pairables.values.filter { !it.skip.contains(round) && !playing.contains(it.id) }
|
||||
else payload.map {
|
||||
// CB - because of the '["all"]' map, conversion to int lands here... Better API syntax for 'all players'?
|
||||
if (it is Number) it.toInt() else badRequest("invalid pairable id: #$it")
|
||||
}.map { id ->
|
||||
tournament.pairables[id]?.also {
|
||||
if (it.skip.contains(round)) badRequest("pairable #$id does not play round $round")
|
||||
if (playing.contains(it.id)) badRequest("pairable #$id already plays round $round")
|
||||
} ?: badRequest("invalid pairable id: #$id")
|
||||
}
|
||||
// check players are not already implied in games in this round
|
||||
val pairablesIDs = pairables.map { it.id }.toSet()
|
||||
tournament.games.getOrNull(round)?.let { games ->
|
||||
games.values.mapNotNull { game ->
|
||||
if (pairablesIDs.contains(game.black)) game.black else if (pairablesIDs.contains(game.white)) game.white else null
|
||||
}.let {
|
||||
if (it.isNotEmpty()) badRequest("The following players are already playing this round: ${it.joinToString { id -> "#${id}" }}")
|
||||
}
|
||||
}
|
||||
val games = tournament.pair(round, pairables)
|
||||
return games.map { it.toJson() }.toJsonArray()
|
||||
}
|
||||
|
@@ -1,4 +1,47 @@
|
||||
package org.jeudego.pairgoth.api
|
||||
|
||||
class ResultsHandler: ApiHandler {
|
||||
import com.republicate.kson.Json
|
||||
import com.republicate.kson.toJsonArray
|
||||
import org.jeudego.pairgoth.api.ApiHandler.Companion.badRequest
|
||||
import org.jeudego.pairgoth.model.Game
|
||||
import org.jeudego.pairgoth.model.Tournament
|
||||
import org.jeudego.pairgoth.model.toJson
|
||||
import org.jeudego.pairgoth.store.Store
|
||||
import javax.servlet.http.HttpServletRequest
|
||||
|
||||
object ResultsHandler: PairgothApiHandler {
|
||||
|
||||
override fun get(request: HttpServletRequest): Json {
|
||||
val tournament = getTournament(request)
|
||||
val round = getSubSelector(request)?.toIntOrNull() ?: badRequest("invalid round number")
|
||||
val games = tournament.games.getOrNull(round)?.values ?: emptyList()
|
||||
return games.map { it.toJson() }.toJsonArray()
|
||||
}
|
||||
|
||||
override fun post(request: HttpServletRequest): Json {
|
||||
val tournament = getTournament(request)
|
||||
val round = getSubSelector(request)?.toIntOrNull() ?: badRequest("invalid round number")
|
||||
val payload = getObjectPayload(request)
|
||||
val game = tournament.games[round][payload.getInt("id")] ?: badRequest("invalid game id")
|
||||
game.result = Game.Result.valueOf(payload.getString("result") ?: badRequest("missing result"))
|
||||
return Json.Object("success" to true)
|
||||
}
|
||||
|
||||
override fun put(request: HttpServletRequest): Json {
|
||||
val tournament = getTournament(request)
|
||||
val round = getSubSelector(request)?.toIntOrNull() ?: badRequest("invalid round number")
|
||||
val payload = getObjectPayload(request)
|
||||
val game = tournament.games[round][payload.getInt("id")] ?: badRequest("invalid game id")
|
||||
game.result = Game.Result.valueOf(payload.getString("result") ?: badRequest("missing result"))
|
||||
return Json.Object("success" to true)
|
||||
}
|
||||
|
||||
override fun delete(request: HttpServletRequest): Json {
|
||||
val tournament = getTournament(request)
|
||||
val round = getSubSelector(request)?.toIntOrNull() ?: badRequest("invalid round number")
|
||||
val payload = getObjectPayload(request)
|
||||
val game = tournament.games[round][payload.getInt("id")] ?: badRequest("invalid game id")
|
||||
tournament.games[round].remove(payload.getInt("id") ?: badRequest("invalid game id")) ?: badRequest("invalid game id")
|
||||
return Json.Object("success" to true)
|
||||
}
|
||||
}
|
@@ -1,4 +1,4 @@
|
||||
package org.jeudego.pairgoth.api
|
||||
|
||||
class StandingsHandler: ApiHandler {
|
||||
object StandingsHandler: PairgothApiHandler {
|
||||
}
|
@@ -4,6 +4,7 @@ import com.republicate.kson.Json
|
||||
import org.jeudego.pairgoth.api.ApiHandler
|
||||
import org.jeudego.pairgoth.api.PairingHandler
|
||||
import org.jeudego.pairgoth.api.PlayerHandler
|
||||
import org.jeudego.pairgoth.api.ResultsHandler
|
||||
import org.jeudego.pairgoth.api.TournamentHandler
|
||||
import org.jeudego.pairgoth.util.Colorizer.blue
|
||||
import org.jeudego.pairgoth.util.Colorizer.green
|
||||
@@ -84,6 +85,7 @@ class ApiServlet : HttpServlet() {
|
||||
null -> TournamentHandler
|
||||
"part" -> PlayerHandler
|
||||
"pair" -> PairingHandler
|
||||
"res" -> ResultsHandler
|
||||
else -> ApiHandler.badRequest("unknown sub-entity: $subEntity")
|
||||
}
|
||||
"player" -> PlayerHandler
|
||||
|
@@ -13,8 +13,14 @@ class ImportTests: TestBase() {
|
||||
val resource = file.readText(StandardCharsets.UTF_8)
|
||||
val resp = TestAPI.post("/api/tour", resource)
|
||||
val id = resp.asObject().getInt("id")
|
||||
val tournament = TestAPI.get("/api/tour/$id")
|
||||
val tournament = TestAPI.get("/api/tour/$id").asObject()
|
||||
logger.info(tournament.toString())
|
||||
val players = TestAPI.get("/api/tour/$id/part").asArray()
|
||||
logger.info(players.toString())
|
||||
for (round in 1..tournament.getInt("rounds")!!) {
|
||||
val games = TestAPI.get("/api/tour/$id/res/1").asArray()
|
||||
logger.info("games for round $round: {}", games.toString())
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
Reference in New Issue
Block a user