ue.titre peut être null + formattage code

This commit is contained in:
Emmanuel Viennet 2024-02-13 13:55:16 +01:00
parent 607604f91e
commit a200be586a
14 changed files with 160 additions and 129 deletions

View File

@ -256,7 +256,7 @@ def _gen_but_niveau_ue(
return f"""<div class="but_niveau_ue {ue_class}
{'annee_prec' if annee_prec else ''}
">
<div title="{ue.titre}">{ue.acronyme}</div>
<div title="{ue.titre or ''}">{ue.acronyme}</div>
<div class="but_note with_scoplement">
<div>{moy_ue_str}</div>
{scoplement}

View File

@ -487,7 +487,6 @@ def arret_de_formation(etud: Identite, cosemestres: list[FormSemestre]) -> bool:
TODO:: A reprendre pour le cas des étudiants à l'étranger
TODO:: A reprendre si BUT avec semestres décalés
"""
# Les semestres APC de l'étudiant
semestres = get_semestres_apc(etud)
semestres_apc = {sem.semestre_id: sem for sem in semestres}

View File

@ -126,53 +126,59 @@ def html_edit_formation_apc(
UniteEns.type != codes_cursus.UE_SPORT,
).first()
H += [
render_template(
"pn/form_mods.j2",
formation=formation,
titre=f"Ressources du S{semestre_idx}",
create_element_msg="créer une nouvelle ressource",
# matiere_parent=matiere_parent,
modules=ressources_in_sem,
module_type=ModuleType.RESSOURCE,
editable=editable,
tag_editable=tag_editable,
icons=icons,
scu=scu,
semestre_id=semestre_idx,
)
if ues_by_sem[semestre_idx].count() > 0
else "",
render_template(
"pn/form_mods.j2",
formation=formation,
titre=f"Situations d'Apprentissage et d'Évaluation (SAÉs) S{semestre_idx}",
create_element_msg="créer une nouvelle SAÉ",
# matiere_parent=matiere_parent,
modules=saes_in_sem,
module_type=ModuleType.SAE,
editable=editable,
tag_editable=tag_editable,
icons=icons,
scu=scu,
semestre_id=semestre_idx,
)
if ues_by_sem[semestre_idx].count() > 0
else "",
render_template(
"pn/form_mods.j2",
formation=formation,
titre=f"Autres modules (non BUT) du S{semestre_idx}",
create_element_msg="créer un nouveau module",
modules=other_modules_in_sem,
module_type=ModuleType.STANDARD,
editable=editable,
tag_editable=tag_editable,
icons=icons,
scu=scu,
semestre_id=semestre_idx,
)
if ues_by_sem[semestre_idx].count() > 0
else """<span class="fontred">créer une UE pour pouvoir ajouter des modules</span>""",
(
render_template(
"pn/form_mods.j2",
formation=formation,
titre=f"Ressources du S{semestre_idx}",
create_element_msg="créer une nouvelle ressource",
# matiere_parent=matiere_parent,
modules=ressources_in_sem,
module_type=ModuleType.RESSOURCE,
editable=editable,
tag_editable=tag_editable,
icons=icons,
scu=scu,
semestre_id=semestre_idx,
)
if ues_by_sem[semestre_idx].count() > 0
else ""
),
(
render_template(
"pn/form_mods.j2",
formation=formation,
titre=f"Situations d'Apprentissage et d'Évaluation (SAÉs) S{semestre_idx}",
create_element_msg="créer une nouvelle SAÉ",
# matiere_parent=matiere_parent,
modules=saes_in_sem,
module_type=ModuleType.SAE,
editable=editable,
tag_editable=tag_editable,
icons=icons,
scu=scu,
semestre_id=semestre_idx,
)
if ues_by_sem[semestre_idx].count() > 0
else ""
),
(
render_template(
"pn/form_mods.j2",
formation=formation,
titre=f"Autres modules (non BUT) du S{semestre_idx}",
create_element_msg="créer un nouveau module",
modules=other_modules_in_sem,
module_type=ModuleType.STANDARD,
editable=editable,
tag_editable=tag_editable,
icons=icons,
scu=scu,
semestre_id=semestre_idx,
)
if ues_by_sem[semestre_idx].count() > 0
else """<span class="fontred">créer une UE pour pouvoir ajouter des modules</span>"""
),
]
return "\n".join(H)
@ -202,7 +208,7 @@ def html_ue_infos(ue):
)
return render_template(
"pn/ue_infos.j2",
titre=f"UE {ue.acronyme} {ue.titre}",
titre=f"UE {ue.acronyme} {ue.titre or ''}",
ue=ue,
formsemestres=formsemestres,
nb_etuds_valid_ue=nb_etuds_valid_ue,

View File

@ -104,7 +104,7 @@ def matiere_create(ue_id=None):
default_numero = max([mat.numero for mat in ue.matieres] or [9]) + 1
H = [
html_sco_header.sco_header(page_title="Création d'une matière"),
f"""<h2>Création d'une matière dans l'UE {ue.titre} ({ue.acronyme})</h2>
f"""<h2>Création d'une matière dans l'UE {ue.titre or ''} ({ue.acronyme})</h2>
<p class="help">Les matières sont des groupes de modules dans une UE
d'une formation donnée. Les matières servent surtout pour la
présentation (bulletins, etc) mais <em>n'ont pas de rôle dans le calcul

View File

@ -85,7 +85,7 @@ _moduleEditor = ndb.EditableTable(
"heures_tp": ndb.float_null_is_zero,
"numero": ndb.int_null_is_zero,
"coefficient": ndb.float_null_is_zero,
"module_type": ndb.int_null_is_zero
"module_type": ndb.int_null_is_zero,
#'ects' : ndb.float_null_is_null
},
)
@ -387,14 +387,16 @@ def module_edit(
"scodoc/help/modules.j2",
is_apc=is_apc,
semestre_id=semestre_id,
formsemestres=FormSemestre.query.filter(
ModuleImpl.formsemestre_id == FormSemestre.id,
ModuleImpl.module_id == module_id,
)
.order_by(FormSemestre.date_debut)
.all()
if not create
else None,
formsemestres=(
FormSemestre.query.filter(
ModuleImpl.formsemestre_id == FormSemestre.id,
ModuleImpl.module_id == module_id,
)
.order_by(FormSemestre.date_debut)
.all()
if not create
else None
),
create=create,
),
]
@ -413,9 +415,11 @@ def module_edit(
}
if module:
module_types |= {
scu.ModuleType(module.module_type)
if module.module_type
else scu.ModuleType.STANDARD
(
scu.ModuleType(module.module_type)
if module.module_type
else scu.ModuleType.STANDARD
)
}
# Numéro du module
# cherche le numero adéquat (pour placer le module en fin de liste)
@ -571,15 +575,17 @@ def module_edit(
"input_type": "menu",
"title": "Rattachement :" if is_apc else "Matière :",
"explanation": (
"UE de rattachement, utilisée notamment pour les malus"
+ (
" (module utilisé, ne peut pas être changé de semestre)"
if in_use
else ""
(
"UE de rattachement, utilisée notamment pour les malus"
+ (
" (module utilisé, ne peut pas être changé de semestre)"
if in_use
else ""
)
)
)
if is_apc
else "un module appartient à une seule matière.",
if is_apc
else "un module appartient à une seule matière."
),
"labels": mat_names,
"allowed_values": ue_mat_ids,
"enabled": unlocked,
@ -733,7 +739,7 @@ def module_edit(
"title": f"""<span class="fontred">{scu.EMO_WARNING }
L'UE <a class="stdlink" href="{
url_for("notes.ue_edit", scodoc_dept=g.scodoc_dept, ue_id=ue.id)
}">{ue.acronyme} {ue.titre}</a>
}">{ue.acronyme} {ue.titre or ''}</a>
n'est pas associée à un niveau de compétences
</span>""",
},
@ -766,12 +772,14 @@ def module_edit(
request.base_url,
scu.get_request_args(),
descr,
html_foot_markup=f"""<div class="sco_tag_module_edit"><span
html_foot_markup=(
f"""<div class="sco_tag_module_edit"><span
class="sco_tag_edit"><textarea data-module_id="{module_id}" class="module_tag_editor"
>{','.join(sco_tag_module.module_tag_list(module_id))}</textarea></span></div>
"""
if not create
else "",
if not create
else ""
),
initvalues=module_dict if module else {},
submitlabel="Modifier ce module" if module else "Créer ce module",
cancelbutton="Annuler",
@ -814,7 +822,7 @@ def module_edit(
tf[2]["matiere_id"] = matiere.id
else:
matiere_id = sco_edit_matiere.do_matiere_create(
{"ue_id": ue.id, "titre": ue.titre, "numero": 1},
{"ue_id": ue.id, "titre": ue.titre or "", "numero": 1},
)
tf[2]["matiere_id"] = matiere_id

View File

@ -167,7 +167,7 @@ def do_ue_delete(ue: UniteEns, delete_validations=False, force=False):
if not ue.can_be_deleted():
raise ScoNonEmptyFormationObject(
f"UE (id={ue.id}, dud)",
msg=ue.titre,
msg=f"{ue.titre or ''} ({ue.acronyme})",
dest_url=url_for(
"notes.ue_table",
scodoc_dept=g.scodoc_dept,
@ -639,8 +639,8 @@ def ue_delete(ue_id=None, delete_validations=False, dialog_confirmed=False):
)
if not ue.can_be_deleted():
raise ScoNonEmptyFormationObject(
f"UE",
msg=ue.titre,
"UE",
msg=f"{ue.titre or ''} ({ue.acronyme})",
dest_url=url_for(
"notes.ue_table",
scodoc_dept=g.scodoc_dept,
@ -651,7 +651,7 @@ def ue_delete(ue_id=None, delete_validations=False, dialog_confirmed=False):
if not dialog_confirmed:
return scu.confirm_dialog(
f"<h2>Suppression de l'UE {ue.titre} ({ue.acronyme})</h2>",
f"<h2>Suppression de l'UE {ue.titre or ''} ({ue.acronyme})</h2>",
dest_url="",
parameters={"ue_id": ue.id},
cancel_url=url_for(
@ -1452,7 +1452,7 @@ def ue_sharing_code(ue_code: str = "", ue_id: int = None, hide_ue_id: int = None
H.append("<ul>")
for ue in ues:
H.append(
f"""<li>{ue.acronyme} ({ue.titre}) dans
f"""<li>{ue.acronyme} ({ue.titre or ''}) dans
<a class="stdlink" href="{
url_for("notes.ue_table",
scodoc_dept=g.scodoc_dept, formation_id=ue.formation.id)}"

View File

@ -283,7 +283,7 @@ def evaluation_create_form(
"coef. mod.:" +str(coef_ue) if coef_ue
else "ce module n'a pas de coef. dans cette UE"
})</span>
<span class="eval_coef_ue_titre">{ue.titre}</span>
<span class="eval_coef_ue_titre">{ue.titre or ''}</span>
""",
"allow_null": False,
# ok si poids nul ou coef vers l'UE nul:

View File

@ -258,13 +258,17 @@ def formsemestre_ext_edit_ue_validations(formsemestre_id, etudid):
submitlabel="Enregistrer ces validations",
cancelbutton="Annuler",
initvalues=initvalues,
cssclass="tf_ext_edit_ue_validations ext_apc"
if formsemestre.formation.is_apc()
else "tf_ext_edit_ue_validations",
cssclass=(
"tf_ext_edit_ue_validations ext_apc"
if formsemestre.formation.is_apc()
else "tf_ext_edit_ue_validations"
),
# En APC, stocke les coefficients pour l'affichage de la moyenne en direct
form_attrs=f"""data-ue_coefs='[{', '.join(str(ue.ects or 0) for ue in ues)}]'"""
if formsemestre.formation.is_apc()
else "",
form_attrs=(
f"""data-ue_coefs='[{', '.join(str(ue.ects or 0) for ue in ues)}]'"""
if formsemestre.formation.is_apc()
else ""
),
)
if tf[0] == -1:
return "<h4>annulation</h4>"
@ -421,12 +425,18 @@ def _ue_form_description(
"input_type": "text",
"size": 4,
"template": itemtemplate,
"title": "<tt>"
+ (f"S{ue.semestre_idx} " if ue.semestre_idx is not None else "")
+ f"<b>{ue.acronyme}</b></tt> {ue.titre}"
+ f" ({ue.ects} ECTS)"
if ue.ects is not None
else "",
"title": (
"<tt>"
+ (
f"S{ue.semestre_idx} "
if ue.semestre_idx is not None
else ""
)
+ f"<b>{ue.acronyme}</b></tt> {ue.titre or ''}"
+ f" ({ue.ects} ECTS)"
if ue.ects is not None
else ""
),
"attributes": [coef_disabled],
},
)

