From e73811c99b4f6f52d091cdb312f78c529e4700d5 Mon Sep 17 00:00:00 2001
From: Martin Mares <mj@ucw.cz>
Date: Mon, 17 Jan 2022 21:44:36 +0100
Subject: [PATCH] =?UTF-8?q?Zpracov=C3=A1n=C3=AD=20sken=C5=AF=20pou=C5=BE?=
 =?UTF-8?q?=C3=ADv=C3=A1=20centr=C3=A1ln=C3=AD=20seznam=20job=C5=AF?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

  •  Po nahrání skenů přesměruje na org_jobs. Nabídne návrat zpět,
     pokud uživatel chce nahrát další skeny.

  •  Stránka s nahráváním skenů upozorní, pokud už existují nějaké
     joby na zpracování skenů, a odkáže na org_jobs.

  •  Stránka s tříděním skenů odmítne fungovat, pokud job není
     dokončený, a přesměruje na org_jobs.
---
 mo/web/org_contest.py                         | 38 +++++------------
 mo/web/templates/org_contest_scans.html       | 42 +++----------------
 .../templates/org_contest_scans_process.html  | 11 -----
 mo/web/templates/org_job.html                 |  2 +-
 4 files changed, 17 insertions(+), 76 deletions(-)

diff --git a/mo/web/org_contest.py b/mo/web/org_contest.py
index 5e1f0896..1a92d233 100644
--- a/mo/web/org_contest.py
+++ b/mo/web/org_contest.py
@@ -1750,39 +1750,25 @@ def org_contest_scans(ct_id: int, site_id: Optional[int] = None):
     if proc_form.validate_on_submit() and proc_form.process_scans.data:
         files = request.files.getlist(proc_form.files.name)
         if check_scan_files(files):
-            job_id = mo.jobs.protocols.schedule_process_scans(
+            mo.jobs.protocols.schedule_process_scans(
                 contest, site, proc_form.scans_type.data, g.user,
                 tasks=[t for t in tasks if getattr(proc_form, f'task_{t.task_id}').data],
                 in_file_names=[f.stream.name for f in files],
             )
             flash('Zpracování skenů zahájeno. Vyčkejte chvíli, než budou připraveny, a poté je roztřiďte.', 'success')
-            return redirect(ctx.url_for('org_contest_scans_process', job_id=job_id))
+            return redirect(url_for('org_jobs', back=ctx.url_for('org_contest_scans')))
 
     jobs_query = sess.query(db.Job).filter_by(type=db.JobType.process_scans)
     if not g.user.is_admin:
         jobs_query = jobs_query.filter_by(user=g.user)
-    jobs: List[Tuple[db.Job, str, List[db.Task]]] = []
-    for job in jobs_query.all():
-        if 'contest_id' not in job.in_json or job.in_json['contest_id'] != ct_id:
-            continue
-        if site_id is not None and ('site_id' not in job.in_json or job.in_json['site_id'] != site_id):
-            continue
-
-        tasks = []
-        for task_id in job.in_json['task_ids']:
-            if task_id in tasks_map:
-                tasks.append(tasks_map[task_id])
-        scans_type = job.in_json['type'] if 'type' in job.in_json else 'solution'
-        scans_type_names = {'solution': 'Odevzdaná řešení', 'feedback': 'Opravená řešení'}
-
-        jobs.append((job, scans_type_names[scans_type], tasks))
+    num_scan_jobs = jobs_query.count()
 
     return render_template(
         'org_contest_scans.html',
         ctx=ctx,
         proc_form=proc_form,
         proc_task_fields=proc_task_fields,
-        jobs=jobs,
+        num_scan_jobs=num_scan_jobs,
     )
 
 
@@ -1815,11 +1801,15 @@ def org_contest_scans_process(ct_id: int, job_id: int, site_id: Optional[int] =
     # Získáme job a zkontrolujeme, že je to správný job, máme na něj práva a už doběhl
     job = sess.query(db.Job).get(job_id)
     if not job or job.type != db.JobType.process_scans:
-        flash('Dávka naskenovaných úloh nenalezena, skeny již byly pravděpodobně zpracovány nebo smazány.')
-        return redirect(ctx.url_for('org_contest_scans'))
+        flash('Dávka naskenovaných úloh nenalezena, skeny již byly pravděpodobně zpracovány nebo smazány.', 'danger')
+        return redirect(url_for('org_jobs'))
     if not g.user.is_admin and g.user.user_id != job.user_id:
         raise werkzeug.exceptions.Forbidden()
 
+    if job.state != db.JobState.done:
+        flash('Počkejte prosím, až dávka naskenovaných úloh doběhne.', 'danger')
+        return redirect(url_for('org_jobs'))
+
     if 'type' in job.in_json and job.in_json['type'] == 'feedback':
         scans_type = 'feedback'
         scans_type_name = 'oprava'
@@ -1832,14 +1822,6 @@ def org_contest_scans_process(ct_id: int, job_id: int, site_id: Optional[int] =
     if scans_type == 'feedback' and not ctx.rights.can_upload_feedback():
         raise werkzeug.exceptions.Forbidden()
 
-    if job.state != db.JobState.done:
-        return render_template(
-            'org_contest_scans_process.html',
-            ctx=ctx,
-            job=job,
-            scans_type=scans_type,
-        )
-
     pages = sess.query(db.ScanPage).filter_by(job_id=job_id).order_by('file_nr', 'page_nr').all()
     tasks = sess.query(db.Task).filter(db.Task.task_id.in_(job.in_json['task_ids'])).order_by('code').all()
     pion_query = sess.query(db.Participation).filter(
diff --git a/mo/web/templates/org_contest_scans.html b/mo/web/templates/org_contest_scans.html
index 40fbb320..b32222ca 100644
--- a/mo/web/templates/org_contest_scans.html
+++ b/mo/web/templates/org_contest_scans.html
@@ -44,42 +44,12 @@ jejich přiřazení jednotlivým soutěžícím.
 	{{ field(proc_form.process_scans) }}
 </form>
 
-<h3>Nahráno k roztřídění</h3>
-{% if jobs %}
-<p>Smazat dávky lze v <a href="{{ url_for('org_jobs') }}">přehledu všech dávek</a>.</p>
-<table class=data>
-	<thead>
-		<tr>
-			<th>Datum
-			<th>Typ skenů
-			<th>Úlohy
-			<th>Stav
-			{% if g.user.is_admin %}<th>Vlastník{% endif %}
-			<th>Akce
-		</tr>
-	</thead>
-	{% for (job, type, tasks) in jobs %}
-	<tr class="job-{{ job.state.name }}">
-		<td>{{ job.created_at|timeformat }}
-		<td>{{ type }}
-		<td>{{ tasks|map(attribute='code')|join(', ') }}
-		<td>
-		{% if job.state == JobState.done %}
-			Připraveno k roztřídění
-		{% else %}
-			{{ job.state.friendly_name() }}
-		{% endif %}
-		{% if g.user.is_admin %}<td>{{ job.user|user_link }}{% endif %}
-		<td><div class="btn-group">
-			{% if job.state == JobState.done %}
-				<a class="btn btn-xs btn-primary" href="{{ ctx.url_for('org_contest_scans_process', job_id=job.job_id) }}">Roztřídit skeny</a>
-			{% endif %}
-		</div>
-	</tr>
-	{% endfor %}
-</table>
-{% else %}
-<p>Žádné nahrané skeny k roztřídění.</p>
+{% if num_scan_jobs > 0 %}
+<h3>Rozpracované třídění</h3>
+
+<p>Už jste nahráli k roztřídění {{ num_scan_jobs|inflected('dávku', 'dávky', 'dávek') }} skenů.
+Podívejte se do <a href='{{ url_for('org_jobs', back=ctx.url_for('org_contest_scans')) }}'>seznamu dávek</a>.
+
 {% endif %}
 
 {% endblock %}
diff --git a/mo/web/templates/org_contest_scans_process.html b/mo/web/templates/org_contest_scans_process.html
index db0504c0..82596c61 100644
--- a/mo/web/templates/org_contest_scans_process.html
+++ b/mo/web/templates/org_contest_scans_process.html
@@ -16,16 +16,6 @@ Třídění skenů {{ scans_title }} pro {{ ctx.round.name|lower }} kategorie {{
 {% endblock %}
 {% block body %}
 
-{% if job.state in [JobState.preparing, JobState.ready, JobState.running] %}
-<p>Právě běží zpracování, vyčkejte prosím několik okamžiků (stránka se sama obnoví).</p>
-
-<script>
-setTimeout(function () { location.reload(1); }, 10_000);
-</script>
-{% elif job.state != JobState.done %}
-<p>Zpracování selhalo, více detailů naleznete v <a href="{{ url_for('org_job', id=job.job_id) }}">detailu dávky</a>.</p>
-{% else %}
-
 <p>Napravo můžete klikáním vybírat jednotlivé naskenované stránky a pomocí vrchních políček je přiřazovat jednotlivým úlohám a soutěžícím. Pokud
 je nějaké řešení přes více stránek, musí na sebe navazovat číslování stránek. Až bude vše správně zatříděné, můžete aktuální stav uložit
 tlačítkem <b>[Uložit]</b>. Poté můžete celou dávku odeslat ke zpracování pomocí <b>[Ukončit a zpracovat]</b>
@@ -461,5 +451,4 @@ selectRow(0);
 scrollToRow(0);
 </script>
 
-{% endif %}
 {% endblock %}
diff --git a/mo/web/templates/org_job.html b/mo/web/templates/org_job.html
index b7f9e035..6dc621b7 100644
--- a/mo/web/templates/org_job.html
+++ b/mo/web/templates/org_job.html
@@ -34,7 +34,7 @@
 
 {% if job.out_file %}
 	<a class='btn btn-primary' href='{{ url_for('org_job_output', id=job.job_id) }}'>Stáhnout výstup</a>
-{% elif job.type == 'process_scans' and 'contest_id' in job.in_json and 'site_id' in job.in_json %}
+{% elif job.type == 'process_scans' and job.state == JobState.done and 'contest_id' in job.in_json and 'site_id' in job.in_json %}
 	<a class='btn btn-primary' href='{{ url_for('org_contest_scans_process', job_id=job.job_id, ct_id=job.in_json['contest_id'], site_id=job.in_json['site_id']) }}'>Roztřídit skeny</a>
 {% endif %}
 
-- 
GitLab