Tableau saisie jury basé sur recap_complet
This commit is contained in:
parent
ec57ba4ef7
commit
7a8c77add4
@ -18,7 +18,7 @@ from app.auth.models import User
|
|||||||
from app.comp.res_cache import ResultatsCache
|
from app.comp.res_cache import ResultatsCache
|
||||||
from app.comp import res_sem
|
from app.comp import res_sem
|
||||||
from app.comp.moy_mod import ModuleImplResults
|
from app.comp.moy_mod import ModuleImplResults
|
||||||
from app.models import FormSemestre, FormSemestreUECoef
|
from app.models import FormSemestre, FormSemestreUECoef, formsemestre
|
||||||
from app.models import Identite
|
from app.models import Identite
|
||||||
from app.models import ModuleImpl, ModuleImplInscription
|
from app.models import ModuleImpl, ModuleImplInscription
|
||||||
from app.models.ues import UniteEns
|
from app.models.ues import UniteEns
|
||||||
@ -388,7 +388,9 @@ class ResultatsSemestre(ResultatsCache):
|
|||||||
|
|
||||||
# --- TABLEAU RECAP
|
# --- TABLEAU RECAP
|
||||||
|
|
||||||
def get_table_recap(self, convert_values=False, include_evaluations=False):
|
def get_table_recap(
|
||||||
|
self, convert_values=False, include_evaluations=False, modejury=False
|
||||||
|
):
|
||||||
"""Result: tuple avec
|
"""Result: tuple avec
|
||||||
- rows: liste de dicts { column_id : value }
|
- rows: liste de dicts { column_id : value }
|
||||||
- titles: { column_id : title }
|
- titles: { column_id : title }
|
||||||
@ -538,6 +540,9 @@ class ResultatsSemestre(ResultatsCache):
|
|||||||
titles_bot[
|
titles_bot[
|
||||||
f"_{col_id}_target_attrs"
|
f"_{col_id}_target_attrs"
|
||||||
] = f"""title="{ue.titre} S{ue.semestre_idx or '?'}" """
|
] = f"""title="{ue.titre} S{ue.semestre_idx or '?'}" """
|
||||||
|
if modejury:
|
||||||
|
# pas d'autre colonnes de résultats
|
||||||
|
continue
|
||||||
# Bonus (sport) dans cette UE ?
|
# Bonus (sport) dans cette UE ?
|
||||||
# Le bonus sport appliqué sur cette UE
|
# Le bonus sport appliqué sur cette UE
|
||||||
if (self.bonus_ues is not None) and (ue.id in self.bonus_ues):
|
if (self.bonus_ues is not None) and (ue.id in self.bonus_ues):
|
||||||
@ -632,6 +637,18 @@ class ResultatsSemestre(ResultatsCache):
|
|||||||
elif nb_ues_validables < len(ues_sans_bonus):
|
elif nb_ues_validables < len(ues_sans_bonus):
|
||||||
row["_ues_validables_class"] += " moy_inf"
|
row["_ues_validables_class"] += " moy_inf"
|
||||||
row["_ues_validables_order"] = nb_ues_validables # pour tri
|
row["_ues_validables_order"] = nb_ues_validables # pour tri
|
||||||
|
if modejury:
|
||||||
|
idx = add_cell(
|
||||||
|
row,
|
||||||
|
"jury_link",
|
||||||
|
"",
|
||||||
|
f"""<a href="{url_for('notes.formsemestre_validation_etud_form',
|
||||||
|
scodoc_dept=g.scodoc_dept, formsemestre_id=self.formsemestre.id, etudid=etudid
|
||||||
|
)
|
||||||
|
}">saisir décision</a>""",
|
||||||
|
"col_jury_link",
|
||||||
|
1000,
|
||||||
|
)
|
||||||
rows.append(row)
|
rows.append(row)
|
||||||
|
|
||||||
self._recap_add_partitions(rows, titles)
|
self._recap_add_partitions(rows, titles)
|
||||||
|
@ -404,9 +404,6 @@ def formsemestre_status_menubar(sem):
|
|||||||
"args": {
|
"args": {
|
||||||
"formsemestre_id": formsemestre_id,
|
"formsemestre_id": formsemestre_id,
|
||||||
"modejury": 1,
|
"modejury": 1,
|
||||||
"hidemodules": 1,
|
|
||||||
"hidebac": 1,
|
|
||||||
"pref_override": 0,
|
|
||||||
},
|
},
|
||||||
"enabled": sco_permissions_check.can_validate_sem(formsemestre_id),
|
"enabled": sco_permissions_check.can_validate_sem(formsemestre_id),
|
||||||
},
|
},
|
||||||
|
@ -31,6 +31,7 @@ import time
|
|||||||
|
|
||||||
import flask
|
import flask
|
||||||
from flask import url_for, g, request
|
from flask import url_for, g, request
|
||||||
|
from app.models.etudiants import Identite
|
||||||
|
|
||||||
import app.scodoc.notesdb as ndb
|
import app.scodoc.notesdb as ndb
|
||||||
import app.scodoc.sco_utils as scu
|
import app.scodoc.sco_utils as scu
|
||||||
@ -107,29 +108,57 @@ def formsemestre_validation_etud_form(
|
|||||||
if not Se.sem["etat"]:
|
if not Se.sem["etat"]:
|
||||||
raise ScoValueError("validation: semestre verrouille")
|
raise ScoValueError("validation: semestre verrouille")
|
||||||
|
|
||||||
|
url_tableau = url_for(
|
||||||
|
"notes.formsemestre_recapcomplet",
|
||||||
|
scodoc_dept=g.scodoc_dept,
|
||||||
|
modejury=1,
|
||||||
|
formsemestre_id=formsemestre_id,
|
||||||
|
selected_etudid=etudid, # va a la bonne ligne
|
||||||
|
)
|
||||||
|
|
||||||
H = [
|
H = [
|
||||||
html_sco_header.sco_header(
|
html_sco_header.sco_header(
|
||||||
page_title="Parcours %(nomprenom)s" % etud,
|
page_title=f"Parcours {etud['nomprenom']}",
|
||||||
javascripts=["js/recap_parcours.js"],
|
javascripts=["js/recap_parcours.js"],
|
||||||
)
|
)
|
||||||
]
|
]
|
||||||
|
|
||||||
Footer = ["<p>"]
|
|
||||||
# Navigation suivant/precedent
|
# Navigation suivant/precedent
|
||||||
if etud_index_prev != None:
|
if etud_index_prev is not None:
|
||||||
etud_p = sco_etud.get_etud_info(etudid=T[etud_index_prev][-1], filled=True)[0]
|
etud_prev = Identite.query.get(T[etud_index_prev][-1])
|
||||||
Footer.append(
|
url_prev = url_for(
|
||||||
'<span><a href="formsemestre_validation_etud_form?formsemestre_id=%s&etud_index=%s">Etud. précédent (%s)</a></span>'
|
"notes.formsemestre_validation_etud_form",
|
||||||
% (formsemestre_id, etud_index_prev, etud_p["nomprenom"])
|
scodoc_dept=g.scodoc_dept,
|
||||||
|
formsemestre_id=formsemestre_id,
|
||||||
|
etud_index=etud_index_prev,
|
||||||
)
|
)
|
||||||
if etud_index_next != None:
|
else:
|
||||||
etud_n = sco_etud.get_etud_info(etudid=T[etud_index_next][-1], filled=True)[0]
|
url_prev = None
|
||||||
Footer.append(
|
if etud_index_next is not None:
|
||||||
'<span style="padding-left: 50px;"><a href="formsemestre_validation_etud_form?formsemestre_id=%s&etud_index=%s">Etud. suivant (%s)</a></span>'
|
etud_next = Identite.query.get(T[etud_index_next][-1])
|
||||||
% (formsemestre_id, etud_index_next, etud_n["nomprenom"])
|
url_next = url_for(
|
||||||
|
"notes.formsemestre_validation_etud_form",
|
||||||
|
scodoc_dept=g.scodoc_dept,
|
||||||
|
formsemestre_id=formsemestre_id,
|
||||||
|
etud_index=etud_index_next,
|
||||||
)
|
)
|
||||||
Footer.append("</p>")
|
else:
|
||||||
Footer.append(html_sco_header.sco_footer())
|
url_next = None
|
||||||
|
footer = ["""<div class="jury_footer"><span>"""]
|
||||||
|
if url_prev:
|
||||||
|
footer.append(
|
||||||
|
f'< <a class="stdlink" href="{url_prev}">{etud_prev.nomprenom}</a>'
|
||||||
|
)
|
||||||
|
footer.append(
|
||||||
|
f"""</span><span><a class="stdlink" href="{url_tableau}">retour à la liste</a></span><span>"""
|
||||||
|
)
|
||||||
|
if url_next:
|
||||||
|
footer.append(
|
||||||
|
f'<a class="stdlink" href="{url_next}">{etud_next.nomprenom}</a> >'
|
||||||
|
)
|
||||||
|
footer.append("</span></div>")
|
||||||
|
|
||||||
|
footer.append(html_sco_header.sco_footer())
|
||||||
|
|
||||||
H.append('<table style="width: 100%"><tr><td>')
|
H.append('<table style="width: 100%"><tr><td>')
|
||||||
if not check:
|
if not check:
|
||||||
@ -171,7 +200,7 @@ def formsemestre_validation_etud_form(
|
|||||||
"""
|
"""
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
return "\n".join(H + Footer)
|
return "\n".join(H + footer)
|
||||||
|
|
||||||
H.append(
|
H.append(
|
||||||
formsemestre_recap_parcours_table(
|
formsemestre_recap_parcours_table(
|
||||||
@ -180,18 +209,10 @@ def formsemestre_validation_etud_form(
|
|||||||
)
|
)
|
||||||
if check:
|
if check:
|
||||||
if not desturl:
|
if not desturl:
|
||||||
desturl = url_for(
|
desturl = url_tableau
|
||||||
"notes.formsemestre_recapcomplet",
|
|
||||||
scodoc_dept=g.scodoc_dept,
|
|
||||||
modejury=1,
|
|
||||||
formsemestre_id=formsemestre_id,
|
|
||||||
sortcol=sortcol
|
|
||||||
or None, # pour refaire tri sorttable du tableau de notes
|
|
||||||
_anchor="etudid%s" % etudid, # va a la bonne ligne
|
|
||||||
)
|
|
||||||
H.append(f'<ul><li><a href="{desturl}">Continuer</a></li></ul>')
|
H.append(f'<ul><li><a href="{desturl}">Continuer</a></li></ul>')
|
||||||
|
|
||||||
return "\n".join(H + Footer)
|
return "\n".join(H + footer)
|
||||||
|
|
||||||
decision_jury = Se.nt.get_etud_decision_sem(etudid)
|
decision_jury = Se.nt.get_etud_decision_sem(etudid)
|
||||||
|
|
||||||
@ -207,7 +228,7 @@ def formsemestre_validation_etud_form(
|
|||||||
"""
|
"""
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
return "\n".join(H + Footer)
|
return "\n".join(H + footer)
|
||||||
|
|
||||||
# Infos si pas de semestre précédent
|
# Infos si pas de semestre précédent
|
||||||
if not Se.prev:
|
if not Se.prev:
|
||||||
@ -345,7 +366,7 @@ def formsemestre_validation_etud_form(
|
|||||||
else:
|
else:
|
||||||
H.append("sans semestres décalés</p>")
|
H.append("sans semestres décalés</p>")
|
||||||
|
|
||||||
return "".join(H + Footer)
|
return "".join(H + footer)
|
||||||
|
|
||||||
|
|
||||||
def formsemestre_validation_etud(
|
def formsemestre_validation_etud(
|
||||||
@ -937,19 +958,23 @@ def do_formsemestre_validation_auto(formsemestre_id):
|
|||||||
)
|
)
|
||||||
if conflicts:
|
if conflicts:
|
||||||
H.append(
|
H.append(
|
||||||
"""<p><b>Attention:</b> %d étudiants non modifiés car décisions différentes
|
f"""<p><b>Attention:</b> {len(conflicts)} étudiants non modifiés
|
||||||
déja saisies :<ul>"""
|
car décisions différentes déja saisies :
|
||||||
% len(conflicts)
|
<ul>"""
|
||||||
)
|
)
|
||||||
for etud in conflicts:
|
for etud in conflicts:
|
||||||
H.append(
|
H.append(
|
||||||
'<li><a href="formsemestre_validation_etud_form?formsemestre_id=%s&etudid=%s&check=1">%s</li>'
|
f"""<li><a href="{
|
||||||
% (formsemestre_id, etud["etudid"], etud["nomprenom"])
|
url_for('notes.formsemestre_validation_etud_form',
|
||||||
|
scodoc_dept=g.scodoc_dept, formsemestre_id=formsemestre_id,
|
||||||
|
etudid=etud["etudid"], check=1)
|
||||||
|
}">{etud["nomprenom"]}</li>"""
|
||||||
)
|
)
|
||||||
H.append("</ul>")
|
H.append("</ul>")
|
||||||
H.append(
|
H.append(
|
||||||
'<a href="formsemestre_recapcomplet?formsemestre_id=%s&modejury=1&hidemodules=1&hidebac=1&pref_override=0">continuer</a>'
|
f"""<a href="{url_for('notes.formsemestre_recapcomplet',
|
||||||
% formsemestre_id
|
scodoc_dept=g.scodoc_dept, formsemestre_id=formsemestre_id, modejury=1)
|
||||||
|
}">continuer</a>"""
|
||||||
)
|
)
|
||||||
H.append(html_sco_header.sco_footer())
|
H.append(html_sco_header.sco_footer())
|
||||||
return "\n".join(H)
|
return "\n".join(H)
|
||||||
|
@ -32,7 +32,7 @@ import time
|
|||||||
from xml.etree import ElementTree
|
from xml.etree import ElementTree
|
||||||
|
|
||||||
from flask import g, request
|
from flask import g, request
|
||||||
from flask import make_response, url_for
|
from flask import url_for
|
||||||
|
|
||||||
from app import log
|
from app import log
|
||||||
from app.but import bulletin_but
|
from app.but import bulletin_but
|
||||||
@ -40,39 +40,29 @@ from app.comp import res_sem
|
|||||||
from app.comp.res_compat import NotesTableCompat
|
from app.comp.res_compat import NotesTableCompat
|
||||||
from app.models import FormSemestre
|
from app.models import FormSemestre
|
||||||
from app.models.etudiants import Identite
|
from app.models.etudiants import Identite
|
||||||
from app.models.evaluations import Evaluation
|
|
||||||
|
|
||||||
from app.scodoc.gen_tables import GenTable
|
from app.scodoc.gen_tables import GenTable
|
||||||
import app.scodoc.sco_utils as scu
|
import app.scodoc.sco_utils as scu
|
||||||
from app.scodoc import html_sco_header
|
from app.scodoc import html_sco_header
|
||||||
from app.scodoc import sco_bulletins_json
|
from app.scodoc import sco_bulletins_json
|
||||||
from app.scodoc import sco_bulletins_xml
|
from app.scodoc import sco_bulletins_xml
|
||||||
from app.scodoc import sco_bulletins, sco_excel
|
|
||||||
from app.scodoc import sco_cache
|
from app.scodoc import sco_cache
|
||||||
from app.scodoc import sco_codes_parcours
|
|
||||||
from app.scodoc import sco_evaluations
|
from app.scodoc import sco_evaluations
|
||||||
from app.scodoc import sco_evaluation_db
|
|
||||||
from app.scodoc.sco_exceptions import ScoValueError
|
from app.scodoc.sco_exceptions import ScoValueError
|
||||||
from app.scodoc import sco_formations
|
|
||||||
from app.scodoc import sco_formsemestre
|
from app.scodoc import sco_formsemestre
|
||||||
from app.scodoc import sco_formsemestre_status
|
from app.scodoc import sco_formsemestre_status
|
||||||
from app.scodoc import sco_groups
|
|
||||||
from app.scodoc import sco_permissions_check
|
from app.scodoc import sco_permissions_check
|
||||||
from app.scodoc import sco_preferences
|
from app.scodoc import sco_preferences
|
||||||
from app.scodoc import sco_etud
|
|
||||||
from app.scodoc import sco_users
|
|
||||||
from app.scodoc import sco_xml
|
|
||||||
from app.scodoc.sco_codes_parcours import DEF, UE_SPORT
|
|
||||||
|
|
||||||
|
|
||||||
def formsemestre_recapcomplet(
|
def formsemestre_recapcomplet(
|
||||||
formsemestre_id=None,
|
formsemestre_id=None,
|
||||||
modejury=False, # affiche lien saisie decision jury
|
modejury=False,
|
||||||
tabformat="html",
|
tabformat="html",
|
||||||
sortcol=None,
|
sortcol=None,
|
||||||
xml_with_decisions=False, # XML avec decisions
|
xml_with_decisions=False,
|
||||||
rank_partition_id=None, # si None, calcul rang global
|
force_publishing=True,
|
||||||
force_publishing=True, # publie les XML/JSON meme si bulletins non publiés
|
selected_etudid=None,
|
||||||
):
|
):
|
||||||
"""Page récapitulant les notes d'un semestre.
|
"""Page récapitulant les notes d'un semestre.
|
||||||
Grand tableau récapitulatif avec toutes les notes de modules
|
Grand tableau récapitulatif avec toutes les notes de modules
|
||||||
@ -89,7 +79,9 @@ def formsemestre_recapcomplet(
|
|||||||
pdf : NON SUPPORTE (car tableau trop grand pour générer un pdf utilisable)
|
pdf : NON SUPPORTE (car tableau trop grand pour générer un pdf utilisable)
|
||||||
|
|
||||||
modejury: cache modules, affiche lien saisie decision jury
|
modejury: cache modules, affiche lien saisie decision jury
|
||||||
|
xml_with_decisions: publie décisions de jury dans xml et json
|
||||||
|
force_publishing: publie les xml et json même si bulletins non publiés
|
||||||
|
selected_etudid: etudid sélectionné (pour scroller au bon endroit)
|
||||||
"""
|
"""
|
||||||
formsemestre = FormSemestre.query.get_or_404(formsemestre_id)
|
formsemestre = FormSemestre.query.get_or_404(formsemestre_id)
|
||||||
|
|
||||||
@ -98,98 +90,92 @@ def formsemestre_recapcomplet(
|
|||||||
xml_with_decisions = int(xml_with_decisions)
|
xml_with_decisions = int(xml_with_decisions)
|
||||||
force_publishing = int(force_publishing)
|
force_publishing = int(force_publishing)
|
||||||
is_file = tabformat in {"csv", "json", "xls", "xlsx", "xlsall", "xml"}
|
is_file = tabformat in {"csv", "json", "xls", "xlsx", "xlsall", "xml"}
|
||||||
H = []
|
data = _do_formsemestre_recapcomplet(
|
||||||
if not is_file:
|
|
||||||
H += [
|
|
||||||
html_sco_header.sco_header(
|
|
||||||
page_title="Récapitulatif",
|
|
||||||
no_side_bar=True,
|
|
||||||
init_qtip=True,
|
|
||||||
javascripts=["js/etud_info.js", "js/table_recap.js"],
|
|
||||||
),
|
|
||||||
sco_formsemestre_status.formsemestre_status_head(
|
|
||||||
formsemestre_id=formsemestre_id
|
|
||||||
),
|
|
||||||
]
|
|
||||||
if len(formsemestre.inscriptions) > 0:
|
|
||||||
H.append(
|
|
||||||
f"""<form name="f" method="get" action="{request.base_url}">
|
|
||||||
<input type="hidden" name="formsemestre_id" value="{formsemestre_id}"></input>
|
|
||||||
"""
|
|
||||||
)
|
|
||||||
if modejury:
|
|
||||||
H.append(
|
|
||||||
f'<input type="hidden" name="modejury" value="{modejury}"></input>'
|
|
||||||
)
|
|
||||||
H.append(
|
|
||||||
'<select name="tabformat" onchange="document.f.submit()" class="noprint">'
|
|
||||||
)
|
|
||||||
for (format, label) in (
|
|
||||||
("html", "Tableau"),
|
|
||||||
("evals", "Avec toutes les évaluations"),
|
|
||||||
("xml", "Bulletins XML (obsolète)"),
|
|
||||||
("json", "Bulletins JSON"),
|
|
||||||
):
|
|
||||||
if format == tabformat:
|
|
||||||
selected = " selected"
|
|
||||||
else:
|
|
||||||
selected = ""
|
|
||||||
H.append(f'<option value="{format}"{selected}>{label}</option>')
|
|
||||||
H.append("</select>")
|
|
||||||
|
|
||||||
H.append(
|
|
||||||
f""" (cliquer sur un nom pour afficher son bulletin ou <a class="stdlink"
|
|
||||||
href="{url_for('notes.formsemestre_bulletins_pdf',
|
|
||||||
scodoc_dept=g.scodoc_dept, formsemestre_id=formsemestre_id)
|
|
||||||
}">ici avoir le classeur papier</a>)
|
|
||||||
"""
|
|
||||||
)
|
|
||||||
|
|
||||||
data = do_formsemestre_recapcomplet(
|
|
||||||
formsemestre_id,
|
formsemestre_id,
|
||||||
format=tabformat,
|
format=tabformat,
|
||||||
modejury=modejury,
|
modejury=modejury,
|
||||||
sortcol=sortcol,
|
sortcol=sortcol,
|
||||||
xml_with_decisions=xml_with_decisions,
|
xml_with_decisions=xml_with_decisions,
|
||||||
rank_partition_id=rank_partition_id,
|
|
||||||
force_publishing=force_publishing,
|
force_publishing=force_publishing,
|
||||||
|
selected_etudid=selected_etudid,
|
||||||
)
|
)
|
||||||
if tabformat == "xml":
|
if is_file:
|
||||||
response = make_response(data)
|
return data
|
||||||
response.headers["Content-Type"] = scu.XML_MIMETYPE
|
H = [
|
||||||
return response
|
html_sco_header.sco_header(
|
||||||
|
page_title="Récapitulatif",
|
||||||
|
no_side_bar=True,
|
||||||
|
init_qtip=True,
|
||||||
|
javascripts=["js/etud_info.js", "js/table_recap.js"],
|
||||||
|
),
|
||||||
|
sco_formsemestre_status.formsemestre_status_head(
|
||||||
|
formsemestre_id=formsemestre_id
|
||||||
|
),
|
||||||
|
]
|
||||||
|
if len(formsemestre.inscriptions) > 0:
|
||||||
|
H.append(
|
||||||
|
f"""<form name="f" method="get" action="{request.base_url}">
|
||||||
|
<input type="hidden" name="formsemestre_id" value="{formsemestre_id}"></input>
|
||||||
|
"""
|
||||||
|
)
|
||||||
|
if modejury:
|
||||||
|
H.append(
|
||||||
|
f'<input type="hidden" name="modejury" value="{modejury}"></input>'
|
||||||
|
)
|
||||||
|
H.append(
|
||||||
|
'<select name="tabformat" onchange="document.f.submit()" class="noprint">'
|
||||||
|
)
|
||||||
|
for (format, label) in (
|
||||||
|
("html", "Tableau"),
|
||||||
|
("evals", "Avec toutes les évaluations"),
|
||||||
|
("xml", "Bulletins XML (obsolète)"),
|
||||||
|
("json", "Bulletins JSON"),
|
||||||
|
):
|
||||||
|
if format == tabformat:
|
||||||
|
selected = " selected"
|
||||||
|
else:
|
||||||
|
selected = ""
|
||||||
|
H.append(f'<option value="{format}"{selected}>{label}</option>')
|
||||||
|
H.append("</select>")
|
||||||
|
|
||||||
|
H.append(
|
||||||
|
f""" (cliquer sur un nom pour afficher son bulletin ou <a class="stdlink"
|
||||||
|
href="{url_for('notes.formsemestre_bulletins_pdf',
|
||||||
|
scodoc_dept=g.scodoc_dept, formsemestre_id=formsemestre_id)
|
||||||
|
}">ici avoir le classeur papier</a>)
|
||||||
|
"""
|
||||||
|
)
|
||||||
H.append(data)
|
H.append(data)
|
||||||
|
|
||||||
if not is_file:
|
if len(formsemestre.inscriptions) > 0:
|
||||||
if len(formsemestre.inscriptions) > 0:
|
H.append("</form>")
|
||||||
H.append("</form>")
|
H.append(
|
||||||
H.append(
|
f"""<p><a class="stdlink" href="{url_for('notes.formsemestre_pvjury',
|
||||||
f"""<p><a class="stdlink" href="{url_for('notes.formsemestre_pvjury',
|
scodoc_dept=g.scodoc_dept, formsemestre_id=formsemestre_id)
|
||||||
scodoc_dept=g.scodoc_dept, formsemestre_id=formsemestre_id)
|
}">Voir les décisions du jury</a></p>"""
|
||||||
}">Voir les décisions du jury</a></p>"""
|
)
|
||||||
)
|
if sco_permissions_check.can_validate_sem(formsemestre_id):
|
||||||
if sco_permissions_check.can_validate_sem(formsemestre_id):
|
H.append("<p>")
|
||||||
H.append("<p>")
|
if modejury:
|
||||||
if modejury:
|
|
||||||
H.append(
|
|
||||||
f"""<a class="stdlink" href="{url_for('formsemestre_validation_auto',
|
|
||||||
formsemestre_id=formsemestre_id)
|
|
||||||
}">Calcul automatique des décisions du jury</a></p>"""
|
|
||||||
)
|
|
||||||
else:
|
|
||||||
H.append(
|
|
||||||
f"""<a class="stdlink" href="{url_for('notes.formsemestre_recapcomplet',
|
|
||||||
scodoc_dept=g.scodoc_dept, formsemestre_id=formsemestre_id, modejury=1)
|
|
||||||
}">Saisie des décisions du jury</a>"""
|
|
||||||
)
|
|
||||||
H.append("</p>")
|
|
||||||
if sco_preferences.get_preference("use_ue_coefs", formsemestre_id):
|
|
||||||
H.append(
|
H.append(
|
||||||
"""
|
f"""<a class="stdlink" href="{url_for('notes.formsemestre_validation_auto',
|
||||||
<p class="infop">utilise les coefficients d'UE pour calculer la moyenne générale.</p>
|
scodoc_dept=g.scodoc_dept, formsemestre_id=formsemestre_id)
|
||||||
"""
|
}">Calcul automatique des décisions du jury</a></p>"""
|
||||||
)
|
)
|
||||||
H.append(html_sco_header.sco_footer())
|
else:
|
||||||
|
H.append(
|
||||||
|
f"""<a class="stdlink" href="{url_for('notes.formsemestre_recapcomplet',
|
||||||
|
scodoc_dept=g.scodoc_dept, formsemestre_id=formsemestre_id, modejury=1)
|
||||||
|
}">Saisie des décisions du jury</a>"""
|
||||||
|
)
|
||||||
|
H.append("</p>")
|
||||||
|
if sco_preferences.get_preference("use_ue_coefs", formsemestre_id):
|
||||||
|
H.append(
|
||||||
|
"""
|
||||||
|
<p class="infop">utilise les coefficients d'UE pour calculer la moyenne générale.</p>
|
||||||
|
"""
|
||||||
|
)
|
||||||
|
H.append(html_sco_header.sco_footer())
|
||||||
# HTML or binary data ?
|
# HTML or binary data ?
|
||||||
if len(H) > 1:
|
if len(H) > 1:
|
||||||
return "".join(H)
|
return "".join(H)
|
||||||
@ -199,18 +185,15 @@ def formsemestre_recapcomplet(
|
|||||||
return H
|
return H
|
||||||
|
|
||||||
|
|
||||||
def do_formsemestre_recapcomplet(
|
def _do_formsemestre_recapcomplet(
|
||||||
formsemestre_id=None,
|
formsemestre_id=None,
|
||||||
format="html", # html, xml, xls, xlsall, json
|
format="html", # html, xml, xls, xlsall, json
|
||||||
hidemodules=False, # ne pas montrer les modules (ignoré en XML)
|
|
||||||
hidebac=False, # pas de colonne Bac (ignoré en XML)
|
|
||||||
xml_nodate=False, # format XML sans dates (sert pour debug cache: comparaison de XML)
|
xml_nodate=False, # format XML sans dates (sert pour debug cache: comparaison de XML)
|
||||||
modejury=False, # saisie décisions jury
|
modejury=False, # saisie décisions jury
|
||||||
sortcol=None, # indice colonne a trier dans table T
|
sortcol=None, # indice colonne a trier dans table T
|
||||||
xml_with_decisions=False,
|
xml_with_decisions=False,
|
||||||
disable_etudlink=False,
|
|
||||||
rank_partition_id=None, # si None, calcul rang global
|
|
||||||
force_publishing=True,
|
force_publishing=True,
|
||||||
|
selected_etudid=None,
|
||||||
):
|
):
|
||||||
"""Calcule et renvoie le tableau récapitulatif."""
|
"""Calcule et renvoie le tableau récapitulatif."""
|
||||||
formsemestre = FormSemestre.query.get_or_404(formsemestre_id)
|
formsemestre = FormSemestre.query.get_or_404(formsemestre_id)
|
||||||
@ -219,13 +202,15 @@ def do_formsemestre_recapcomplet(
|
|||||||
f"""recap-{formsemestre.titre_num()}-{time.strftime("%Y-%m-%d")}"""
|
f"""recap-{formsemestre.titre_num()}-{time.strftime("%Y-%m-%d")}"""
|
||||||
)
|
)
|
||||||
|
|
||||||
if (format == "html" or format == "evals") and not modejury:
|
if format == "html" or format == "evals":
|
||||||
res: NotesTableCompat = res_sem.load_formsemestre_results(formsemestre)
|
res: NotesTableCompat = res_sem.load_formsemestre_results(formsemestre)
|
||||||
data = gen_formsemestre_recapcomplet_html(
|
data = gen_formsemestre_recapcomplet_html(
|
||||||
formsemestre,
|
formsemestre,
|
||||||
res,
|
res,
|
||||||
include_evaluations=(format == "evals"),
|
include_evaluations=(format == "evals"),
|
||||||
|
modejury=modejury,
|
||||||
filename=filename,
|
filename=filename,
|
||||||
|
selected_etudid=selected_etudid,
|
||||||
)
|
)
|
||||||
return data
|
return data
|
||||||
elif format.startswith("xls") or format == "csv":
|
elif format.startswith("xls") or format == "csv":
|
||||||
@ -388,35 +373,51 @@ def _gen_cell(key: str, row: dict, elt="td"):
|
|||||||
return f"<{elt} {attrs}>{content}</{elt}>"
|
return f"<{elt} {attrs}>{content}</{elt}>"
|
||||||
|
|
||||||
|
|
||||||
def _gen_row(keys: list[str], row, elt="td"):
|
def _gen_row(keys: list[str], row, elt="td", selected_etudid=None):
|
||||||
klass = row.get("_tr_class")
|
klass = row.get("_tr_class")
|
||||||
tr_class = f'class="{klass}"' if klass else ""
|
tr_class = f'class="{klass}"' if klass else ""
|
||||||
return f'<tr {tr_class}>{"".join([_gen_cell(key, row, elt) for key in keys])}</tr>'
|
tr_id = (
|
||||||
|
f"""id="row_selected" """ if (row.get("etudid", "") == selected_etudid) else ""
|
||||||
|
)
|
||||||
|
return f'<tr {tr_id} {tr_class}>{"".join([_gen_cell(key, row, elt) for key in keys])}</tr>'
|
||||||
|
|
||||||
|
|
||||||
def gen_formsemestre_recapcomplet_html(
|
def gen_formsemestre_recapcomplet_html(
|
||||||
formsemestre: FormSemestre,
|
formsemestre: FormSemestre,
|
||||||
res: NotesTableCompat,
|
res: NotesTableCompat,
|
||||||
include_evaluations=False,
|
include_evaluations=False,
|
||||||
|
modejury=False,
|
||||||
filename="",
|
filename="",
|
||||||
|
selected_etudid=None,
|
||||||
):
|
):
|
||||||
"""Construit table recap pour le BUT
|
"""Construit table recap pour le BUT
|
||||||
Cache le résultat pour le semestre.
|
Cache le résultat pour le semestre (sauf en mode jury).
|
||||||
|
|
||||||
|
Si modejury, cache colonnes modules et affiche un lien vers la saisie de la décision de jury
|
||||||
|
|
||||||
Return: data, filename
|
Return: data, filename
|
||||||
data est une chaine, le <div>...</div> incluant le tableau.
|
data est une chaine, le <div>...</div> incluant le tableau.
|
||||||
"""
|
"""
|
||||||
if include_evaluations:
|
table_html = None
|
||||||
table_html = sco_cache.TableRecapWithEvalsCache.get(formsemestre.id)
|
if not (modejury or selected_etudid):
|
||||||
else:
|
|
||||||
table_html = sco_cache.TableRecapCache.get(formsemestre.id)
|
|
||||||
if table_html is None:
|
|
||||||
table_html = _gen_formsemestre_recapcomplet_html(
|
|
||||||
formsemestre, res, include_evaluations, filename
|
|
||||||
)
|
|
||||||
if include_evaluations:
|
if include_evaluations:
|
||||||
sco_cache.TableRecapWithEvalsCache.set(formsemestre.id, table_html)
|
table_html = sco_cache.TableRecapWithEvalsCache.get(formsemestre.id)
|
||||||
else:
|
else:
|
||||||
sco_cache.TableRecapCache.set(formsemestre.id, table_html)
|
table_html = sco_cache.TableRecapCache.get(formsemestre.id)
|
||||||
|
if modejury or (table_html is None):
|
||||||
|
table_html = _gen_formsemestre_recapcomplet_html(
|
||||||
|
formsemestre,
|
||||||
|
res,
|
||||||
|
include_evaluations,
|
||||||
|
modejury,
|
||||||
|
filename,
|
||||||
|
selected_etudid=selected_etudid,
|
||||||
|
)
|
||||||
|
if not modejury:
|
||||||
|
if include_evaluations:
|
||||||
|
sco_cache.TableRecapWithEvalsCache.set(formsemestre.id, table_html)
|
||||||
|
else:
|
||||||
|
sco_cache.TableRecapCache.set(formsemestre.id, table_html)
|
||||||
|
|
||||||
return table_html
|
return table_html
|
||||||
|
|
||||||
@ -425,11 +426,13 @@ def _gen_formsemestre_recapcomplet_html(
|
|||||||
formsemestre: FormSemestre,
|
formsemestre: FormSemestre,
|
||||||
res: NotesTableCompat,
|
res: NotesTableCompat,
|
||||||
include_evaluations=False,
|
include_evaluations=False,
|
||||||
|
modejury=False,
|
||||||
filename: str = "",
|
filename: str = "",
|
||||||
|
selected_etudid=None,
|
||||||
) -> str:
|
) -> str:
|
||||||
"""Génère le html"""
|
"""Génère le html"""
|
||||||
rows, footer_rows, titles, column_ids = res.get_table_recap(
|
rows, footer_rows, titles, column_ids = res.get_table_recap(
|
||||||
convert_values=True, include_evaluations=include_evaluations
|
convert_values=True, include_evaluations=include_evaluations, modejury=modejury
|
||||||
)
|
)
|
||||||
if not rows:
|
if not rows:
|
||||||
return (
|
return (
|
||||||
@ -437,7 +440,8 @@ def _gen_formsemestre_recapcomplet_html(
|
|||||||
)
|
)
|
||||||
H = [
|
H = [
|
||||||
f"""<div class="table_recap"><table class="table_recap {
|
f"""<div class="table_recap"><table class="table_recap {
|
||||||
'apc' if formsemestre.formation.is_apc() else 'classic'}"
|
'apc' if formsemestre.formation.is_apc() else 'classic'
|
||||||
|
} {'jury' if modejury else ''}"
|
||||||
data-filename="{filename}">"""
|
data-filename="{filename}">"""
|
||||||
]
|
]
|
||||||
# header
|
# header
|
||||||
@ -451,7 +455,7 @@ def _gen_formsemestre_recapcomplet_html(
|
|||||||
# body
|
# body
|
||||||
H.append("<tbody>")
|
H.append("<tbody>")
|
||||||
for row in rows:
|
for row in rows:
|
||||||
H.append(f"{_gen_row(column_ids, row)}\n")
|
H.append(f"{_gen_row(column_ids, row, selected_etudid=selected_etudid)}\n")
|
||||||
H.append("</tbody>\n")
|
H.append("</tbody>\n")
|
||||||
# footer
|
# footer
|
||||||
H.append("<tfoot>")
|
H.append("<tfoot>")
|
||||||
|
@ -1146,6 +1146,18 @@ span.jurylink a {
|
|||||||
text-decoration: underline;
|
text-decoration: underline;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
div.jury_footer {
|
||||||
|
display: flex;
|
||||||
|
justify-content: space-evenly;
|
||||||
|
}
|
||||||
|
|
||||||
|
div.jury_footer>span {
|
||||||
|
border: 2px solid rgb(90, 90, 90);
|
||||||
|
border-radius: 4px;
|
||||||
|
padding: 4px;
|
||||||
|
background-color: rgb(230, 242, 230);
|
||||||
|
}
|
||||||
|
|
||||||
.eval_description p {
|
.eval_description p {
|
||||||
margin-left: 15px;
|
margin-left: 15px;
|
||||||
margin-bottom: 2px;
|
margin-bottom: 2px;
|
||||||
|
@ -21,43 +21,54 @@ $(function () {
|
|||||||
dt.columns(".partition_aux").visible(!visible);
|
dt.columns(".partition_aux").visible(!visible);
|
||||||
dt.buttons('toggle_partitions:name').text(visible ? "Toutes les partitions" : "Cacher les partitions");
|
dt.buttons('toggle_partitions:name').text(visible ? "Toutes les partitions" : "Cacher les partitions");
|
||||||
}
|
}
|
||||||
},
|
}];
|
||||||
$('table.table_recap').hasClass("apc") ?
|
if (!$('table.table_recap').hasClass("jury")) {
|
||||||
{
|
buttons.push(
|
||||||
name: "toggle_res",
|
$('table.table_recap').hasClass("apc") ?
|
||||||
text: "Cacher les ressources",
|
{
|
||||||
action: function (e, dt, node, config) {
|
name: "toggle_res",
|
||||||
let visible = dt.columns(".col_res").visible()[0];
|
text: "Cacher les ressources",
|
||||||
dt.columns(".col_res").visible(!visible);
|
action: function (e, dt, node, config) {
|
||||||
dt.columns(".col_ue_bonus").visible(!visible);
|
let visible = dt.columns(".col_res").visible()[0];
|
||||||
dt.columns(".col_malus").visible(!visible);
|
dt.columns(".col_res").visible(!visible);
|
||||||
dt.buttons('toggle_res:name').text(visible ? "Montrer les ressources" : "Cacher les ressources");
|
dt.columns(".col_ue_bonus").visible(!visible);
|
||||||
|
dt.columns(".col_malus").visible(!visible);
|
||||||
|
dt.buttons('toggle_res:name').text(visible ? "Montrer les ressources" : "Cacher les ressources");
|
||||||
|
}
|
||||||
|
} : {
|
||||||
|
name: "toggle_mod",
|
||||||
|
text: "Cacher les modules",
|
||||||
|
action: function (e, dt, node, config) {
|
||||||
|
let visible = dt.columns(".col_mod:not(.col_empty)").visible()[0];
|
||||||
|
dt.columns(".col_mod:not(.col_empty)").visible(!visible);
|
||||||
|
dt.columns(".col_ue_bonus").visible(!visible);
|
||||||
|
dt.columns(".col_malus").visible(!visible);
|
||||||
|
dt.buttons('toggle_mod:name').text(visible ? "Montrer les modules" : "Cacher les modules");
|
||||||
|
visible = dt.columns(".col_empty").visible()[0];
|
||||||
|
dt.buttons('toggle_col_empty:name').text(visible ? "Cacher mod. vides" : "Montrer mod. vides");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
} : {
|
);
|
||||||
name: "toggle_mod",
|
if ($('table.table_recap').hasClass("apc")) {
|
||||||
text: "Cacher les modules",
|
buttons.push({
|
||||||
|
name: "toggle_sae",
|
||||||
|
text: "Cacher les SAÉs",
|
||||||
action: function (e, dt, node, config) {
|
action: function (e, dt, node, config) {
|
||||||
let visible = dt.columns(".col_mod:not(.col_empty)").visible()[0];
|
let visible = dt.columns(".col_sae").visible()[0];
|
||||||
dt.columns(".col_mod:not(.col_empty)").visible(!visible);
|
dt.columns(".col_sae").visible(!visible);
|
||||||
dt.columns(".col_ue_bonus").visible(!visible);
|
dt.buttons('toggle_sae:name').text(visible ? "Montrer les SAÉs" : "Cacher les SAÉs");
|
||||||
dt.columns(".col_malus").visible(!visible);
|
|
||||||
dt.buttons('toggle_mod:name').text(visible ? "Montrer les modules" : "Cacher les modules");
|
|
||||||
visible = dt.columns(".col_empty").visible()[0];
|
|
||||||
dt.buttons('toggle_col_empty:name').text(visible ? "Cacher mod. vides" : "Montrer mod. vides");
|
|
||||||
}
|
}
|
||||||
}
|
})
|
||||||
];
|
}
|
||||||
if ($('table.table_recap').hasClass("apc")) {
|
|
||||||
buttons.push({
|
buttons.push({
|
||||||
name: "toggle_sae",
|
name: "toggle_col_empty",
|
||||||
text: "Cacher les SAÉs",
|
text: "Montrer mod. vides",
|
||||||
action: function (e, dt, node, config) {
|
action: function (e, dt, node, config) {
|
||||||
let visible = dt.columns(".col_sae").visible()[0];
|
let visible = dt.columns(".col_empty").visible()[0];
|
||||||
dt.columns(".col_sae").visible(!visible);
|
dt.columns(".col_empty").visible(!visible);
|
||||||
dt.buttons('toggle_sae:name').text(visible ? "Montrer les SAÉs" : "Cacher les SAÉs");
|
dt.buttons('toggle_col_empty:name').text(visible ? "Montrer mod. vides" : "Cacher mod. vides");
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
|
|
||||||
}
|
}
|
||||||
buttons.push({
|
buttons.push({
|
||||||
name: "toggle_admission",
|
name: "toggle_admission",
|
||||||
@ -68,15 +79,6 @@ $(function () {
|
|||||||
dt.buttons('toggle_admission:name').text(visible ? "Montrer infos admission" : "Cacher infos admission");
|
dt.buttons('toggle_admission:name').text(visible ? "Montrer infos admission" : "Cacher infos admission");
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
buttons.push({
|
|
||||||
name: "toggle_col_empty",
|
|
||||||
text: "Montrer mod. vides",
|
|
||||||
action: function (e, dt, node, config) {
|
|
||||||
let visible = dt.columns(".col_empty").visible()[0];
|
|
||||||
dt.columns(".col_empty").visible(!visible);
|
|
||||||
dt.buttons('toggle_col_empty:name').text(visible ? "Montrer mod. vides" : "Cacher mod. vides");
|
|
||||||
}
|
|
||||||
})
|
|
||||||
$('table.table_recap').DataTable(
|
$('table.table_recap').DataTable(
|
||||||
{
|
{
|
||||||
paging: false,
|
paging: false,
|
||||||
@ -143,4 +145,10 @@ $(function () {
|
|||||||
$(this).addClass('selected');
|
$(this).addClass('selected');
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
// Pour montrer et highlihter l'étudiant sélectionné:
|
||||||
|
$(function () {
|
||||||
|
document.querySelector("#row_selected").scrollIntoView();
|
||||||
|
window.scrollBy(0, -50);
|
||||||
|
document.querySelector("#row_selected").classList.add("selected");
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
Loading…
Reference in New Issue
Block a user