From eb88a8ca83aab5a1747cf144d62163b4d2f5dd30 Mon Sep 17 00:00:00 2001 From: Iziram Date: Mon, 27 May 2024 17:59:34 +0200 Subject: [PATCH 1/9] =?UTF-8?q?[WIP]=20Assiduit=C3=A9=20:=20saisie=5Fassid?= =?UTF-8?q?uites=5Fhebdo?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../pages/signal_assiduites_hebdo.j2 | 212 ++++++++++++++++++ app/views/assiduites.py | 101 +++++++++ 2 files changed, 313 insertions(+) create mode 100644 app/templates/assiduites/pages/signal_assiduites_hebdo.j2 diff --git a/app/templates/assiduites/pages/signal_assiduites_hebdo.j2 b/app/templates/assiduites/pages/signal_assiduites_hebdo.j2 new file mode 100644 index 000000000..6bab7673a --- /dev/null +++ b/app/templates/assiduites/pages/signal_assiduites_hebdo.j2 @@ -0,0 +1,212 @@ +{% extends "sco_page.j2" %} + +{% block styles %} +{{ super() }} + + + + +{% endblock styles %} + +{% block scripts %} +{{ super() }} + + + +{% include "sco_timepicker.j2" %} + + + + +{% endblock scripts %} + +{% block title %} +{{ title }} +{% endblock title %} + +{% block app_content %} + +

Signalement hebdomadaire de l'assiduité {{ gr | safe }}

+
+
+ + + +
+ +

+ Le matin 9h à 12h et l'après-midi de 13h à 17h +

+ + + + + + + + + + + + + + + + + + + + + + + + + + {% for etud in etudiants %} + + + {# à changer par jour travaillés (sco pref) #} + {% for day in ['lundi', 'mardi', 'mercredi', 'jeudi', 'vendredi'] %} + + + {% endfor %} + + {% endfor %} + +
ÉtudiantsLundiMardiMercrediJeudiVendredi
MatinAprès-midiMatinAprès-midiMatinAprès-midiMatinAprès-midiMatinAprès-midi
{{ etud.nomprenom }} + + + + + + + +
+ +{% include "assiduites/widgets/alert.j2" %} +{% endblock app_content %} \ No newline at end of file diff --git a/app/views/assiduites.py b/app/views/assiduites.py index f5ffe223f..4fb66a7fe 100644 --- a/app/views/assiduites.py +++ b/app/views/assiduites.py @@ -1987,6 +1987,107 @@ def traitement_justificatifs(): ) +@bp.route("signal_assiduites_hebdo") +@scodoc +@permission_required(Permission.AbsChange) +def signal_assiduites_hebdo(): + """ + signal_assiduites_hebdo + + paramètres obligatoires : + - formsemestre_id : id du formsemestre + - semaine : date semaine (iso 8601 -> 20XX-WXX) + - groups_id : id des groupes (séparés par des virgules -> 1,2,3) + + paramètres optionnels : + - moduleimpl_id : id du moduleimpl (par défaut None) + """ + + # Récupération des paramètres + moduleimpl_id: int = request.args.get("moduleimpl_id", None) + semaine: str = request.args.get("semaine", None) + group_ids: list[int] = request.args.get("group_ids", None) + formsemestre_id: int = request.args.get("formsemestre_id", -1) + + # Vérification des paramètres + if semaine is None or group_ids is None or formsemestre_id is None: + raise ScoValueError("Paramètres manquants", dest_url=request.referrer) + + # Récupération du moduleimpl + moduleimpl: ModuleImpl | None = ModuleImpl.query.get(moduleimpl_id) + module_text: str = "Non spécifié" + if moduleimpl is not None: + module_text = f"{moduleimpl.code} {moduleimpl.titre}" + else: + if moduleimpl_id == "autre": + module_text = "Autre module (pas dans la liste)" + moduleimpl_id = None if moduleimpl_id != "autre" else moduleimpl_id + + # Récupération du formsemestre + formsemestre: FormSemestre = FormSemestre.get_formsemestre(formsemestre_id) + + # vérification semaine dans format iso 8601 et formsemestre + try: + lundi_semaine = datetime.datetime.strptime(semaine + "-1", "%G-W%V-%u") + if ( + lundi_semaine.date() < formsemestre.date_debut + or lundi_semaine.date() > formsemestre.date_fin + ): + raise ScoValueError( + "Semaine en dehors du semestre", dest_url=request.referrer + ) + + except (ValueError, TypeError) as exc: + raise ScoValueError("Semaine invalide", dest_url=request.referrer) from exc + except ScoValueError as exc: + raise exc + + etudiants: list[Identite] = [] + + # Vérification des groupes + if group_ids is None: + group_ids = [] + else: + group_ids = group_ids.split(",") + map(str, group_ids) + groups_infos = sco_groups_view.DisplayedGroupsInfos( + group_ids, formsemestre_id=formsemestre.id, select_all_when_unspecified=True + ) + if not groups_infos.members: + return ( + html_sco_header.sco_header(page_title="Assiduité: saisie hébdomadaire") + + "

