Skip to content
Snippets Groups Projects
Commit 082cf331 authored by Martin Mareš's avatar Martin Mareš
Browse files

Propojení s CMS

parent 5b78f02a
No related branches found
No related tags found
No related merge requests found
This commit is part of merge request !98. Comments created here will be created in the context of that merge request.
......@@ -56,3 +56,8 @@ REG_TOKEN_VALIDITY = 10
# Aktuální ročník MO
CURRENT_YEAR = 71
# Instance CMS, ve které žijí praktické programovací úlohy, a její SSO secret.
# Pokud se neuvede nebo je None, praktické úlohy nejde odevzdávat.
# CMS_ROOT = 'https://contest.kam.mff.cuni.cz/cms/'
# CMS_SSO_SECRET = 'BrumBrum'
......@@ -42,6 +42,7 @@ app.jinja_env.globals.update(LogType=db.LogType)
app.jinja_env.globals.update(PartState=db.PartState)
app.jinja_env.globals.update(RoleType=db.RoleType)
app.jinja_env.globals.update(PaperType=db.PaperType)
app.jinja_env.globals.update(TaskType=db.TaskType)
app.jinja_env.globals.update(JobType=db.JobType)
app.jinja_env.globals.update(JobState=db.JobState)
......
......
{% extends "base.html" %}
{% block title %}Vítejte{% endblock %}
{% block body %}
<form action='http://localhost:8888/sso-login' method=POST>
<input type=hidden name=username value="{{ username }}">
<input type=hidden name=first_name value="{{ first_name }}">
<input type=hidden name=last_name value="{{ last_name }}">
<input type=hidden name=timestamp value="{{ timestamp }}">
<input type=hidden name=signature value="{{ signature }}">
<input type=submit value="CMS">
</form>
{% endblock %}
......@@ -23,6 +23,7 @@
{% if state == RoundState.running %}
{% if contest.ct_can_submit() %}
<h3>Odevzdat řešení</h3>
{% if task.type == TaskType.regular %}
{% 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|time_and_timedelta }}.
Vaše řešení nemusí být hodnoceno. Doporučujeme využít políčko pro poznámku a vysvětlit situaci.
......@@ -32,6 +33,22 @@
nahradili (např. nahráli jste omylem řešení jiné úlohy).
{% endif %}
{{ wtf.quick_form(form, form_type='basic', button_map={'submit': 'primary'}) }}
{% elif task.type == TaskType.cms and cms_params %}
<p>Tato úloha je praktická a odevzdává se do systému CMS. Odevzdaná řešení
se zde objeví až s koncem soutěže.
<form action='{{ cms_params.url }}' method=POST>
<input type=hidden name=username value="{{ cms_params.username }}">
<input type=hidden name=first_name value="{{ cms_params.first_name }}">
<input type=hidden name=last_name value="{{ cms_params.last_name }}">
<input type=hidden name=timestamp value="{{ cms_params.timestamp }}">
<input type=hidden name=signature value="{{ cms_params.signature }}">
<input type=hidden name=back_url value="{{ cms_params.back_url }}">
<input type=submit class='btn btn-primary' value="Přejít do CMS">
</form>
{% else %}
<p>Úloha s neznámým režimem odevzdávání.
{% endif %}
{% else %}
<p>Již není možné odevzdat řešení, termín na odevzdávání vypršel.</p>
{% endif %}
......@@ -57,7 +74,7 @@
<p>Soutěž se nachází v neznámém stavu. To by se nemělo stát :)
{% endif %}
{% if sol or state == RoundState.running %}
{% if sol or state == RoundState.running and task.type == TaskType.regular %}
<h3>Historie vašich řešení</h3>
{% if papers %}
......
......
from dataclasses import dataclass
from flask import render_template, jsonify, g, redirect, url_for, flash, request
from flask_wtf import FlaskForm
import flask_wtf.file
......@@ -5,7 +6,7 @@ import hashlib
import hmac
from sqlalchemy import and_
from sqlalchemy.orm import joinedload
from typing import List, Tuple
from typing import List, Tuple, Optional
import werkzeug.exceptions
import wtforms
from wtforms.validators import Required
......@@ -344,6 +345,34 @@ class SubmitForm(FlaskForm):
submit = wtforms.SubmitField('Odevzdat')
@dataclass
class CMSParams:
url: str
username: str
first_name: str
last_name: str
timestamp: str
signature: str = ""
back_url: str = ""
def get_cms_params() -> Optional[CMSParams]:
if not (hasattr(config, 'CMS_ROOT') and hasattr(config, 'CMS_SSO_SECRET')):
return None
p = CMSParams(
url=config.CMS_ROOT + 'sso-login',
username=f'osmo{g.user.user_id}',
first_name=g.user.first_name,
last_name=g.user.last_name,
timestamp=str(int(mo.now.timestamp())),
)
msg = ":".join((p.username, p.first_name, p.last_name, p.timestamp)).encode('utf-8')
key = config.CMS_SSO_SECRET.encode('us-ascii')
p.signature = hmac.HMAC(key, msg, digestmod=hashlib.sha256).hexdigest()
return p
@app.route('/user/contest/<int:contest_id>/task/<int:task_id>/', methods=('GET', 'POST'))
def user_contest_task(contest_id: int, task_id: int):
contest = get_contest(contest_id)
......@@ -361,8 +390,13 @@ def user_contest_task(contest_id: int, task_id: int):
# stránku, abychom něco neprozradili jménem úlohy
raise werkzeug.exceptions.Forbidden()
form: Optional[SubmitForm] = None
if task.type == db.TaskType.regular:
form = SubmitForm()
if contest.ct_can_submit() and form.validate_on_submit():
if task.type != db.TaskType.regular:
raise werkzeug.exceptions.Forbidden()
file = form.file.data.stream
paper = db.Paper(task=task, for_user_obj=g.user, uploaded_by_obj=g.user, type=db.PaperType.solution, note=form.note.data)
submitter = mo.submit.Submitter()
......@@ -396,6 +430,12 @@ def user_contest_task(contest_id: int, task_id: int):
flash('Řešení odevzdáno', 'success')
return redirect(url_for('user_contest', id=contest_id))
cms_params: Optional[CMSParams] = None
if task.type == db.TaskType.cms:
cms_params = get_cms_params()
if cms_params:
cms_params.back_url = url_for('user_contest_task', contest_id=contest_id, task_id=task_id)
sol = sess.query(db.Solution).filter_by(task=task, user=g.user).one_or_none()
papers = (sess.query(db.Paper)
......@@ -411,6 +451,7 @@ def user_contest_task(contest_id: int, task_id: int):
sol=sol,
papers=papers,
form=form,
cms_params=cms_params,
messages=messages,
)
......@@ -449,23 +490,3 @@ def user_paper(contest_id: int, paper_id: int):
raise werkzeug.exceptions.Forbidden()
return mo.web.util.send_task_paper(paper)
@app.route('/user/cms')
def user_cms():
username = "brum"
first_name = "Lední"
last_name = "Medvěd"
timestamp = str(int(mo.now.timestamp()))
msg = ":".join((username, first_name, last_name, timestamp)).encode('utf-8')
key = "BrumBrum".encode('us-ascii')
signature = hmac.HMAC(key, msg, digestmod=hashlib.sha256).hexdigest()
return render_template(
'cms.html',
username=username,
first_name=first_name,
last_name=last_name,
timestamp=timestamp,
signature=signature,
)
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please to comment