Skip to content
Snippets Groups Projects
Commit 35aee941 authored by Jiří Setnička's avatar Jiří Setnička
Browse files

Účastnická část webu - ukazujeme kola a úlohy ve všech stádiích

* připravuje se: Je vidět jen informace o tom, že kolo bude (případně i s datem
  zveřejnění zadání, pokud je zadané.
* běží: Pokud ještě nenastal čas zveřejnění zadání, tak je podobné jako
  'připravuje se' jen s jinou zprávou. Jinak zobrazuje vše a umožňuje
  odevzdávat (a pokud už je po termínu, zobrazuje varování).
* opravuje se: Jsou vidět všechny odevzdané úlohy, ale nelze odevzdávat
  další.
* ukončeno: Jako opravuje se, ale v tabulce jsou vidět i body a
  opravená řešení. Obsahuje FIXME: výsledkovka.
parent 0d9bd1fb
No related branches found
No related tags found
No related merge requests found
This commit is part of merge request !12. Comments created here will be created in the context of that merge request.
......@@ -6,28 +6,52 @@
<h2>{{ round.name }} {{ round.year }}. ročníku kategorie {{ round.category }}: {{ contest.place.name }}</h2>
{% if state == db.RoundState.preparing %}
<p>
Soutěžní kolo se <b>připravuje</b>{% if round.ct_tasks_start and round.ct_tasks_start > g.now %},
začne <b>{{ round.ct_tasks_start|timeformat }} ({{ human_timedelta(round.ct_tasks_start, g.now) }})</b>{% endif %}.
Až začne, budete mít na této stránce {% if round.has_tasks() %}k dispozici text zadání,{% endif %}
přehled úloh a budete zde moci odevzdat svá řešení k jednotlivým úlohám.
Do té doby zde nenajdete nic jiného.
</p>
{% elif state == db.RoundState.running and not round.can_submit() %}
<p>
Soutěžní kolo <b>je připraveno</b>, ale zatím nelze odevzdávat. Odevzdávání začne
<b>{{ round.ct_tasks_start|timeformat }} ({{ human_timedelta(round.ct_tasks_start, g.now) }})</b>.
  • Přijde mi, že kombinace "timestamp a k němu timedelta" je natolik častá, že by si zasloužila samostatnou funkci.

  • Jiří Setnička @setnicka

    changed this line in version 3 of the diff

    ·

    changed this line in version 3 of the diff

    Toggle commit list
  • Author Maintainer

    Nakonec jsem z toho udělal timedelta a time_and_timedelta a registroval jsem je do jinja templates jako filtery, nakonec je jejich použití takhle příjemnější.

  • Please register or sign in to reply
Až začne, budete mít na této stránce {% if round.has_tasks() %}k dispozici text zadání,{% endif %}
přehled úloh a budete zde moci odevzdat svá řešení k jednotlivým úlohám.
Do té doby zde nenajdete nic jiného.
</p>
{% else %}
{% if state == db.RoundState.running %}
<p>Soutěž běží.
<p>
{% if round.ct_submit_end == None %}
Můžete odevzdávat svá řešení.
Soutěžní kolo běží, <b>můžete odevzdávat svá řešení.</b>
{% elif round.ct_submit_end > g.now %}
Soutěžní kolo běží, <b>svá řešení odevzdávejte do {{ round.ct_submit_end|timeformat }} ({{ human_timedelta(round.ct_submit_end, g.now) }})</b>.
V případě technických problémů můžete odevzdat i později, ale není zaručeno, že řešení budou hodnocena.
{% else %}
Svá řešení odevzdávejte do {{ round.ct_submit_end|timeformat }}.
V případě technických problémů můžete odevzdat i později,
ale není zaručeno, že řešení budou hodnocena.
Řádný termín soutěžního kola <b>již skončil</b> (v {{ round.ct_submit_end|timeformat }}, {{ human_timedelta(round.ct_submit_end, g.now) }}),
ale stále můžete odevzdat svá řešení, která se vám nepovedla odevzdat kvůli
technickým problémům. Není však zaručeno, že řešení budou hodnocena.
{% endif %}
</p>
{% if round.can_submit() %}
<p>Řešení odevzdávejte ve formátu PDF jako soubor o velikosti maximálně
{{ max_submit_size // 1048576 }} MB.
{% endif %}
{% elif state == db.RoundState.grading %}
<p>Odevzdávání bylo ukončeno. Vyčkejte prosím, až úlohy opravíme.
{% elif state == db.RoundState.closed %}
<p>FIXME
<p>Soutěžní kolo bylo ukončeno, níže si můžete prohlédnout svá ohodnocená a okomentovaná řešení.
<p>FIXME výsledkovka
{% else %}
<p>Soutěž se nachází v neznámém stavu. To by se nemělo stát :)
{% endif %}
{% if statement_visible %}
{% if round.task_statement_available() %}
<p>Můžete si stáhnout <a href='{{ url_for('user_task_statement', id=contest.contest_id) }}'>zadání úloh</a>.
{% endif %}
......@@ -41,9 +65,8 @@
{% if round.state == db.RoundState.closed %}
<th>Opraveno
<th>Body
{% else %}
<th>Akce
{% endif %}
<th>Akce
<tbody>
{% for task, sol in task_sols %}
<tr>
......@@ -60,13 +83,13 @@
<td>
{% endif %}
<td>{{ sol.points if sol.points != None else '–' }}
{% else %}
<td>
{% if round.state == db.RoundState.running %}
<a class='btn btn-xs btn-primary' href='{{ url_for('user_contest_task', contest_id=contest.contest_id, task_id=task.task_id) }}'>Odevzdat</a>
{% endif %}
{% endif %}
<td>
<a class='btn btn-xs btn-primary' href='{{ url_for('user_contest_task', contest_id=contest.contest_id, task_id=task.task_id) }}'>
{% if round.can_submit() %}Odevzdat{% else %}Detail úlohy{% endif %}
</a>
{% endfor %}
</table>
{% endif %}
{% endblock %}
......@@ -7,14 +7,18 @@
<p><a href='{{ url_for('user_contest', id=contest.contest_id) }}'>Zpět na seznam úloh</a>
{% if round.can_submit() %}
<h3>Odevzdat řešení</h3>
{% if round.ct_submit_end != None and g.now > round.ct_submit_end %}
<p class="alert alert-danger">Pozor, odevzdáváte po termínu. Vaše řešení nemusí být hodnoceno.
Doporučujeme využít políčko pro komentář a vysvětlit situaci.
{% if round.ct_submit_end and g.now > round.ct_submit_end %}
<p class="alert alert-danger">Pozor, odevzdáváte po termínu (uplynul {{ round.ct_submit_end|timeformat }},
{{ human_timedelta(round.ct_submit_end) }}). Vaše řešení nemusí být hodnoceno. Doporučujeme využít políčko pro komentář a vysvětlit situaci.
{% endif %}
{{ wtf.quick_form(form, form_type='basic', button_map={'submit': 'primary'}) }}
{% else %}
<p><i>Soutěžní kolo neběží, již není možné odevzdat nové řešení.</i></p>
{% endif %}
<h3>Historie vašich řešení</h3>
......
......@@ -5,7 +5,7 @@
{% if pions %}
<p>Účastníte se následujících kol MO:
<table class=data>
<table class="table">
<thead>
<tr>
<th title='ročník MO'>Roč.
......@@ -21,11 +21,9 @@
<td>{{ round.category }}
<td>{{ round.name }}
<td>{{ contest.place.name }}
<td>{{ round.state.friendly_name() }}
<td>{{ round.long_state() }}
<td><div class="btn-group">
{% if round.state == db.RoundState.running %}
<a class='btn btn-xs btn-primary' href='{{ url_for('user_contest', id=contest.contest_id) }}'>Odevzdávat</a>
{% endif %}
<a class='btn btn-xs btn-primary' href='{{ url_for('user_contest', id=contest.contest_id) }}'>Detail kola</a>
</div>
{% endfor %}
</table>
......
......@@ -29,7 +29,6 @@ def user_index():
.join(db.Contest)
.join(db.Round)
.filter(db.Participation.user == g.user)
.filter(db.Round.state != db.RoundState.preparing)
.options(joinedload(db.Contest.place))
.order_by(db.Round.year.desc(), db.Round.category, db.Round.seq)
.all())
......@@ -50,12 +49,6 @@ def get_contest(id: int) -> db.Contest:
if not contest:
raise werkzeug.exceptions.NotFound()
# FIXME: Časem chceme účastníky pustit i v jiných stavech
# FIXME: A také místo generického Forbidden říci něco konkrétnějšího
# (je možné, že se sem účastník dostal reloadem stránky po konci contestu)
if contest.round.state != db.RoundState.running:
raise werkzeug.exceptions.Forbidden()
# FIXME: Kontrolovat nějak pion.state?
pion = (db.get_session().query(db.Participation)
.filter_by(user=g.user, contest=contest)
......@@ -94,7 +87,6 @@ def user_contest(id: int):
'user_contest.html',
contest=contest,
task_sols=task_sols,
statement_visible=contest.round.task_statement_available(),
max_submit_size=config.MAX_CONTENT_LENGTH,
db=db, # kvůli hodnotám enumů
)
......@@ -104,7 +96,7 @@ def user_contest(id: int):
def user_task_statement(id: int):
contest = get_contest(id)
if not contest.round.task_statement_available():
if not contest.round.task_statement_available(mo.now):
logger.warn(f'Účastník #{g.user.user_id} chce zadání, na které nemá právo')
raise werkzeug.exceptions.Forbidden()
......@@ -123,8 +115,14 @@ def user_contest_task(contest_id: int, task_id: int):
task = get_task(contest, task_id)
sess = db.get_session()
round = contest.round
if round.state == db.RoundState.preparing or (round.state == db.RoundState.running and not round.can_submit(mo.now)):
# Dokud se kolo připravuje nebo čeká na zveřejnění zadání, tak ani nezobrazujeme
# stránku, abychom něco neprozradili jménem úlohy
raise werkzeug.exceptions.Forbidden()
form = SubmitForm()
if form.validate_on_submit():
if round.can_submit(now) and form.validate_on_submit():
# FIXME: Tohle je pomalé, dělá se tu zbytečná další kopie dat.
# Nicméně werkzeugu by měla jít podstrčit stream factory,
# která bude vyrábět streamy rovnou uložené v našem tmp.
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment