"""Seitenleiste ausblenden: Vorgabe des Admins, eigene Auswahl, Vereinigung.""" import json import pytest from fastapi import HTTPException from sqlalchemy.exc import IntegrityError from app.models import NavigationSichtbarkeit, Role, User from app.routers.navigation import ( eigene_auswahl_setzen, navigation_lesen, vorgabe_setzen, ) from app.schemas import NavigationSetzen @pytest.fixture() def admin(db): person = User(username="admin", password_hash="x", role=Role.admin) db.add(person) db.commit() db.refresh(person) return person @pytest.fixture() def mitbewohner(db): person = User(username="mitbewohner", password_hash="x", role=Role.user) db.add(person) db.commit() db.refresh(person) return person def _setze_vorgabe(db, admin, werte): return vorgabe_setzen(NavigationSetzen(versteckt=werte), db=db, user=admin) def _setze_eigen(db, user, werte): return eigene_auswahl_setzen(NavigationSetzen(versteckt=werte), db=db, user=user) # ---- Vorgabe ---- def test_ohne_eintrag_ist_nichts_versteckt(db, admin): out = navigation_lesen(db=db, user=admin) assert out.vorgabe == [] and out.eigen == [] and out.versteckt == [] def test_vorgabe_gilt_fuer_alle(db, admin, mitbewohner): _setze_vorgabe(db, admin, ["/rezepte"]) assert navigation_lesen(db=db, user=mitbewohner).versteckt == ["/rezepte"] assert navigation_lesen(db=db, user=admin).versteckt == ["/rezepte"] def test_normaler_nutzer_darf_die_vorgabe_nicht_setzen(db, mitbewohner): """require_admin greift – geprueft ueber die Rolle, wie in deps.py.""" from app.deps import require_admin with pytest.raises(HTTPException) as fehler: require_admin(mitbewohner) assert fehler.value.status_code == 403 # ---- Eigene Auswahl ---- def test_eigene_auswahl_betrifft_nur_einen(db, admin, mitbewohner): _setze_eigen(db, mitbewohner, ["/history"]) assert navigation_lesen(db=db, user=mitbewohner).versteckt == ["/history"] assert navigation_lesen(db=db, user=admin).versteckt == [] def test_eigene_auswahl_kommt_zur_vorgabe_dazu(db, admin, mitbewohner): _setze_vorgabe(db, admin, ["/rezepte"]) _setze_eigen(db, mitbewohner, ["/history"]) out = navigation_lesen(db=db, user=mitbewohner) assert out.vorgabe == ["/rezepte"] assert out.eigen == ["/history"] assert out.versteckt == ["/history", "/rezepte"] def test_nutzer_kann_die_vorgabe_nicht_aufheben(db, admin, mitbewohner): """Die eigene Auswahl addiert nur – sie nimmt nichts weg.""" _setze_vorgabe(db, admin, ["/shopping"]) _setze_eigen(db, mitbewohner, []) assert navigation_lesen(db=db, user=mitbewohner).versteckt == ["/shopping"] # ---- Speicherung ---- def test_zweimal_setzen_legt_keine_zweite_zeile_an(db, mitbewohner): _setze_eigen(db, mitbewohner, ["/history"]) _setze_eigen(db, mitbewohner, ["/verliehen"]) zeilen = db.query(NavigationSichtbarkeit).all() assert len(zeilen) == 1 assert json.loads(zeilen[0].versteckt) == ["/verliehen"] def test_nur_eine_vorgabezeile(db, admin): """Der Teilindex muss eine zweite Vorgabe verhindern.""" _setze_vorgabe(db, admin, ["/rezepte"]) db.add(NavigationSichtbarkeit(user_id=None, versteckt='["/shopping"]')) with pytest.raises(IntegrityError): db.commit() db.rollback() def test_nur_eine_zeile_je_konto(db, mitbewohner): _setze_eigen(db, mitbewohner, ["/history"]) db.add(NavigationSichtbarkeit(user_id=mitbewohner.id, versteckt="[]")) with pytest.raises(IntegrityError): db.commit() db.rollback() def test_doppelte_und_leere_eintraege_fallen_weg(db, mitbewohner): out = _setze_eigen(db, mitbewohner, ["/history", "/history", "", " ", "/verliehen"]) assert out.eigen == ["/history", "/verliehen"] def test_kaputter_inhalt_sperrt_niemanden_aus(db, mitbewohner): """Lieber die volle Leiste als eine Fehlermeldung.""" db.add(NavigationSichtbarkeit(user_id=mitbewohner.id, versteckt="kein JSON")) db.commit() assert navigation_lesen(db=db, user=mitbewohner).versteckt == [] def test_unbekannter_schluessel_wird_mitgefuehrt_aber_stoert_nicht(db, mitbewohner): """Ein umbenannter Eintrag darf die Leiste nicht zerreissen – der Server kennt die Pfade gar nicht, die Oberflaeche ignoriert Unbekanntes.""" out = _setze_eigen(db, mitbewohner, ["/gibtsnichtmehr"]) assert out.versteckt == ["/gibtsnichtmehr"]