DigiDekan
Hochschul-Dekanats-Plattform — Java/Spring Boot, modernes JS-Frontend, CI/CD-Pipelines (GitHub Actions, automatisierte Tests).

Eckdaten
Umfang
Dateien
Modelle
API-Routes
Lines of Code
Apps
Seiten
Services
Herausforderung
Manuelle Semesterplanung per Tabelle, papierbasierte Formulare, keine zentrale Übersicht für den Dekan, fehleranfällige SWS-Berechnung und wochenlange Anerkennungs-Prozesse auf Papier — alles administrative Engpässe an einer deutschen Hochschule.
Lösung
Duale Plattform mit 7-Schritte-SemesterplanungWizard, SWS/Deputat-Berechnungs-Engine mit Kategorien-Obergrenzen und Warnungen, rollenbasierten Dashboards (Dekan, Professor, Lehrbeauftragte) und einem 5-Schritte-AnerkennungWizard mit 6-Stufen-Status-Timeline. Java/Spring-Boot-Backend mit REST-APIs, JWT-Auth via Spring Security, PDF-Export für Deputatsabrechnungen und @Scheduled-Jobs für E-Mail-Erinnerungen. Modernes TypeScript/React-Frontend mit React Hook Form-Validierung.
Ergebnis
Produktiv im Einsatz an einer deutschen Hochschule. Automatisierte SWS/Deputat-Berechnung ersetzt manuelle Tabellen, Anerkennungs-Prozesse von Wochen auf Tage verkürzt, zentrale Dekan-Übersicht über alle Professoren und Semester.
Über das Projekt
Hintergrund
Duale Plattform für Hochschul-Dekanate. „Digitales Dekanat" bietet Semesterplanung mit 7-Schritte-Wizard, SWS/Deputat-Berechnungs-Engine, Modulverwaltung und rollenbasierte Dashboards für Dekan, Professor und Lehrbeauftragte. „Anerkennung Standalone" liefert einen 5-Schritte-Wizard für Studierende mit 6-Stufen-Status-Timeline, Dokumenten-Upload, Dozent-Review-Workflow und automatischen E-Mail-Benachrichtigungen. Weiterentwicklung mit Java/Spring Boot, modernem JS-Frontend und automatisierten CI/CD-Pipelines (GitHub Actions, automatisierte Tests).
Stack
Technologien
Highlights
Kernfunktionen
Architektur
System auf einen Blick
React-Frontends sprechen über Spring Security mit JWT gegen vier Domain-Services. Geschäftslogik (SWS, Workflows, Planung) bleibt im Backend, PostgreSQL hält den Zustand mit Audit-Trail.
UI-Tour
Im Detail — 7 Kapitel · 22 Screens
Jeder Screenshot mit fachlichem Kontext. Springe direkt in ein Kapitel oder scrolle die komplette Tour.
01 / Dekanat
Zugang & Dashboards
Einstiegspunkt der Plattform für drei unterschiedliche Rollen — Dekan, Professor und Lehrbeauftragte. Jede Rolle bekommt nach JWT-Login eine eigene, rollenspezifisch zugeschnittene Übersicht.

01.01 · Auth · JWT · RBAC
Einheitlicher Login
Eine gemeinsame Login-Seite für alle drei internen Rollen. Im Hintergrund läuft Spring Security mit JWT (Access- und Refresh-Token); methoden-basierte Annotationen (@PreAuthorize) regeln den Zugriff pro Endpoint, der globale ExceptionHandler liefert konsistente API-Fehlerformate.
- ▸Token-basierte Authentifizierung mit Rollen-Claim
- ▸Rate-Limit auf fehlgeschlagene Logins
- ▸Audit-Log jedes Anmeldeversuchs
01.02 · KPI · Semester-Übersicht
Dekan-Dashboard
Zentrale Übersicht für den Dekan: Status der aktiven Semesterplanung, Anzahl offener Aufträge, Deputat-Auslastung des Fachbereichs und Quick-Links in die wichtigsten Verwaltungsbereiche. Die KPIs werden serverseitig über JPA-Aggregations-Queries auf den Domain-Entitäten berechnet.
- ▸Drilldown von jeder Kennzahl in die zugrundeliegende Liste
- ▸Visualisierung des aktuellen Planungsphasen-Status
- ▸Direkte Sprünge in Modul- und Dozentenverwaltung