View File

@ -281,9 +281,11 @@ def formsemestre_status_menubar(formsemestre: FormSemestre) -> str:
menu_inscriptions = [
{
"title": "Gérer les inscriptions aux UE et modules"
if formsemestre.formation.is_apc()
else "Gérer les inscriptions aux modules",
"title": (
"Gérer les inscriptions aux UE et modules"
if formsemestre.formation.is_apc()
else "Gérer les inscriptions aux modules"
),
"endpoint": "notes.moduleimpl_inscriptions_stats",
"args": {"formsemestre_id": formsemestre_id},
}
@ -619,9 +621,9 @@ def formsemestre_description_table(
if ue.color:
for k in list(ue_info.keys()):
if not k.startswith("_"):
ue_info[
f"_{k}_td_attrs"
] = f'style="background-color: {ue.color} !important;"'
ue_info[f"_{k}_td_attrs"] = (
f'style="background-color: {ue.color} !important;"'
)
if not is_apc:
# n'affiche la ligne UE qu'en formation classique
# car l'UE de rattachement n'a pas d'intérêt en BUT
@ -1050,9 +1052,11 @@ def formsemestre_status(formsemestre_id=None, check_parcours=True):
formsemestre_id=formsemestre_id, page_title="Tableau de bord"
),
formsemestre_warning_apc_setup(formsemestre, nt),
formsemestre_warning_etuds_sans_note(formsemestre, nt)
if can_change_all_notes
else "",
(
formsemestre_warning_etuds_sans_note(formsemestre, nt)
if can_change_all_notes
else ""
),
"""<p style="font-size: 130%"><b>Tableau de bord&nbsp;: </b>""",
]
if formsemestre.est_courant():
@ -1226,7 +1230,7 @@ def formsemestre_tableau_modules(
ue = modimpl.module.ue
if show_ues and (prev_ue_id != ue.id):
prev_ue_id = ue.id
titre = ue.titre
titre = ue.titre or ""
if use_ue_coefs:
titre += f""" <b>(coef. {ue.coefficient or 0.0})</b>"""
H.append(

View File

@ -728,7 +728,9 @@ def formsemestre_recap_parcours_table(
)
# Dispense BUT ?
if (etudid, ue.id) in nt.dispense_ues:
moy_ue_txt = "" if (ue_status and ue_status["is_capitalized"]) else ""
moy_ue_txt = (
"" if (ue_status and ue_status["is_capitalized"]) else ""
)
explanation_ue.append("non inscrit (dispense)")
else:
moy_ue_txt = scu.fmt_note(moy_ue)
@ -1098,7 +1100,7 @@ def formsemestre_validate_previous_ue(formsemestre: FormSemestre, etud: Identite
ue_names = ["Choisir..."] + [
f"""{('S'+str(ue.semestre_idx)+' : ') if ue.semestre_idx is not None else ''
}{ue.acronyme} {ue.titre} ({ue.ue_code or ""})"""
}{ue.acronyme} {ue.titre or ''} ({ue.ue_code or ""})"""
for ue in ues
]
ue_ids = [""] + [ue.id for ue in ues]

View File

@ -682,9 +682,9 @@ class RowRecap(tb.Row):
self.add_ue_modimpls_cols(ue, ue_status["is_capitalized"])
self.nb_ues_etud_parcours = len(res.etud_parcours_ues_ids(etud.id))
ue_valid_txt = (
ue_valid_txt_html
) = f"{self.nb_ues_validables}/{self.nb_ues_etud_parcours}"
ue_valid_txt = ue_valid_txt_html = (
f"{self.nb_ues_validables}/{self.nb_ues_etud_parcours}"
)
if self.nb_ues_warning:
ue_valid_txt_html += " " + scu.EMO_WARNING
cell_class = ""
@ -708,9 +708,9 @@ class RowRecap(tb.Row):
# sous-classé par JuryRow pour ajouter les codes
table: TableRecap = self.table
formsemestre: FormSemestre = table.res.formsemestre
table.group_titles[
"col_ue"
] = f"UEs du S{formsemestre.semestre_id} {formsemestre.annee_scolaire()}"
table.group_titles["col_ue"] = (
f"UEs du S{formsemestre.semestre_id} {formsemestre.annee_scolaire()}"
)
col_id = f"moy_ue_{ue.id}"
val = (
ue_status["moy"]
@ -740,7 +740,7 @@ class RowRecap(tb.Row):
)
table.foot_title_row.cells[col_id].target_attrs[
"title"
] = f"""{ue.titre} S{ue.semestre_idx or '?'}"""
] = f"""{ue.titre or ue.acronyme} S{ue.semestre_idx or '?'}"""
def add_ue_modimpls_cols(self, ue: UniteEns, is_capitalized: bool):
"""Ajoute à row les moyennes des modules (ou ressources et SAÉs) dans l'UE"""

View File

@ -1,7 +1,7 @@
{# Édition liste UEs APC #}
{% for semestre_idx in semestre_ids %}
<div class="formation_list_ues">
<div class="formation_list_ues_titre">Unités d'Enseignement
<div class="formation_list_ues_titre">Unités d'Enseignement
semestre {{semestre_idx}} &nbsp;-&nbsp; {{ects_by_sem[semestre_idx] | safe}} ECTS
</div>
<div class="formation_list_ues_content">
@ -9,14 +9,14 @@
{% for ue in ues_by_sem[semestre_idx] %}
<li class="notes_ue_list">
{% if editable and not loop.first %}
<a href="{{ url_for('notes.ue_move',
<a href="{{ url_for('notes.ue_move',
scodoc_dept=g.scodoc_dept, ue_id=ue.id, after=0 )
}}" class="aud">{{icons.arrow_up|safe}}</a>
{% else %}
{{icons.arrow_none|safe}}
{% endif %}
{% if editable and not loop.last %}
<a href="{{ url_for('notes.ue_move',
<a href="{{ url_for('notes.ue_move',
scodoc_dept=g.scodoc_dept, ue_id=ue.id, after=1 )
}}" class="aud">{{icons.arrow_down|safe}}</a>
{% else %}
@ -24,7 +24,7 @@
{% endif %}
</span>
<a class="smallbutton" href="{{ url_for('notes.ue_delete',
<a class="smallbutton" href="{{ url_for('notes.ue_delete',
scodoc_dept=g.scodoc_dept, ue_id=ue.id)
}}">{% if editable and not ue.modules.count() %}{{icons.delete|safe}}{% else
%}{{icons.delete_disabled|safe}}{% endif %}</a>
@ -34,12 +34,12 @@
ue.color if ue.color is not none else 'blue'}}"></span>
<b>{{ue.acronyme}} <a class="discretelink" href="{{
url_for('notes.ue_infos', scodoc_dept=g.scodoc_dept, ue_id=ue.id)}}" title="{{ue.acronyme}}: {{
('pas de compétence associée'
if ue.niveau_competence is none
('pas de compétence associée'
if ue.niveau_competence is none
else 'compétence ' + ue.niveau_competence.annee + ' ' + ue.niveau_competence.competence.titre_long)
if ue.type == 0
else ''
}}">{{ue.titre}}</a>
}}">{{ue.titre or ue.acronyme}}</a>
</b>
{% set virg = joiner(", ") %}
<span class="ue_code">(
@ -66,7 +66,7 @@
</div>
{% endif %}
{% if editable and not ue.is_locked() %}
<a class="stdlink" href="{{ url_for('notes.ue_edit',
<a class="stdlink" href="{{ url_for('notes.ue_edit',
scodoc_dept=g.scodoc_dept, ue_id=ue.id)
}}">modifier</a>
{% endif %}
@ -100,8 +100,8 @@
{% if editable %}
<ul>
<li class="notes_ue_list notes_ue_list_add"><a class="stdlink" href="{{
url_for('notes.ue_create',
scodoc_dept=g.scodoc_dept,
url_for('notes.ue_create',
scodoc_dept=g.scodoc_dept,
formation_id=formation.id,
default_semestre_idx=semestre_idx,
)}}">ajouter une UE</a>

