Aggiungi export XLSX diagnostica

This commit is contained in:
2026-07-06 18:14:13 +02:00
parent 8e9294f80b
commit 7f3ce9d3af
3 changed files with 119 additions and 2 deletions

View File

@@ -3,7 +3,8 @@
from __future__ import annotations
import tkinter as tk
from tkinter import messagebox, ttk
from datetime import datetime
from tkinter import filedialog, messagebox, ttk
from typing import Any
import customtkinter as ctk
@@ -72,6 +73,7 @@ class DiagnosticaWindow(ctk.CTkToplevel):
self._load_in_progress = False
self._current_check = ""
self.var_status = tk.StringVar(value="")
self._last_export_slug = "diagnostica"
self.title(
versioned_title(
@@ -124,6 +126,15 @@ class DiagnosticaWindow(ctk.CTkToplevel):
font=button_font,
).grid(row=0, column=0, sticky="w", padx=(0, 8))
self.btn_export = ctk.CTkButton(
top,
text=loc_text("diagnostics.button.export", catalog=self._locale_catalog, default="Esporta XLSX"),
command=self._export_xlsx,
font=button_font,
state="disabled",
)
self.btn_export.grid(row=0, column=2, sticky="e")
ctk.CTkLabel(
self,
textvariable=self.var_status,
@@ -205,6 +216,11 @@ class DiagnosticaWindow(ctk.CTkToplevel):
self._load_in_progress = True
self._current_check = key
self._last_export_slug = key
try:
self.btn_export.configure(state="disabled")
except Exception:
pass
try:
self._busy.show(busy_text)
self._async.run(job(), self._on_loaded, self._on_error)
@@ -237,6 +253,10 @@ class DiagnosticaWindow(ctk.CTkToplevel):
),
tags=(zebra_tag(index),),
)
try:
self.btn_export.configure(state="normal" if rows else "disabled")
except Exception:
pass
self._set_status(
loc_text(
"diagnostics.status.rows",
@@ -264,6 +284,91 @@ class DiagnosticaWindow(ctk.CTkToplevel):
parent=self,
)
def _export_xlsx(self) -> None:
"""Export the currently visible diagnostic grid to an Excel file."""
rows = [self.tree.item(iid, "values") for iid in self.tree.get_children("")]
if not rows:
messagebox.showinfo(
loc_text("diagnostics.export.title", catalog=self._locale_catalog, default="Esporta"),
loc_text(
"diagnostics.export.empty",
catalog=self._locale_catalog,
default="Non ci sono righe da esportare.",
),
parent=self,
)
return
try:
from openpyxl import Workbook
from openpyxl.styles import Alignment, Font
from openpyxl.utils import get_column_letter
except Exception as exc:
messagebox.showerror(
loc_text("diagnostics.export.title", catalog=self._locale_catalog, default="Esporta"),
loc_text(
"diagnostics.export.dep",
catalog=self._locale_catalog,
default="Per l'esportazione serve 'openpyxl' (pip install openpyxl).",
).format(error=exc),
parent=self,
)
return
ts = datetime.now().strftime("%Y%m%d_%H%M")
default_name = f"{self._last_export_slug}_{ts}.xlsx"
path = filedialog.asksaveasfilename(
parent=self,
title=loc_text("diagnostics.export.title", catalog=self._locale_catalog, default="Esporta"),
defaultextension=".xlsx",
filetypes=[("Excel Workbook", "*.xlsx")],
initialfile=default_name,
)
if not path:
return
try:
wb = Workbook()
ws = wb.active
ws.title = "Diagnostica"
columns = list(self.tree["columns"])
headers = [str(self.tree.heading(col, "text") or col) for col in columns]
for col_index, header in enumerate(headers, start=1):
cell = ws.cell(row=1, column=col_index, value=header)
cell.font = Font(bold=True)
cell.alignment = Alignment(horizontal="center", vertical="center")
for row_index, row in enumerate(rows, start=2):
for col_index, value in enumerate(row, start=1):
ws.cell(row=row_index, column=col_index, value=value)
widths: dict[int, int] = {}
for row in ws.iter_rows(values_only=True):
for col_index, value in enumerate(row, start=1):
widths[col_index] = max(widths.get(col_index, 0), len("" if value is None else str(value)))
for col_index, width in widths.items():
ws.column_dimensions[get_column_letter(col_index)].width = min(max(width + 2, 12), 70)
wb.save(path)
messagebox.showinfo(
loc_text("diagnostics.export.title", catalog=self._locale_catalog, default="Esporta"),
loc_text("diagnostics.export.ok", catalog=self._locale_catalog, default="File creato:\n{path}").format(path=path),
parent=self,
)
except Exception as exc:
log_exception(__name__, exc, context="export diagnostica xlsx")
messagebox.showerror(
loc_text("diagnostics.export.title", catalog=self._locale_catalog, default="Esporta"),
loc_text(
"diagnostics.export.error",
catalog=self._locale_catalog,
default="Errore durante l'esportazione:\n{error}",
).format(error=exc),
parent=self,
)
def open_diagnostica_window(parent: tk.Misc, db_client, session=None) -> tk.Misc:
"""Open the diagnostics window."""