From 488e4b1c85ee067b6a175088efbfc0b82a49f4d6 Mon Sep 17 00:00:00 2001 From: Emmanuel Viennet Date: Mon, 10 Apr 2023 11:25:46 +0200 Subject: [PATCH] =?UTF-8?q?Affichage/=C3=A9dition=20des=20programmes=20BUT?= =?UTF-8?q?/Niveaux=20de=20comp=C3=A9tences.=20Tests.=20--=20WIP?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/__init__.py | 2 +- app/api/formations.py | 72 +- app/but/apc_edit_ue.py | 2 +- app/forms/formation/__init__.py | 1 + app/models/but_refcomp.py | 25 +- app/models/ues.py | 26 +- app/scodoc/sco_edit_apc.py | 12 +- app/scodoc/sco_edit_ue.py | 21 +- app/static/css/parcour_formation.css | 90 ++- app/static/css/refcomp_parcours_niveaux.css | 57 +- app/static/css/scodoc.css | 34 + app/templates/but/parcour_formation.j2 | 144 +++- app/templates/pn/form_ues.j2 | 27 +- app/templates/sco_page.j2 | 6 +- app/views/but_formation.py | 45 +- pytest.ini | 3 + .../scodoc_formation_BUT_INFO_v1.xml | 675 ++++++++++++++++++ .../scodoc_formation_BUT_RT_v23.xml | 587 +++++++++++++++ tests/ressources/yaml/cursus_but_info.yaml | 43 ++ 19 files changed, 1811 insertions(+), 61 deletions(-) create mode 100644 app/forms/formation/__init__.py create mode 100644 tests/ressources/formations/scodoc_formation_BUT_INFO_v1.xml create mode 100644 tests/ressources/formations/scodoc_formation_BUT_RT_v23.xml create mode 100644 tests/ressources/yaml/cursus_but_info.yaml diff --git a/app/__init__.py b/app/__init__.py index d11347a8e..0889da642 100644 --- a/app/__init__.py +++ b/app/__init__.py @@ -272,7 +272,7 @@ def create_app(config_class=DevConfig): # S'arrête sur tous les warnings, sauf # flask_sqlalchemy/query (pb deprecation du model.get()) warnings.filterwarnings("error", module="flask_sqlalchemy/query") - + # warnings.filterwarnings("ignore", module="json/provider.py") xxx sans effet en test # Vérifie/crée lien sym pour les URL statiques link_filename = f"{app.root_path}/static/links/{sco_version.SCOVERSION}" if not os.path.exists(link_filename): diff --git a/app/api/formations.py b/app/api/formations.py index 80c680221..e9f200a9e 100644 --- a/app/api/formations.py +++ b/app/api/formations.py @@ -8,16 +8,23 @@ ScoDoc 9 API : accès aux formations """ -from flask import g, request +from flask import flash, g, request from flask_json import as_json from flask_login import login_required import app -from app import log +from app import db, log from app.api import api_bp as bp, api_web_bp from app.scodoc.sco_utils import json_error from app.decorators import scodoc, permission_required -from app.models import ApcParcours, Formation, FormSemestre, ModuleImpl, UniteEns +from app.models import ( + ApcNiveau, + ApcParcours, + Formation, + FormSemestre, + ModuleImpl, + UniteEns, +) from app.scodoc import sco_formations from app.scodoc.sco_permissions import Permission @@ -315,3 +322,62 @@ def set_ue_parcours(ue_id: int): log(f"set_ue_parcours: ue_id={ue.id} parcours_ids={parcours_ids}") ok, error_message = ue.set_parcours(parcours) return {"status": ok, "message": error_message} + + +@bp.route( + "/assoc_ue_niveau//", + methods=["POST"], +) +@api_web_bp.route( + "/assoc_ue_niveau//", + methods=["POST"], +) +@login_required +@scodoc +@permission_required(Permission.ScoChangeFormation) +@as_json +def assoc_ue_niveau(ue_id: int, niveau_id: int): + """Associe l'UE au niveau de compétence""" + query = UniteEns.query.filter_by(id=ue_id) + if g.scodoc_dept: + query = query.join(Formation).filter_by(dept_id=g.scodoc_dept_id) + ue: UniteEns = query.first_or_404() + niveau: ApcNiveau = ApcNiveau.query.get_or_404(niveau_id) + ok, error_message = ue.set_niveau_competence(niveau) + if not ok: + if g.scodoc_dept: # "usage web" + flash(error_message) + return json_error(404, error_message) + if g.scodoc_dept: # "usage web" + flash(f"UE {ue.acronyme} associée au niveau {niveau.libelle}") + return {"status": 0} + + +@bp.route( + "/desassoc_ue_niveau/", + methods=["POST"], +) +@api_web_bp.route( + "/desassoc_ue_niveau/", + methods=["POST"], +) +@login_required +@scodoc +@permission_required(Permission.ScoChangeFormation) +@as_json +def desassoc_ue_niveau(ue_id: int): + """Désassocie cette UE de son niveau de compétence + (si elle n'est pas associée, ne fait rien) + """ + query = UniteEns.query.filter_by(id=ue_id) + if g.scodoc_dept: + query = query.join(Formation).filter_by(dept_id=g.scodoc_dept_id) + ue: UniteEns = query.first_or_404() + ue.niveau_competence = None + db.session.add(ue) + db.session.commit() + log(f"desassoc_ue_niveau: {ue}") + if g.scodoc_dept: + # "usage web" + flash(f"UE {ue.acronyme} dé-associée") + return {"status": 0} diff --git a/app/but/apc_edit_ue.py b/app/but/apc_edit_ue.py index c68d98f6f..bdd88205d 100644 --- a/app/but/apc_edit_ue.py +++ b/app/but/apc_edit_ue.py @@ -49,7 +49,7 @@ def form_ue_choix_niveau(ue: UniteEns) -> str: onchange="set_ue_parcour(this);" data-ue_id="{ue.id}" data-setter="{ - url_for( "notes.set_ue_parcours", scodoc_dept=g.scodoc_dept) + url_for( "apiweb.set_ue_parcours", scodoc_dept=g.scodoc_dept, ue_id=ue.id) }">