View File

@ -4,7 +4,7 @@
{% block app_content %}
<!-- begin ue_infos -->
<h2>Unité d'Enseignement {{ue.acronyme|e}} {{ue.titre}}</h2>
<h2>Unité d'Enseignement {{ue.acronyme|e}} {{(ue.titre or '')|e}}</h2>
<div class="ue_infos">
@ -36,7 +36,7 @@
{% if loop.first %}
<ul>
{% endif %}
<li><a href="{{url_for('notes.formsemestre_status',
<li><a href="{{url_for('notes.formsemestre_status',
scodoc_dept=g.scodoc_dept, formsemestre_id=sem.id )}}">{{sem.titre_mois()}}</a></li>
{% if loop.last %}
</ul>

View File

@ -113,7 +113,7 @@ def table_modules_ue_coefs(formation_id, semestre_idx=None, parcours_id: int = N
"y": 1, # 1ere ligne
"style": "title_ue",
"data": ue.acronyme,
"title": ue.titre,
"title": ue.titre or ue.acronymexs,
}
for (col, ue) in enumerate(ues, start=2)
]
@ -214,11 +214,13 @@ def edit_modules_ue_coefs():
{lockicon}
</h2>
""",
"""<span class="warning">Formation verrouilée car un ou plusieurs
(
"""<span class="warning">Formation verrouilée car un ou plusieurs
semestres verrouillés l'utilisent.
</span>"""
if locked
else "",
if locked
else ""
),
render_template(
"pn/form_modules_ue_coefs.j2",
formation=formation,