forked from ScoDoc/ScoDoc
ajout export fichier par NIP
This commit is contained in:
parent
a5e5ad6248
commit
5cd495e33e
@ -40,6 +40,8 @@ from openpyxl.comments import Comment
|
||||
from openpyxl import Workbook, load_workbook
|
||||
from openpyxl.cell import WriteOnlyCell
|
||||
from openpyxl.styles import Font, Border, Side, Alignment, PatternFill
|
||||
from openpyxl.utils import quote_sheetname, absolute_coordinate
|
||||
from openpyxl.workbook.defined_name import DefinedName
|
||||
from openpyxl.worksheet.worksheet import Worksheet
|
||||
|
||||
import app.scodoc.sco_utils as scu
|
||||
@ -218,6 +220,7 @@ class ScoExcelSheet:
|
||||
self.rows = [] # list of list of cells
|
||||
self.column_dimensions = {}
|
||||
self.row_dimensions = {}
|
||||
self.formulae = {}
|
||||
|
||||
def excel_make_composite_style(
|
||||
self,
|
||||
@ -363,6 +366,9 @@ class ScoExcelSheet:
|
||||
"""ajoute une ligne déjà construite à la feuille."""
|
||||
self.rows.append(row)
|
||||
|
||||
def set_formula(self, coord, formula):
|
||||
self.formulae[coord] = formula
|
||||
|
||||
def prepare(self):
|
||||
"""génére un flux décrivant la feuille.
|
||||
Ce flux pourra ensuite être repris dans send_excel_file (classeur mono feille)
|
||||
@ -383,6 +389,8 @@ class ScoExcelSheet:
|
||||
|
||||
# construction d'un flux (https://openpyxl.readthedocs.io/en/stable/tutorial.html#saving-as-a-stream)
|
||||
self.prepare()
|
||||
for coord, formula in self.formulae.items():
|
||||
self.ws[coord] = formula
|
||||
with NamedTemporaryFile() as tmp:
|
||||
self.wb.save(tmp.name)
|
||||
tmp.seek(0)
|
||||
@ -433,7 +441,12 @@ def excel_simple_table(
|
||||
return ws.generate()
|
||||
|
||||
|
||||
def excel_feuille_saisie(evaluation: "Evaluation", titreannee, description, lines):
|
||||
from openpyxl.utils import absolute_coordinate
|
||||
|
||||
|
||||
def excel_feuille_saisie(
|
||||
evaluation: "Evaluation", titreannee, description, lines, withnips=False
|
||||
):
|
||||
"""Genere feuille excel pour saisie des notes.
|
||||
E: evaluation (dict)
|
||||
lines: liste de tuples
|
||||
@ -450,6 +463,13 @@ def excel_feuille_saisie(evaluation: "Evaluation", titreannee, description, line
|
||||
ws.set_column_dimension_width("D", 164.0 / 7) # groupes
|
||||
ws.set_column_dimension_width("E", 115.0 / 7) # notes
|
||||
ws.set_column_dimension_width("F", 355.0 / 7) # remarques
|
||||
if withnips:
|
||||
ws.set_column_dimension_width("G", 11.0 / 7) # colonne NIP cachée
|
||||
ws.set_column_dimension_width(
|
||||
"H", 105.0 / 7
|
||||
) # Colonne blanche entre liste et zone de saisie
|
||||
ws.set_column_dimension_width("I", 90.0 / 7) # Saisie: NIP
|
||||
ws.set_column_dimension_width("J", 115.0 / 7) # Saisie: Note
|
||||
|
||||
# fontes
|
||||
font_base = Font(name="Arial", size=12)
|
||||
@ -497,15 +517,32 @@ def excel_feuille_saisie(evaluation: "Evaluation", titreannee, description, line
|
||||
"font": font_blue,
|
||||
"border": border_top,
|
||||
}
|
||||
style_input = {
|
||||
"font": font_bold,
|
||||
"border": border_top,
|
||||
"fill": fill_light_yellow,
|
||||
}
|
||||
|
||||
if withnips:
|
||||
del style_notes["fill"]
|
||||
|
||||
list_top = 9
|
||||
|
||||
# ligne de titres
|
||||
ws.append_single_cell_row(
|
||||
"Feuille saisie note (à enregistrer au format excel)", style_titres
|
||||
)
|
||||
# lignes d'instructions
|
||||
if withnips:
|
||||
ws.append_single_cell_row(
|
||||
"Saisir les (NIP, note) en colonne I et J (cases jaunes). ordre des NIP indifférent",
|
||||
style_expl,
|
||||
)
|
||||
else:
|
||||
ws.append_single_cell_row(
|
||||
"Saisir les notes dans la colonne E (cases jaunes)", style_expl
|
||||
)
|
||||
|
||||
ws.append_single_cell_row("Ne pas modifier les cases en mauve !", style_expl)
|
||||
# Nom du semestre
|
||||
ws.append_single_cell_row(scu.unescape_html(titreannee), style_titres)
|
||||
@ -518,8 +555,7 @@ def excel_feuille_saisie(evaluation: "Evaluation", titreannee, description, line
|
||||
# ligne blanche
|
||||
ws.append_blank_row()
|
||||
# code et titres colonnes
|
||||
ws.append_row(
|
||||
[
|
||||
title_row = [
|
||||
ws.make_cell("!%s" % evaluation.id, style_ro),
|
||||
ws.make_cell("Nom", style_titres),
|
||||
ws.make_cell("Prénom", style_titres),
|
||||
@ -527,10 +563,25 @@ def excel_feuille_saisie(evaluation: "Evaluation", titreannee, description, line
|
||||
ws.make_cell("Note sur %g" % (evaluation.note_max or 0.0), style_titres),
|
||||
ws.make_cell("Remarque", style_titres),
|
||||
]
|
||||
)
|
||||
if withnips:
|
||||
title_row += [
|
||||
ws.make_cell("NIP", style_titres),
|
||||
ws.make_cell(),
|
||||
ws.make_cell("NIP", style_titres),
|
||||
ws.make_cell("Note sur 20", style_titres),
|
||||
]
|
||||
ws.append_row(title_row)
|
||||
|
||||
# Calcul de la zone de saisie (au format $I$9:$J$45) pour intégration dans la formule
|
||||
if withnips:
|
||||
min_row = list_top
|
||||
max_row = list_top + len(lines) - 1
|
||||
min_col = "I"
|
||||
max_col = "J"
|
||||
input_range = absolute_coordinate(f"{min_col}{min_row}:{max_col}{max_row}")
|
||||
|
||||
# etudiants
|
||||
for line in lines:
|
||||
for line_number, line in enumerate(lines):
|
||||
st = style_nom
|
||||
if line[3] != "I":
|
||||
st = style_dem
|
||||
@ -543,9 +594,15 @@ def excel_feuille_saisie(evaluation: "Evaluation", titreannee, description, line
|
||||
try:
|
||||
val = float(line[5])
|
||||
except ValueError:
|
||||
if withnips and line[5] == "":
|
||||
ws.set_formula(
|
||||
f"E{list_top + line_number}",
|
||||
f"=VLOOKUP(G{list_top + line_number},{input_range}, 2, FALSE)",
|
||||
)
|
||||
val = ""
|
||||
else:
|
||||
val = line[5]
|
||||
ws.append_row(
|
||||
[
|
||||
row = [
|
||||
ws.make_cell("!" + line[0], style_ro), # code
|
||||
ws.make_cell(line[1], st),
|
||||
ws.make_cell(line[2], st),
|
||||
@ -553,7 +610,14 @@ def excel_feuille_saisie(evaluation: "Evaluation", titreannee, description, line
|
||||
ws.make_cell(val, style_notes), # note
|
||||
ws.make_cell(line[6], style_comment), # comment
|
||||
]
|
||||
)
|
||||
if withnips:
|
||||
row += [
|
||||
ws.make_cell(line[7], style_ro), # NIP
|
||||
ws.make_cell(),
|
||||
ws.make_cell("", style_input), # Saisie NIP
|
||||
ws.make_cell("", style_input), # Saisie note
|
||||
]
|
||||
ws.append_row(row)
|
||||
|
||||
# explication en bas
|
||||
ws.append_row([None, ws.make_cell("Code notes", style_titres)])
|
||||
|
@ -733,6 +733,8 @@ def saisie_notes_tableur(evaluation_id, group_ids=()):
|
||||
<li><a class="stdlink" href="feuille_saisie_notes?evaluation_id={evaluation_id}&{
|
||||
groups_infos.groups_query_args}"
|
||||
id="lnk_feuille_saisie">obtenir le fichier tableur à remplir</a>
|
||||
(<a class="stdlink" href="feuille_saisie_notes?evaluation_id={evaluation_id}&{
|
||||
groups_infos.groups_query_args}&withnips=1">saisie par NIP</a>)
|
||||
</li>
|
||||
<li>ou <a class="stdlink" href="{url_for("notes.saisie_notes",
|
||||
scodoc_dept=g.scodoc_dept, evaluation_id=evaluation_id)
|
||||
@ -875,7 +877,7 @@ def saisie_notes_tableur(evaluation_id, group_ids=()):
|
||||
return "\n".join(H)
|
||||
|
||||
|
||||
def feuille_saisie_notes(evaluation_id, group_ids=[]):
|
||||
def feuille_saisie_notes(evaluation_id, group_ids=[], withnips=0):
|
||||
"""Document Excel pour saisie notes dans l'évaluation et les groupes indiqués"""
|
||||
evaluation: Evaluation = db.session.get(Evaluation, evaluation_id)
|
||||
if not evaluation:
|
||||
@ -922,15 +924,12 @@ def feuille_saisie_notes(evaluation_id, group_ids=[]):
|
||||
|
||||
# une liste de liste de chaines: lignes de la feuille de calcul
|
||||
rows = []
|
||||
|
||||
etuds = _get_sorted_etuds(evaluation, etudids, formsemestre.id)
|
||||
for e in etuds:
|
||||
etudid = e["etudid"]
|
||||
groups = sco_groups.get_etud_groups(etudid, formsemestre.id)
|
||||
grc = sco_groups.listgroups_abbrev(groups)
|
||||
|
||||
rows.append(
|
||||
[
|
||||
row = [
|
||||
str(etudid),
|
||||
e["nom"].upper(),
|
||||
e["prenom"].lower().capitalize(),
|
||||
@ -939,11 +938,17 @@ def feuille_saisie_notes(evaluation_id, group_ids=[]):
|
||||
e["val"],
|
||||
e["explanation"],
|
||||
]
|
||||
)
|
||||
if withnips == 1:
|
||||
row.append(e["code_nip"])
|
||||
rows.append(row)
|
||||
|
||||
filename = f"notes_{eval_name}_{gr_title_filename}"
|
||||
xls = sco_excel.excel_feuille_saisie(
|
||||
evaluation, formsemestre.titre_annee(), description, lines=rows
|
||||
evaluation,
|
||||
formsemestre.titre_annee(),
|
||||
description,
|
||||
lines=rows,
|
||||
withnips=(withnips == 1),
|
||||
)
|
||||
return scu.send_file(xls, filename, scu.XLSX_SUFFIX, mime=scu.XLSX_MIMETYPE)
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user