Aucun étudiant !

" + + html_sco_header.sco_footer() + ) + + # Récupération des étudiants + etudiants.extend( + [Identite.get_etud(etudid=m["etudid"]) for m in groups_infos.members] + ) + etudiants = list(sorted(etudiants, key=lambda etud: etud.sort_key)) + + if groups_infos.tous_les_etuds_du_sem: + gr_tit = "en" + else: + if len(groups_infos.group_ids) > 1: + grp = "des groupes" + else: + grp = "du groupe" + gr_tit = ( + grp + ' ' + groups_infos.groups_titles + "" + ) + + return render_template( + "assiduites/pages/signal_assiduites_hebdo.j2", + gr=gr_tit, + module=module_text, + etudiants=etudiants, + moduleimpl_select=_module_selector( + formsemestre=formsemestre, moduleimpl_id=moduleimpl_id + ), + ) + + def generate_bul_list(etud: Identite, semestre: FormSemestre) -> str: """Génère la liste des assiduités d'un étudiant pour le bulletin mail""" From f94998f66b7a48118dc89c32070ad7a7cc6d6626 Mon Sep 17 00:00:00 2001 From: Iziram Date: Mon, 27 May 2024 22:33:01 +0200 Subject: [PATCH 2/9] =?UTF-8?q?[WIP]=20Assiduit=C3=A9=20:=20corrections=20?= =?UTF-8?q?saisie=5Fassiduites=5Fhebdo?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../pages/signal_assiduites_hebdo.j2 | 15 +--- app/views/assiduites.py | 72 +++++++++---------- 2 files changed, 35 insertions(+), 52 deletions(-) diff --git a/app/templates/assiduites/pages/signal_assiduites_hebdo.j2 b/app/templates/assiduites/pages/signal_assiduites_hebdo.j2 index 6bab7673a..5a000d6dd 100644 --- a/app/templates/assiduites/pages/signal_assiduites_hebdo.j2 +++ b/app/templates/assiduites/pages/signal_assiduites_hebdo.j2 @@ -57,14 +57,10 @@ text-align: center; } - #tableau-periode { - overflow-x: auto; - max-width: 100%; - } - table { border-collapse: collapse; width: 100%; + max-width: 1600px; position: relative; } @@ -99,7 +95,7 @@ z-index: 1; } - td.active>.rbtn:not(:checked)::before { + .rbtn:not(:checked)::before { opacity: 0.5; } @@ -128,13 +124,6 @@ input.checked = false; } }); - - if(!target.checked && parent.classList.contains("active")){ - parent.classList.remove("active"); - }else{ - parent.classList.add("active"); - } - }); }); diff --git a/app/views/assiduites.py b/app/views/assiduites.py index 4fb66a7fe..2dcfec2ef 100644 --- a/app/views/assiduites.py +++ b/app/views/assiduites.py @@ -1989,82 +1989,75 @@ def traitement_justificatifs(): @bp.route("signal_assiduites_hebdo") @scodoc -@permission_required(Permission.AbsChange) +@permission_required(Permission.ScoView) def signal_assiduites_hebdo(): """ signal_assiduites_hebdo paramètres obligatoires : - formsemestre_id : id du formsemestre - - semaine : date semaine (iso 8601 -> 20XX-WXX) + - week : date semaine (iso 8601 -> 20XX-WXX) - groups_id : id des groupes (séparés par des virgules -> 1,2,3) paramètres optionnels : - moduleimpl_id : id du moduleimpl (par défaut None) + + + Permissions : + - ScoView -> page en lecture seule + - AbsChange -> page en lecture/écriture """ # Récupération des paramètres moduleimpl_id: int = request.args.get("moduleimpl_id", None) - semaine: str = request.args.get("semaine", None) - group_ids: list[int] = request.args.get("group_ids", None) + week: str = request.args.get("week", None) + group_ids: str = request.args.get("group_ids", "") # ex: "1,2,3" formsemestre_id: int = request.args.get("formsemestre_id", -1) # Vérification des paramètres - if semaine is None or group_ids is None or formsemestre_id is None: + if week is None or group_ids == "" or formsemestre_id == -1: raise ScoValueError("Paramètres manquants", dest_url=request.referrer) # Récupération du moduleimpl - moduleimpl: ModuleImpl | None = ModuleImpl.query.get(moduleimpl_id) - module_text: str = "Non spécifié" - if moduleimpl is not None: - module_text = f"{moduleimpl.code} {moduleimpl.titre}" - else: - if moduleimpl_id == "autre": - module_text = "Autre module (pas dans la liste)" - moduleimpl_id = None if moduleimpl_id != "autre" else moduleimpl_id + try: + moduleimpl_id: int = int(moduleimpl_id) + except (ValueError, TypeError): + moduleimpl_id: str | None = None if moduleimpl_id != "autre" else moduleimpl_id # Récupération du formsemestre formsemestre: FormSemestre = FormSemestre.get_formsemestre(formsemestre_id) - # vérification semaine dans format iso 8601 et formsemestre - try: - lundi_semaine = datetime.datetime.strptime(semaine + "-1", "%G-W%V-%u") - if ( - lundi_semaine.date() < formsemestre.date_debut - or lundi_semaine.date() > formsemestre.date_fin - ): - raise ScoValueError( - "Semaine en dehors du semestre", dest_url=request.referrer - ) + # Vérification semaine dans format iso 8601 et formsemestre + regex_iso8601 = r"^\d{4}-W\d{2}$" + if not re.match(regex_iso8601, week): + raise ScoValueError("Semaine invalide", dest_url=request.referrer) - except (ValueError, TypeError) as exc: - raise ScoValueError("Semaine invalide", dest_url=request.referrer) from exc - except ScoValueError as exc: - raise exc + fs_deb_iso8601 = formsemestre.date_debut.strftime("%Y-W%W") + fs_fin_iso8601 = formsemestre.date_fin.strftime("%Y-W%W") - etudiants: list[Identite] = [] + # Utilisation de la propriété de la norme iso 8601 + # les chaines sont triables par ordre alphanumérique croissant + # et produiront le même ordre que les dates par ordre chronologique croissant + if week < fs_deb_iso8601 or week > fs_fin_iso8601: + raise ScoValueError("Semaine hors du semestre", dest_url=request.referrer) # Vérification des groupes - if group_ids is None: - group_ids = [] - else: - group_ids = group_ids.split(",") - map(str, group_ids) + group_ids = group_ids.split(",") if group_ids != "" else [] + groups_infos = sco_groups_view.DisplayedGroupsInfos( group_ids, formsemestre_id=formsemestre.id, select_all_when_unspecified=True ) if not groups_infos.members: return ( - html_sco_header.sco_header(page_title="Assiduité: saisie hébdomadaire") + html_sco_header.sco_header(page_title="Assiduité: saisie hebdomadaire") + "