01.03 · Persönliche Deputatsübersicht
Professor-Dashboard
Professor-spezifische Ansicht: eigene SWS-Auslastung, Liste zugewiesener Module und Semesteraufträge, To-dos für die aktuelle Planungsphase. RBAC sorgt dafür, dass jeder Professor nur seine eigenen Daten sieht.
- ▸Eigenes Deputat mit Ampel-Bewertung (erfüllt / Abweichung / starke Abweichung)
- ▸Persönliche Aufgaben pro Planungsphase
- ▸Direkter Zugriff auf die eigene SWS-Abrechnung
02 / Dekanat
Semesterplanung — 7-Schritte-Wizard
Das Herzstück des Digitalen Dekanats: Ein geführter 7-Schritte-Wizard von Semester-Auswahl bis Freigabe. Jeder Schritt validiert serverseitig, lässt sich zwischenspeichern und ist resumable.

02.01 · Stepper · React Hook Form · State Management
Wizard-Einstieg & Schritt-Navigation
Wizard-Startseite mit visuellem Stepper. Der Zustand jedes Schritts wird im Frontend gehalten und bei jeder Aktion gegen den Spring-REST-Endpoint validiert; der Stepper visualisiert offene und abgeschlossene Schritte.
- ▸7 Schritte: Semester · Module · Multiplikatoren · Zusatzinfos · Mitarbeiter · Aufträge · Freie Tage · Freigabe
- ▸Zwischenspeichern jederzeit möglich — Resume beim nächsten Login
- ▸Schritt-Validierung sowohl client- als auch serverseitig
02.02 · Geplante Module · Lehrform-Multiplikatoren
Modulzuordnung per Drag & Drop
Aus dem Modulkatalog werden Module per Drag & Drop in die laufende Semesterplanung gezogen. Pro Modul wird die Lehrform (Vorlesung / Seminar / Praktikum) erkannt und der zugehörige SWS-Multiplikator angewendet.
- ▸Suche & Filter auf 100+ Modulen des Katalogs
- ▸Live-Validierung gegen Doppelvergaben
- ▸Multiplikator-Override mit Begründungsfeld


02.03 · Pre-Submit-Check · Audit-Trail
Validierung & Freigabe
Letzter Schritt: Komplette Zusammenfassung der Planung mit allen Validierungs-Warnungen (überschrittene SWS-Obergrenzen, fehlende Zuordnungen). Erst nach explizitem „Freigeben" wird die Planung versioniert in die DB übernommen.
- ▸Versionierte Snapshots — frühere Stände bleiben einsehbar
- ▸Warn-Hierarchie: Fehler blockieren, Warnungen lassen sich quittieren
- ▸Audit-Log mit Benutzer-ID und Zeitstempel
03 / Dekanat
Deputat & Planungssteuerung
Das fachliche Schwergewicht: Die SWS/Deputat-Engine berechnet pro Professor die Lehrverpflichtung nach Hochschulgesetz. Praxisseminare, Master-Seminare und Betreuungen unterliegen Obergrenzen — wird überschritten, gibt es Warnungen.
Live-Demo · Domain-Logik
SWS-Berechnung selbst ausprobieren
Bewege die Regler — die Engine wendet Kategorien-Obergrenzen an, bilanziert das Gesamtdeputat gegen die Netto-Lehrverpflichtung und kennzeichnet jeden Cap, der überschritten wird, mit einer Warnung.
Lehre angerechnet
20.0SWS
Gesamtdeputat
27.0SWS
Differenz zum Soll
+9.0SWS
Cap-Warnungen aus der Engine
- Betreuungen: 5 SWS, max. 4 angerechnet
Die Logik entspricht 1:1 dem produktiven DeputatService in DigiDekan: Kategorien-Caps, Status-Bewertung bei |Δ| ≤ 1 (erfüllt), ≤ 3 (Abweichung), sonst „starke Abweichung“.

03.01 · Berechnungs-Engine · DeputatService.java
SWS/Deputat-Abrechnung
Pro Professor wird das Gesamtdeputat aus Lehrtätigkeiten, Lehrexport, Vertretungen, Betreuungen und Ermäßigungen berechnet. Praxisseminar (max. 6 SWS), Seminar Master (max. 4 SWS) und Betreuungen (max. 4 SWS) unterliegen Obergrenzen, die in der Engine automatisch angewendet und als Warnung dokumentiert werden.
- ▸Status-Bewertung: erfüllt (|Δ| ≤ 1) · Abweichung (|Δ| ≤ 3) · starke Abweichung (>3)
- ▸Multiplikatoren pro Lehrform mit Override
- ▸PDF-Export via OpenPDF für offizielle Abrechnung
03.02 · Dekan-Cockpit · Aggregation
Deputat-Gesamtsicht
Tabellarische Übersicht aller Professor-Deputate des Fachbereichs — IST, SOLL, Δ und Status pro Person nebeneinander. Sortier-, Filter- und Suchfunktionen erlauben dem Dekan, schnell Schieflagen zu erkennen.
- ▸Bulk-Sortierung nach Abweichung, Name, Status
- ▸CSV-Export für Verwaltungsberichte
- ▸Direktsprung in die einzelne Abrechnung


