From 89fd6f0189e5b12f59333b8a93a2f62e4d459acc Mon Sep 17 00:00:00 2001 From: Thibault Duplessis Date: Tue, 2 Mar 2021 18:46:23 +0100 Subject: [PATCH] download selected games in mod view --- app/controllers/GameMod.scala | 16 +++++++++------- ui/common/src/xhr.ts | 14 +++++++++----- ui/site/src/modGames.ts | 15 ++++++++------- 3 files changed, 26 insertions(+), 19 deletions(-) diff --git a/app/controllers/GameMod.scala b/app/controllers/GameMod.scala index 128fab60db..7ff1f69308 100644 --- a/app/controllers/GameMod.scala +++ b/app/controllers/GameMod.scala @@ -46,9 +46,9 @@ final class GameMod(env: Env) extends LilaController(env) { .fold( err => BadRequest(err.toString).fuccess, { - case (gameIds, "analyse") => multipleAnalysis(me, gameIds) - case (gameIds, "pgn") => downloadPgn(gameIds).fuccess - case _ => notFound + case (gameIds, Some("pgn")) => downloadPgn(user, gameIds).fuccess + case (gameIds, Some("analyse") | None) => multipleAnalysis(me, gameIds) + case _ => notFound } ) } @@ -69,7 +69,7 @@ final class GameMod(env: Env) extends LilaController(env) { }.sequenceFu >> env.fishnet.awaiter(games.map(_.id), 2 minutes) } inject NoContent - private def downloadPgn(gameIds: Seq[lila.game.Game.ID]) = + private def downloadPgn(user: lila.user.User, gameIds: Seq[lila.game.Game.ID]) = Ok.chunked { env.api.gameApiV2.exportByIds( GameApiV2.ByIdsConfig( @@ -80,8 +80,10 @@ final class GameMod(env: Env) extends LilaController(env) { playerFile = none ) ) - }.withHeaders(noProxyBufferHeader) - .as(pgnContentType) + }.withHeaders( + noProxyBufferHeader, + CONTENT_DISPOSITION -> s"attachment; filename=lichess_mod_${user.username}_${gameIds.size}_games.pgn" + ).as(pgnContentType) private def guessSwisses(user: lila.user.User): Fu[Seq[lila.swiss.Swiss]] = fuccess(Nil) } @@ -127,7 +129,7 @@ object GameMod { Form( tuple( "game" -> list(nonEmptyText), - "action" -> lila.common.Form.stringIn(Set("download", "analyse")) + "action" -> optional(lila.common.Form.stringIn(Set("pgn", "analyse"))) ) ) } diff --git a/ui/common/src/xhr.ts b/ui/common/src/xhr.ts index 2192a35fdb..1ac3d78e8c 100644 --- a/ui/common/src/xhr.ts +++ b/ui/common/src/xhr.ts @@ -69,8 +69,12 @@ export const url = (path: string, params: { [k: string]: string | number | boole }; /* submit a form with XHR */ -export const formToXhr = (el: HTMLFormElement): Promise => - text(el.action, { - method: el.method, - body: new FormData(el), - }); +export const formToXhr = (el: HTMLFormElement): Promise => { + const action = el.getAttribute('action'); + return action + ? text(action, { + method: el.method, + body: new FormData(el), + }) + : Promise.reject(`Form has no action: ${el}`); +}; diff --git a/ui/site/src/modGames.ts b/ui/site/src/modGames.ts index fca31ee993..3d8370d908 100644 --- a/ui/site/src/modGames.ts +++ b/ui/site/src/modGames.ts @@ -43,13 +43,14 @@ const setupActionForm = () => { $(form).on('click', 'button', e => { const button = e.target as HTMLButtonElement; const action = button.getAttribute('value'); - debugger; - const nbToAnalyse = form.querySelectorAll('input:checked').length; - if (nbToAnalyse < 1) return; - if (nbToAnalyse >= 20 && !confirm(`Analyse ${nbToAnalyse} games?`)) return; - $(form).find('button').text('Sent').prop('disabled', true); - debouncedSubmit(); - return false; + const nbSelected = form.querySelectorAll('input:checked').length; + if (nbSelected < 1) return false; + if (action == 'analyse') { + if (nbSelected >= 20 && !confirm(`Analyse ${nbSelected} games?`)) return; + $(form).find('button[value="analyse"]').text('Sent').prop('disabled', true); + debouncedSubmit(); + return false; + } }); };