Aucun étudiant !

" + html_sco_header.sco_footer() ) # Récupération des étudiants - etudiants.extend( - [Identite.get_etud(etudid=m["etudid"]) for m in groups_infos.members] - ) - etudiants = list(sorted(etudiants, key=lambda etud: etud.sort_key)) + etudiants: list[Identite] = [ + Identite.get_etud(etudid=m["etudid"]) for m in groups_infos.members + ] if groups_infos.tous_les_etuds_du_sem: gr_tit = "en" @@ -2077,10 +2070,11 @@ def signal_assiduites_hebdo(): grp + ' ' + groups_infos.groups_titles + "" ) + # TODO vérif perm AbsChange -> readonly + return render_template( "assiduites/pages/signal_assiduites_hebdo.j2", gr=gr_tit, - module=module_text, etudiants=etudiants, moduleimpl_select=_module_selector( formsemestre=formsemestre, moduleimpl_id=moduleimpl_id From ab9543c310d969ee3d9b40dc81e0bdc858d3a1c1 Mon Sep 17 00:00:00 2001 From: Iziram Date: Mon, 27 May 2024 23:26:13 +0200 Subject: [PATCH 3/9] =?UTF-8?q?[WIP]=20Assiduit=C3=A9=20:=20signal=5Fassid?= =?UTF-8?q?uites=5Fhebdo=20:=20choix=20horaires?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../pages/signal_assiduites_hebdo.j2 | 169 +++++++++++++++++- 1 file changed, 168 insertions(+), 1 deletion(-) diff --git a/app/templates/assiduites/pages/signal_assiduites_hebdo.j2 b/app/templates/assiduites/pages/signal_assiduites_hebdo.j2 index 5a000d6dd..f819d3187 100644 --- a/app/templates/assiduites/pages/signal_assiduites_hebdo.j2 +++ b/app/templates/assiduites/pages/signal_assiduites_hebdo.j2 @@ -100,6 +100,65 @@ } + + + {% endblock styles %} @@ -113,6 +172,24 @@ + + {% endblock scripts %} @@ -149,7 +299,7 @@