03.03 · Workflow-Steuerung · Deadlines
Planungsphasen-Manager
Steuerung der semesterweiten Planungsphasen — von „Vorbereitung" über „Modul-Pflege" und „Dozentenzuweisung" bis „Freigabe". Jede Phase hat Start- und End-Datum, Verantwortliche und Status; Spring @Scheduled-Jobs verschicken Erinnerungs-E-Mails an Säumige.
- ▸Phasen lassen sich aktivieren, sperren und versioniert kopieren
- ▸Automatische Reminder bei nahenden Deadlines
- ▸Phase-spezifische Sichtbarkeitsregeln für UI-Bereiche
04 / Dekanat
Stammdaten & Module
Saubere Stammdaten sind Voraussetzung für eine korrekte Planung. Vier eigenständige Verwaltungsbereiche kümmern sich um Module, Modulkatalog, Dozenten und Semester.

04.01 · Stammdaten · Data-Tables
Modul-Verwaltung (CRUD)
Vollständige CRUD-Operationen auf den Modul-Stammdaten: Modulnummer, Titel, ECTS, SWS, Lehrform, zugeordneter Studiengang. Validierung verhindert inkonsistente Datensätze (z. B. SWS ohne Lehrform).
- ▸Inline-Editing mit Optimistic Updates
- ▸Versionsführung pro Modul für Curriculum-Änderungen
- ▸Pflichtfeld-Validierung clientseitig & serverseitig
04.02 · Suchbarer Read-Only-Katalog
Modulkatalog
Lesefreundliche Sicht auf den gesamten Modulkatalog mit Volltextsuche und Filter nach Studiengang, ECTS, Pflicht/Wahl. Wird vom Wizard als Quelle für Modulauswahl genutzt und ist für alle Rollen einsehbar.
- ▸Fuzzy-Suche über Modulnummer und Titel
- ▸Filter nach Studiengang, Semester, Modultyp
- ▸Detail-Drawer mit Modulbeschreibung und Curriculum-Verortung


04.03 · Personalstammdaten · Rollen
Dozenten-Verwaltung
Verwaltung aller Lehrenden — Professoren, Lehrbeauftragte und Vertretungen. Pro Person werden Rolle, Vertragsumfang (volle/halbe Stelle), Netto-Lehrverpflichtung in SWS und Sonderaufgaben gepflegt. Bildet die Datenbasis für die Deputatsberechnung.
- ▸Rollen-zentrierte RBAC-Zuweisung pro Person
- ▸Verlauf von Stellenanteil und Ermäßigungen
- ▸Verknüpfung zum Login-Konto (1:1)
04.04 · Zeitliche Strukturen · Wiederverwendbar
Semester-Verwaltung
Anlage und Konfiguration von Sommer- und Wintersemestern. Jedes Semester hat eigene Phasen, Stichtage, eine Liste angebotener Module und Statistiken. Semester können geklont werden, um neue Planungszyklen schnell aufzusetzen.
- ▸Semester-Klonen mit allen Modul-Zuordnungen
- ▸Semesterspezifische Stichtage und Phasen
- ▸Read-Only-Modus für abgeschlossene Semester

05 / Dekanat
Aufträge & Konfiguration
Über das reine Modul-Lehren hinaus haben Lehrende viele weitere Aufgaben — Prüfungsausschuss, Studiengangsleitung, Mentoring. Diese werden über Semesteraufträge erfasst und können wiederverwendbar als Vorlage abgelegt werden.

