input Validierung und UI handling fühlbar beschleunigt

This commit is contained in:
trnq1ll0 committed 2026-06-10 08:33:34 +02:00
1 parent 31cdc7747f
commit f4afd4b2e5
1 file changed
+77 -27
+77 -27
View File
@@ -54,6 +54,15 @@ if "input_validated" not in st.session_state:
st.session_state.input_validated = False
if "template_validated" not in st.session_state:
st.session_state.template_validated = False
# Caches für Validierung/Parsing – nur bei Dateiwechsel neu ausführen
if "last_input_file" not in st.session_state:
st.session_state.last_input_file = None
if "last_template_file" not in st.session_state:
st.session_state.last_template_file = None
if "cached_val_result" not in st.session_state:
st.session_state.cached_val_result = None
if "cached_tpl_result" not in st.session_state:
st.session_state.cached_tpl_result = None
# --- Layout: zwei Spalten ---
col1, col2 = st.columns(2)
@@ -73,9 +82,30 @@ with col1:
if selected_input:
input_path = Path(app_config.input_dir) / selected_input
# Validiere und parse sofort
with st.spinner("Validiere Input-Datei…"):
val_result = validate_input_file(input_path, app_config.input_schema, app_config.month_sheet_pattern)
# Nur validieren/parsen wenn sich die Datei geändert hat
if selected_input != st.session_state.last_input_file:
with st.spinner("Validiere Input-Datei…"):
val_result = validate_input_file(input_path, app_config.input_schema, app_config.month_sheet_pattern)
if val_result.is_valid:
records = parse_input_file(
input_path,
app_config.input_schema,
app_config.month_sheet_pattern,
app_config.skip_empty_name,
app_config.skip_empty_antragsnummer,
)
st.session_state.parsed_records = records
st.session_state.input_validated = True
else:
st.session_state.parsed_records = []
st.session_state.input_validated = False
st.session_state.cached_val_result = val_result
st.session_state.last_input_file = selected_input
else:
val_result = st.session_state.cached_val_result
if not val_result.is_valid:
st.markdown(
@@ -100,27 +130,19 @@ with col1:
for warn in val_result.warnings:
st.warning(warn)
# Parse die Datei
records = parse_input_file(
input_path,
app_config.input_schema,
app_config.month_sheet_pattern,
app_config.skip_empty_name,
app_config.skip_empty_antragsnummer,
)
st.session_state.parsed_records = records
st.session_state.input_validated = True
# Zeige Zusammenfassung
# Zeige Zusammenfassung aus gecachten Records
records = st.session_state.parsed_records
employees = get_unique_employees(records)
antragsnummern = get_unique_antragsnummern(records)
st.success(f"✅ {len(records)} Einträge in {val_result.info.get('sheets_with_data', 0)} Monats-Sheets")
st.metric("Mitarbeiter", len(employees))
st.metric("Antragsnummern", len(antragsnummern))
with st.expander("Antragsnummern anzeigen"):
for an in antragsnummern:
st.text(f"• {an}")
pills = " ".join(
f'<span style="display:inline-block; background:#e8f0fe; color:#1a73e8; '
f'border-radius:16px; padding:4px 12px; margin:3px; font-size:0.9em; '
f'white-space:nowrap">{an}</span>'
for an in antragsnummern
)
st.markdown(f"**Antragsnummern:**<br>{pills}", unsafe_allow_html=True)
with col2:
st.subheader("2. Template")
@@ -140,9 +162,16 @@ with col2:
)
if selected_template:
template_path = Path(app_config.template_dir) / selected_template
with st.spinner("Validiere Template…"):
tpl_result = validate_template(template_path, app_config.output_mapping)
# Nur validieren wenn sich das Template geändert hat
if selected_template != st.session_state.last_template_file:
template_path = Path(app_config.template_dir) / selected_template
with st.spinner("Validiere Template…"):
tpl_result = validate_template(template_path, app_config.output_mapping)
st.session_state.cached_tpl_result = tpl_result
st.session_state.last_template_file = selected_template
st.session_state.template_validated = tpl_result.is_valid
else:
tpl_result = st.session_state.cached_tpl_result
if not tpl_result.is_valid:
st.markdown(
@@ -176,11 +205,32 @@ st.subheader("3. Mitarbeiter auswählen")
if st.session_state.input_validated and st.session_state.parsed_records:
employees = get_unique_employees(st.session_state.parsed_records)
selected_employees = st.multiselect(
f"{len(employees)} Mitarbeiter gefunden – wähle aus, für wen Tätigkeitsnachweise erstellt werden sollen:",
options=employees,
default=employees,
st.caption(f"{len(employees)} Mitarbeiter gefunden – wähle aus, für wen Tätigkeitsnachweise erstellt werden sollen:")
# "Alle" / "Keine" Buttons
btn_col1, btn_col2 = st.columns(2)
if btn_col1.button("☑ Alle auswählen", use_container_width=True):
for emp in employees:
st.session_state[f"sel_{emp}"] = True
if btn_col2.button("☐ Keine auswählen", use_container_width=True):
for emp in employees:
st.session_state[f"sel_{emp}"] = False
# Mitarbeiter-Liste mit Rahmen
st.markdown(
'<div style="border:1px solid #d5d5d5; border-radius:6px; padding:8px 12px; '
'background:#fafafa; max-height:300px; overflow-y:auto">',
unsafe_allow_html=True,
)
selected_employees = []
for emp in employees:
key = f"sel_{emp}"
if key not in st.session_state:
st.session_state[key] = True
if st.checkbox(emp, value=st.session_state[key], key=key):
selected_employees.append(emp)
st.markdown("</div>", unsafe_allow_html=True)
st.caption(f"{len(selected_employees)} von {len(employees)} Mitarbeitern ausgewählt")
else:
selected_employees = []