- Le matin 9h à 12h et l'après-midi de 13h à 17h + Le matin 9h à 12h et l'après-midi de 13h à 17h

@@ -197,5 +347,22 @@
+
+
+ × +

Choisissez les horaires

+
+ + +
+
+ + +
+ + +
+
+ {% include "assiduites/widgets/alert.j2" %} {% endblock app_content %} \ No newline at end of file From dea403b03d51b37d76bcde5205c3782ffea5db34 Mon Sep 17 00:00:00 2001 From: Iziram Date: Tue, 28 May 2024 09:51:40 +0200 Subject: [PATCH 4/9] =?UTF-8?q?Assiduit=C3=A9=20:=20signal=5Fassiduites=5F?= =?UTF-8?q?hebdo=20:=20verif=20heure=20matin=20<=20aprem?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/templates/assiduites/pages/signal_assiduites_hebdo.j2 | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/app/templates/assiduites/pages/signal_assiduites_hebdo.j2 b/app/templates/assiduites/pages/signal_assiduites_hebdo.j2 index f819d3187..874f463b4 100644 --- a/app/templates/assiduites/pages/signal_assiduites_hebdo.j2 +++ b/app/templates/assiduites/pages/signal_assiduites_hebdo.j2 @@ -250,9 +250,17 @@ function openModal(morning = true){ } if (morning){ + if (fin > temps.apresmidi.debut){ + alert("L'heure de fin du matin doit être inférieure à l'heure de début de l'après-midi"); + return; + } temps.matin.debut = debut; temps.matin.fin = fin; } else { + if (debut < temps.matin.fin){ + alert("L'heure de début de l'après-midi doit être supérieure à l'heure de fin du matin"); + return; + } temps.apresmidi.debut = debut; temps.apresmidi.fin = fin; } From d73b92500672b7c93422f1930ab693606f8a0286 Mon Sep 17 00:00:00 2001 From: Iziram Date: Tue, 28 May 2024 20:07:25 +0200 Subject: [PATCH 5/9] =?UTF-8?q?Assiduit=C3=A9=20:=20signal=5Fassiduites=5F?= =?UTF-8?q?hedbo=20:=20v1=20OK?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/static/js/date_utils.js | 20 + .../pages/signal_assiduites_hebdo.j2 | 445 ++++++++++++++++-- app/views/assiduites.py | 40 ++ 3 files changed, 462 insertions(+), 43 deletions(-) diff --git a/app/static/js/date_utils.js b/app/static/js/date_utils.js index 0db9d3b0f..efdc120e7 100644 --- a/app/static/js/date_utils.js +++ b/app/static/js/date_utils.js @@ -430,3 +430,23 @@ class Duration { function hasTimeConflict(period, interval) { return period.deb.isBefore(interval.fin) && period.fin.isAfter(interval.deb); } + +// Fonction auxiliaire pour obtenir le numéro de semaine ISO d'une date donnée +function getISOWeek(date) { + const target = new Date(date.valueOf()); + const dayNr = (date.getUTCDay() + 6) % 7; + target.setUTCDate(target.getUTCDate() - dayNr + 3); + const firstThursday = target.valueOf(); + target.setUTCMonth(0, 1); + if (target.getUTCDay() !== 4) { + target.setUTCMonth(0, 1 + ((4 - target.getUTCDay() + 7) % 7)); + } + return 1 + Math.ceil((firstThursday - target) / 604800000); +} + +// Fonction auxiliaire pour obtenir le nombre de semaines ISO dans une année donnée +function getISOWeeksInYear(year) { + const date = new Date(year, 11, 31); + const week = getISOWeek(date); + return week === 1 ? getISOWeek(new Date(year, 11, 24)) : week; +} diff --git a/app/templates/assiduites/pages/signal_assiduites_hebdo.j2 b/app/templates/assiduites/pages/signal_assiduites_hebdo.j2 index 874f463b4..5b2a7f28f 100644 --- a/app/templates/assiduites/pages/signal_assiduites_hebdo.j2 +++ b/app/templates/assiduites/pages/signal_assiduites_hebdo.j2 @@ -7,8 +7,9 @@ @@ -159,6 +168,10 @@ #confirmButton:hover { background-color: var(--color-secondary); } + +.etudinfo{ + text-align: left; +} {% endblock styles %} @@ -172,37 +185,359 @@ + + + + {% endblock scripts %} {% block title %} @@ -298,48 +642,63 @@ document.addEventListener("DOMContentLoaded", ()=>{

Signalement hebdomadaire de l'assiduité {{ gr | safe }}


- + - +

Le matin 9h à 12h et l'après-midi de 13h à 17h

- +
- - - - - + + {% for jour in hebdo_jours %} + + {% if not jour[0] or jour[1][0] not in ['Samedi', 'Dimanche'] %} + + {% endif %} + + {% endfor %} - - - - - - - - - - + {% for jour in hebdo_jours %} + + {% if not jour[0] or jour[1][0] not in ['Samedi', 'Dimanche'] %} + + + {% endif %} + {% endfor %} + + + {# Ne pas afficher si preference "non presences" #} + + {% for jour in hebdo_jours %} + {% if not jour[0] or jour[1][0] not in ['Samedi', 'Dimanche'] %} + + + {% endif %} + {% endfor %} + {% for etud in etudiants %} - + - {# à changer par jour travaillés (sco pref) #} - {% for day in ['lundi', 'mardi', 'mercredi', 'jeudi', 'vendredi'] %} - - {% endfor %} + #} {% endfor %} @@ -373,4 +731,5 @@ document.addEventListener("DOMContentLoaded", ()=>{ {% include "assiduites/widgets/alert.j2" %} +{% include "assiduites/widgets/toast.j2" %} {% endblock app_content %} \ No newline at end of file diff --git a/app/views/assiduites.py b/app/views/assiduites.py index 2dcfec2ef..f84330b64 100644 --- a/app/views/assiduites.py +++ b/app/views/assiduites.py @@ -2072,6 +2072,45 @@ def signal_assiduites_hebdo(): # TODO vérif perm AbsChange -> readonly + # Gestion des jours + jours: dict[str, list[str]] = { + "lun": [ + "Lundi", + datetime.datetime.strptime(week + "-1", "%G-W%V-%u").strftime("%d/%m/%Y"), + ], + "mar": [ + "Mardi", + datetime.datetime.strptime(week + "-2", "%G-W%V-%u").strftime("%d/%m/%Y"), + ], + "mer": [ + "Mercredi", + datetime.datetime.strptime(week + "-3", "%G-W%V-%u").strftime("%d/%m/%Y"), + ], + "jeu": [ + "Jeudi", + datetime.datetime.strptime(week + "-4", "%G-W%V-%u").strftime("%d/%m/%Y"), + ], + "ven": [ + "Vendredi", + datetime.datetime.strptime(week + "-5", "%G-W%V-%u").strftime("%d/%m/%Y"), + ], + "sam": [ + "Samedi", + datetime.datetime.strptime(week + "-6", "%G-W%V-%u").strftime("%d/%m/%Y"), + ], + "dim": [ + "Dimanche", + datetime.datetime.strptime(week + "-7", "%G-W%V-%u").strftime("%d/%m/%Y"), + ], + } + + non_travail = sco_preferences.get_preference("non_travail") + non_travail = non_travail.replace(" ", "").split(",") + + hebdo_jours: list[tuple[bool, str]] = [] + for key, val in jours.items(): + hebdo_jours.append((key in non_travail, val)) + return render_template( "assiduites/pages/signal_assiduites_hebdo.j2", gr=gr_tit, @@ -2079,6 +2118,7 @@ def signal_assiduites_hebdo(): moduleimpl_select=_module_selector( formsemestre=formsemestre, moduleimpl_id=moduleimpl_id ), + hebdo_jours=hebdo_jours, ) From f4f6c13d79975b597333b629798d8e5ed24885ec Mon Sep 17 00:00:00 2001 From: Iziram Date: Wed, 29 May 2024 15:59:19 +0200 Subject: [PATCH 6/9] =?UTF-8?q?Assiduit=C3=A9=20:=20signal=5Fassiduites=5F?= =?UTF-8?q?hebdo=20:=20v2=20sans=20mobile?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/static/js/assiduites.js | 15 +- .../pages/signal_assiduites_hebdo.j2 | 205 +++++++++++++++--- app/views/assiduites.py | 9 +- 3 files changed, 197 insertions(+), 32 deletions(-) diff --git a/app/static/js/assiduites.js b/app/static/js/assiduites.js index a9ded03c8..089469eb0 100644 --- a/app/static/js/assiduites.js +++ b/app/static/js/assiduites.js @@ -68,7 +68,13 @@ async function async_post(path, data, success, errors) { const responseData = await response.json(); success(responseData); } else { - throw new Error("Network response was not ok."); + if (response.status == 404) { + response.json().then((data) => { + if (errors) errors(data); + }); + } else { + throw new Error("Network response was not ok."); + } } } catch (error) { console.error(error); @@ -615,7 +621,10 @@ function erreurModuleImpl(message) { openAlertModal("Sélection du module", content); } - if (message == "L'étudiant n'est pas inscrit au module") { + if ( + message == "L'étudiant n'est pas inscrit au module" || + message == "param 'moduleimpl_id': etud non inscrit" + ) { const HTML = `

Attention, l'étudiant n'est pas inscrit à ce module.

Si c'est une erreur, veuillez voir avec le ou les responsables de votre scodoc.

@@ -822,7 +831,7 @@ function dateCouranteEstTravaillee() { const nouvelleDate = retourJourTravail(date); $("#date").datepicker("setDate", nouvelleDate); let msg = "Le jour sélectionné"; - if ((new Date()).format("YYYY-MM-DD") == date.format("YYYY-MM-DD")) { + if (new Date().format("YYYY-MM-DD") == date.format("YYYY-MM-DD")) { msg = "Aujourd'hui"; } const att = document.createTextNode( diff --git a/app/templates/assiduites/pages/signal_assiduites_hebdo.j2 b/app/templates/assiduites/pages/signal_assiduites_hebdo.j2 index 5b2a7f28f..09a0e750b 100644 --- a/app/templates/assiduites/pages/signal_assiduites_hebdo.j2 +++ b/app/templates/assiduites/pages/signal_assiduites_hebdo.j2 @@ -108,6 +108,11 @@ background-color: var(--color-conflit); } + .conflit_calendar{ + font-size: 1.5em; + cursor: pointer; + } + @@ -185,6 +190,9 @@ @@ -654,6 +795,15 @@ document.addEventListener("DOMContentLoaded", ()=>{ Le matin 9h à 12h et l'après-midi de 13h à 17h +{% if readonly %} +

+ Ouvert en mode lecture seule. +

+ +{% endif %}
ÉtudiantsLundiMardiMercrediJeudiVendredi{{ jour[1][0] }} {{jour[1][1] }}
MatinAprès-midiMatinAprès-midiMatinAprès-midiMatinAprès-midiMatinAprès-midiMatinAprès-midi
+ + + +
{{ etud.nomprenom }} + {# Sera rempli en JS #} + {# Ne pas afficher bouton présent si pref "non présences" #} + {# @@ -348,8 +707,7 @@ document.addEventListener("DOMContentLoaded", ()=>{ -
@@ -676,8 +826,9 @@ document.addEventListener("DOMContentLoaded", ()=>{ {% endif %} {% endfor %} + {% if not readonly and not non_present %} - {# Ne pas afficher si preference "non presences" #} + {# Ne pas afficher si preference "non presences" / "readonly" #} {% for jour in hebdo_jours %} {% if not jour[0] or jour[1][0] not in ['Samedi', 'Dimanche'] %} @@ -689,13 +840,13 @@ document.addEventListener("DOMContentLoaded", ()=>{ {% endif %} {% endfor %} - + {% endif %} {% for etud in etudiants %} - + {# Sera rempli en JS #} {# Ne pas afficher bouton présent si pref "non présences" #} {#
{{ etud.nomprenom }}{{ etud.nom_prenom() }} diff --git a/app/views/assiduites.py b/app/views/assiduites.py index f84330b64..99ce6ab6f 100644 --- a/app/views/assiduites.py +++ b/app/views/assiduites.py @@ -2070,8 +2070,6 @@ def signal_assiduites_hebdo(): grp + ' ' + groups_infos.groups_titles + "" ) - # TODO vérif perm AbsChange -> readonly - # Gestion des jours jours: dict[str, list[str]] = { "lun": [ @@ -2113,12 +2111,19 @@ def signal_assiduites_hebdo(): return render_template( "assiduites/pages/signal_assiduites_hebdo.j2", + title="Assiduité: saisie hebdomadaire", gr=gr_tit, etudiants=etudiants, moduleimpl_select=_module_selector( formsemestre=formsemestre, moduleimpl_id=moduleimpl_id ), hebdo_jours=hebdo_jours, + readonly=not current_user.has_permission(Permission.AbsChange), + non_present=sco_preferences.get_preference( + "non_present", + formsemestre_id=formsemestre_id, + dept_id=g.scodoc_dept_id, + ), ) From f275286b712232d220980737e733a7c99a897f0a Mon Sep 17 00:00:00 2001 From: Iziram Date: Wed, 29 May 2024 16:29:34 +0200 Subject: [PATCH 7/9] =?UTF-8?q?Assiduit=C3=A9=20:=20liens=20saisie=20hebdo?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/scodoc/sco_formsemestre_status.py | 23 ++++++++++++++++++++++- app/scodoc/sco_groups_view.py | 12 ++++++------ app/scodoc/sco_moduleimpl_status.py | 22 +++++++++++++++++++--- 3 files changed, 47 insertions(+), 10 deletions(-) diff --git a/app/scodoc/sco_formsemestre_status.py b/app/scodoc/sco_formsemestre_status.py index 0d7686ec8..02a0738a1 100755 --- a/app/scodoc/sco_formsemestre_status.py +++ b/app/scodoc/sco_formsemestre_status.py @@ -838,6 +838,27 @@ def _make_listes_sem(formsemestre: FormSemestre) -> str: )}"> Saisir l'assiduité + """ + ) + # YYYY-Www (ISO 8601) : + current_week: str = datetime.datetime.now().strftime("%G-W%V") + H.append( + f""" + + """ + ) + if can_edit_abs: + H.append( + f""" - """ + """ ) H.append( f""" diff --git a/app/scodoc/sco_groups_view.py b/app/scodoc/sco_groups_view.py index 0ebed4727..80454b435 100644 --- a/app/scodoc/sco_groups_view.py +++ b/app/scodoc/sco_groups_view.py @@ -26,7 +26,7 @@ ############################################################################## """Affichage étudiants d'un ou plusieurs groupes - sous forme: de liste html (table exportable), de trombinoscope (exportable en pdf) +sous forme: de liste html (table exportable), de trombinoscope (exportable en pdf) """ # Re-ecriture en 2014 (re-organisation de l'interface, modernisation du code) @@ -585,8 +585,8 @@ def groups_table( etud_info["_nom_disp_order"] = etud_sort_key(etud_info) etud_info["_prenom_target"] = fiche_url - etud_info["_nom_disp_td_attrs"] = 'id="%s" class="etudinfo"' % ( - etud_info["etudid"] + etud_info["_nom_disp_td_attrs"] = ( + 'id="%s" class="etudinfo"' % (etud_info["etudid"]) ) etud_info["bourse_str"] = "oui" if etud_info["boursier"] else "non" if etud_info["etat"] == "D": @@ -998,12 +998,12 @@ def form_choix_saisie_semaine(groups_infos): return "" query_args = parse_qs(request.query_string) moduleimpl_id = query_args.get("moduleimpl_id", [None])[0] - semaine = datetime.date.today().isocalendar().week + semaine = datetime.datetime.now().strftime("%G-W%V") return f"""