05.01 · Funktionszuweisung · SWS-Ermäßigungen
Semesteraufträge & Funktionen
Erfassung aller nicht-modulbezogenen Aufgaben pro Semester: Studiengangsleitung, Akkreditierung, Prüfungsausschuss usw. Jede Funktion ist mit einer SWS-Ermäßigung verknüpft, die in die Deputatsberechnung einfließt.
- ▸Funktions-Katalog mit Standard-Ermäßigungen
- ▸Mehrere Funktionen pro Person und Semester
- ▸Begründungsfelder für Abweichungen vom Standard
05.02 · Wiederverwendung · Best Practices
Planungsvorlagen
Wiederverwendbare Templates für typische Semester-Konfigurationen. Vor allem hilfreich, wenn sich Pflichtprogramm und Funktionen über Jahre wenig ändern — eine Vorlage spart das manuelle Anlegen.
- ▸Templates lassen sich freigeben für andere Studiengänge
- ▸Versionsführung pro Template
- ▸Materialisierung mit einem Klick in neue Planungen


05.03 · Konfiguration · Defaults
System- & Benutzereinstellungen
Konfigurationszentrale für system- und benutzerbezogene Defaults — SWS-Obergrenzen, Standard-Multiplikatoren, E-Mail-Templates, Benachrichtigungsregeln. Änderungen werden versioniert protokolliert.
- ▸SWS-Obergrenzen zentral pflegbar (Praxisseminar, Master, Betreuung)
- ▸E-Mail-Templates mit Platzhalter-Vorschau
- ▸Audit-Log jeder Konfigurationsänderung
06 / Anerkennung
Anerkennung — Studierenden-Portal
Zweite App im DigiDekan-Ökosystem: ein eigenständiges Portal, über das Studierende Anerkennungsanträge für extern erbrachte Leistungen stellen — komplett asynchron, mit eigenen Routen und eigenem Auth-Setup.

06.01 · Eigene Auth-Domäne
Studierenden-Login
Separater Login für Studierende — eigenes Auth-Schema, eigene Session-Lebensdauer, eigener Token-Issuer. Strikte Trennung von der Mitarbeiter-Authentifizierung verhindert Rollenvermischung.
- ▸E-Mail-Verifikation bei Erstanmeldung
- ▸Passwort-Reset mit Time-Boxed-Tokens
- ▸Geräte-spezifische Refresh-Tokens
06.02 · Antragserstellung · Upload
5-Schritte-Anerkennungs-Wizard
Geführter Antrags-Wizard in 5 Schritten: Persönliche Angaben → Herkunfts-Hochschule → zu anerkennende Module → Dokument-Upload (Leistungsnachweis, Modulbeschreibung) → Zusammenfassung & Einreichen. Jeder Schritt ist auch als Entwurf speicherbar.
- ▸Drag & Drop-Upload mit Virus-Scan und Größen-Validierung
- ▸PDF-Vorschau direkt im Browser
- ▸Resume-fähig — Studierende können Antrag pausieren

07 / Anerkennung
Anerkennung — Workflow & Verwaltung
Sobald ein Antrag eingereicht ist, durchläuft er einen 6-stufigen Workflow mit klaren Verantwortlichkeiten — Studierende, Verwaltung, fachprüfende Dozenten. Jeder Statuswechsel löst automatische E-Mail-Benachrichtigungen aus.

07.01 · Workflow-Steuerung · Bulk-Aktionen
Admin-Dashboard für Anträge
Verwaltungs-Cockpit: alle eingehenden Anträge mit Status, Antragsteller, Modul-Anzahl und Tagen seit Einreichung. Filter, Sortierung und Bulk-Operationen (z. B. mehrere Anträge gleichzeitig an Dozenten zuweisen).
- ▸Filter nach Status, Studiengang, Dozent
- ▸Bulk-Zuweisung an Fachprüfer
- ▸SLA-Indikator: Tage seit letzter Aktion
07.02 · 6-Stufen-Workflow · State-Machine
Antragsdetail mit Status-Timeline
Vollständige Antragsansicht mit 6-stufiger Status-Timeline: Entwurf → Eingereicht → In Prüfung → Geprüft → Ergebnis mitgeteilt → Abgeschlossen. Eine Nachforderung kann den Status von „In Prüfung" zurück auf „Eingereicht" setzen — die State-Machine im Backend stellt sicher, dass nur erlaubte Übergänge passieren.
- ▸Zeitstempel und verantwortliche Person pro Statuswechsel
- ▸Nachforderungs-Schleife mit Frist-Tracking
- ▸Dokumenten-Anhänge pro Status sichtbar


07.03 · Begutachtung · Notenmapping
Fachliche Prüfung durch Dozent
Der zuständige Dozent prüft fachlich, ob die extern erbrachte Leistung dem Hochschul-Modul entspricht. Eingabefelder für Note (mit automatischem Notenmapping zwischen Skalen), Begründung und Empfehlung (anerkannt / nicht anerkannt / Auflage).
- ▸Notenmapping mit Default-Tabelle (z. B. ECTS → deutsches System)
- ▸Kommentar-Pflichtfeld bei Ablehnung
- ▸Direktes Speichern eines Gutachtens als PDF
07.04 · Spring Scheduling · SMTP · Templates
Auto-Benachrichtigungen
Alle Statuswechsel lösen automatische E-Mails mit Template-Rendering aus — Studierende werden über Einreichungs-Bestätigung, Nachforderungen und Ergebnis informiert, Dozenten über neue Prüfungen. Spring @Scheduled-Jobs verschicken zusätzlich Erinnerungen bei Inaktivität nach 7 und 14 Tagen.
- ▸Templates pro Statuswechsel mit Platzhalter-Engine
- ▸Versand-Log mit Retry-Mechanik bei SMTP-Fehlern
- ▸Erinnerungs-Logik via Scheduler bei Säumigkeit

Code
Auszüge
SWS/Deputat-Berechnungs-Engine
javaDomain-Service in Spring Boot — berechnet alle SWS-Summen pro Professor mit Obergrenzen (Praxisseminar, Projektveranstaltung, Seminar Master, Betreuung), bestimmt Differenz zur Netto-Lehrverpflichtung und Status-Bewertung (erfüllt / Abweichung / starke Abweichung) und sammelt Warnungen bei überschrittenen Caps.
@Service
@RequiredArgsConstructor
public class DeputatService {
private final DeputatsEinstellungenRepository einstellungenRepo;
public DeputatsErgebnis berechneSummen(Professor prof) {
DeputatsEinstellungen e = einstellungenRepo.getCurrent();
// Lehrtätigkeiten nach Kategorie mit Obergrenzen
Map<Kategorie, Double> nachKategorie = prof.getLehrtaetigkeiten().stream()
.collect(Collectors.groupingBy(
Lehrtaetigkeit::getKategorie,
Collectors.summingDouble(Lehrtaetigkeit::getSws)));
double praxisseminarRoh = nachKategorie.getOrDefault(Kategorie.PRAXISSEMINAR, 0.0);
double projektRoh = nachKategorie.getOrDefault(Kategorie.PROJEKTVERANSTALTUNG, 0.0);
double seminarMasterRoh = nachKategorie.getOrDefault(Kategorie.SEMINAR_MASTER, 0.0);
double sonstige = nachKategorie.getOrDefault(Kategorie.SONSTIGE, 0.0);
double praxisseminar = Math.min(praxisseminarRoh, e.getMaxSwsPraxisseminar());
double projekt = Math.min(projektRoh, e.getMaxSwsProjekt());
double seminarMaster = Math.min(seminarMasterRoh, e.getMaxSwsSeminarMaster());
double swsLehre = sonstige + praxisseminar + projekt + seminarMaster;
double lehrexport = sumSws(prof.getLehrexporte());
double vertretungen = sumSws(prof.getVertretungen());
double ermaessigungen = sumSws(prof.getErmaessigungen());
double betreuungenRoh = sumSws(prof.getBetreuungen());
double betreuungen = Math.min(betreuungenRoh, e.getMaxSwsBetreuung());
double gesamt = swsLehre + lehrexport + vertretungen + betreuungen + ermaessigungen;
double diff = gesamt - prof.getNettoLehrverpflichtung();
Bewertung bewertung = Math.abs(diff) <= 1.0 ? Bewertung.ERFUELLT
: Math.abs(diff) <= 3.0 ? Bewertung.ABWEICHUNG
: Bewertung.STARKE_ABWEICHUNG;
List<String> warnungen = new ArrayList<>();
if (praxisseminarRoh > e.getMaxSwsPraxisseminar()) {
warnungen.add("Praxisseminar: %.1f SWS, max. %.1f angerechnet"
.formatted(praxisseminarRoh, e.getMaxSwsPraxisseminar()));
}
if (betreuungenRoh > e.getMaxSwsBetreuung()) {
warnungen.add("Betreuungen: %.1f SWS, max. %.1f angerechnet"
.formatted(betreuungenRoh, e.getMaxSwsBetreuung()));
}
return DeputatsErgebnis.builder()
.swsLehre(round(swsLehre))
.gesamtdeputat(round(gesamt))
.nettoLehrverpflichtung(round(prof.getNettoLehrverpflichtung()))
.differenz(round(diff))
.bewertung(bewertung)
.warnungen(warnungen)
.build();
}
}Credit Recognition Status Timeline
tsxReact-Stepper-Komponente implementiert einen 6-Stufen-Lifecycle (Entwurf → Eingereicht → In Prüfung → Geprüft → Ergebnis mitgeteilt → Abgeschlossen) mit Nachforderung-Handling, Zurückweisung-Anzeige, rollenbasierter Sichtbarkeit und Datums-Formatierung.
const TIMELINE_STEPS: TimelineStep[] = [
{ status: 'entwurf', label: 'Entwurf', dateField: 'created_at' },
{ status: 'eingereicht', label: 'Eingereicht', dateField: 'eingereicht_am' },
{ status: 'in_pruefung', label: 'In Pruefung', dateField: 'in_pruefung_am' },
{ status: 'geprueft', label: 'Geprueft', dateField: 'geprueft_am' },
{ status: 'ergebnis_mitgeteilt', label: 'Ergebnis mitgeteilt', dateField: 'ergebnis_mitgeteilt_am' },
{ status: 'abgeschlossen', label: 'Abgeschlossen', dateField: 'abgeschlossen_am' },
];
export default function AnerkennungStatusTimeline({ antrag, viewerRolle }: AnerkennungStatusTimelineProps) {
const activeStepIndex = getActiveStepIndex(antrag.status);
const isStudent = viewerRolle === 'student';
return (
<Box>
<Stepper activeStep={activeStepIndex} orientation="vertical">
{TIMELINE_STEPS.map((step, index) => {
const dateValue = antrag[step.dateField] as string | undefined;
const isCompleted = index < activeStepIndex;
const isActive = index === activeStepIndex;
const hasNachforderung =
step.status === 'in_pruefung' &&
(antrag.status === 'nachforderung' || antrag.nachforderung_am);
return (
<Step key={step.status} completed={isCompleted}>
<StepLabel
error={isActive && antrag.status === 'nachforderung'}
>
<Box sx={{ display: 'flex', alignItems: 'center', gap: 1 }}>
<Typography variant="body2" sx={{ fontWeight: isActive ? 600 : 400 }}>
{step.label}
</Typography>
{isActive && antrag.status === 'nachforderung' && (
<Chip label="Nachforderung" size="small" color="error" variant="outlined" />
)}
</Box>
</StepLabel>
<StepContent>
{isActive && antrag.status === 'nachforderung' && antrag.nachforderung_grund && (
<Typography variant="body2" color="error.main">
Nachforderung: {antrag.nachforderung_grund}
</Typography>
)}
{step.status === 'eingereicht' && antrag.zurueckgewiesen_am && (
<Chip label="Zurueckgewiesen" size="small" color="warning" variant="outlined" />
)}
</StepContent>
</Step>
);
})}
</Stepper>
</Box>
);
}RBAC — Spring Security mit Rollen
javaKonfiguration der Rollen-basierten Zugriffskontrolle in Spring Security: granulare URL-Mapping-Regeln plus methoden-basierte Annotation per @PreAuthorize. JWT-Filter validiert Token aus dem Authorization-Header und befüllt den SecurityContext.
@Configuration
@EnableMethodSecurity(prePostEnabled = true)
@RequiredArgsConstructor
public class SecurityConfig {
private final JwtAuthenticationFilter jwtFilter;
@Bean
public SecurityFilterChain filterChain(HttpSecurity http) throws Exception {
return http
.csrf(AbstractHttpConfigurer::disable)
.sessionManagement(s -> s.sessionCreationPolicy(SessionCreationPolicy.STATELESS))
.authorizeHttpRequests(auth -> auth
.requestMatchers("/api/auth/**").permitAll()
.requestMatchers("/api/dekanat/**").hasRole("DEKAN")
.requestMatchers("/api/deputat/own/**").hasAnyRole("DEKAN", "PROFESSOR")
.requestMatchers("/api/anerkennung/pruefung/**").hasRole("DOZENT")
.anyRequest().authenticated())
.addFilterBefore(jwtFilter, UsernamePasswordAuthenticationFilter.class)
.build();
}
}
// Methoden-basierte Absicherung im Controller
@RestController
@RequestMapping("/api/semester")
@RequiredArgsConstructor
public class SemesterPlanungController {
private final PlanungService planung;
@PreAuthorize("hasAnyRole('DEKAN', 'VERWALTUNG')")
@PostMapping("/{id}/freigabe")
public ResponseEntity<PlanungDto> freigeben(@PathVariable Long id, Principal user) {
return ResponseEntity.ok(planung.freigeben(id, user.getName()));
}
}