12 KiB
Diplomarbeitsbuch
1. Einleitung
Ausgangssituation
Motivation
Kurzbeschreibung des Projekts
Persönlicher Aufgabenbereich
Abgrenzung der Arbeit
Die Datenbankinfrastruktur war zum Projektstart bereits vorhanden und wurde nicht im Rahmen dieser Arbeit konzipiert. Die Diplomarbeit beschränkt sich auf die Entwicklung der Anwendungsschicht, bestehend aus CMS-Konfiguration, Modul- und Theme-Entwicklung.
Individuelle Themenstellung
3. Projektumfeld & Rahmenbedingungen
Einsatz eines bestehenden CMS (Oqtane)
Teamarbeit
Das Projektteam wurde im Verlauf des Projekts von sechs auf drei Personen reduziert.
Schulisches Umfeld (HTL)
Zeitliche Rahmenbedingungen
4. Technologischer Überblick
4.1 Web-Entwicklung mit ASP.NET & C#
Backend-Logik
API-basierte Kommunikation
Zusammenspiel mit Oqtane
4.2 Oqtane – Überblick
Grundidee & Architektur
Modul- & Theme-Konzept
Vorteile für das Projekt
4.3 CMS-Grundkonfiguration
Initiale Einrichtung
Modul-Integration
Rollen & Berechtigungen
Grundlegende Systemeinstellungen
5. System- und Lösungsarchitektur
Gesamtarchitektur des Systems
Einordnung von CMS, Modulen und Theme
Datenfluss
Architekturentscheidungen
6. Entwicklung des Oqtane Themes
Ziel des Themes
Technische Umsetzung
Herausforderungen
7. Umsetzung der Module
7.1 Anmeldetool
Ziel des Moduls
Frontend (Eingabemaske)
Backend-Logik
API-Schnittstelle
Datenauswertung
UX-Überlegungen
7.2 Hall of Fame
Das Hall-of-Fame-Modul ist ein Oqtane-Modul, das ehemalige Absolventinnen und Absolventen der Schule auf der Vereinswebseite präsentiert. Es wurde als eigenständiges, wiederverwendbares Modul innerhalb des Oqtane-Frameworks entwickelt und ermöglicht registrierten Benutzerinnen und Benutzern, sich selbst mit einem persönlichen Profil einzutragen. Die Einträge werden erst nach bewusster Veröffentlichung durch die jeweilige Person auf der öffentlichen Seite angezeigt, können als PDF exportiert werden und unterliegen einem Meldesystem zur Qualitätssicherung.
Datenmodell
Das Modul verwendet zwei Entitäten, die in der Datenbank als Tabellen abgebildet werden.
Entität HallOfFame
Die zentrale Entität repräsentiert einen einzelnen Absolventeneintrag und wird in der Datenbanktabelle SZUAbsolventenvereinHallOfFame gespeichert.
| Spalte | Datentyp | Beschreibung |
|---|---|---|
HallOfFameId |
int (PK, Auto-Inkrement) |
Primärschlüssel |
ModuleId |
int (FK → Module) |
Fremdschlüssel zur Oqtane-Modulinstanz |
Name |
string |
Name der Person |
Year |
int |
Abschlussjahrgang |
Description |
string |
Beschreibung bzw. Werdegang |
Image |
string |
Relativer Pfad zum hochgeladenen Foto |
Link |
string |
Optionaler externer Link |
Status |
string (max. 50) |
Veröffentlichungsstatus: „Draft" oder „Published" |
UserId |
int |
ID der Benutzerin bzw. des Benutzers, der den Eintrag erstellt hat |
IsReported |
bool |
Kennzeichnung, ob der Eintrag gemeldet wurde |
ReportReason |
string |
(Legacy) Ursprüngliches Feld für Meldegrund, abgelöst durch die Report-Tabelle |
CreatedBy |
string |
Erstellt von (Audit) |
CreatedOn |
DateTime |
Erstellzeitpunkt (Audit) |
ModifiedBy |
string |
Zuletzt geändert von (Audit) |
ModifiedOn |
DateTime |
Zeitpunkt der letzten Änderung (Audit) |
Die Entität implementiert das Oqtane-Interface IAuditable, wodurch die Audit-Felder automatisch vom Framework befüllt werden. Der Fremdschlüssel ModuleId verknüpft jeden Eintrag mit einer bestimmten Modulinstanz und ermöglicht so den Multi-Tenant-Betrieb: Mehrere Hall-of-Fame-Module auf verschiedenen Seiten der Website verwalten jeweils unabhängige Datensätze. |
||
| Entität HallOfFameReport | ||
Die zweite Entität bildet einzelne Meldungen zu einem Eintrag ab und wird in der Tabelle SZUAbsolventenvereinHallOfFameReport gespeichert. |
||
| Spalte | Datentyp | Beschreibung |
| -------- | ---------- | -------------- |
HallOfFameReportId |
int (PK, Auto-Inkrement) |
Primärschlüssel |
HallOfFameId |
int (FK → SZUAbsolventenvereinHallOfFame) |
Zugehöriger Eintrag |
Reason |
string |
Meldegrund |
CreatedBy |
string |
Erstellt von (Audit) |
CreatedOn |
DateTime |
Erstellzeitpunkt (Audit) |
ModifiedBy |
string |
Zuletzt geändert von (Audit) |
ModifiedOn |
DateTime |
Zeitpunkt der letzten Änderung (Audit) |
Der Fremdschlüssel zu SZUAbsolventenvereinHallOfFame ist mit kaskadierendem Löschen konfiguriert, sodass beim Löschen eines Eintrags automatisch alle zugehörigen Meldungen entfernt werden. Zwischen den beiden Entitäten besteht somit eine 1:n-Beziehung: Ein Eintrag kann beliebig viele Meldungen besitzen. |
Datenbankmigrationen
Die Datenbankstruktur wird über Entity Framework Core Migrationen versioniert verwaltet. Oqtane verwendet ein eigenes Migrationssystem, das auf der Klasse MultiDatabaseMigration basiert und die Kompatibilität mit verschiedenen Datenbankanbietern sicherstellt.
| Migration | Versionsnummer | Inhalt |
|---|---|---|
InitializeModule |
01.00.00.00 |
Erstellt die Haupttabelle mit allen Grundspalten (Name, Year, Description, Image, Link, Status, UserId) sowie den Audit-Spalten |
AddReportingColumns |
01.00.00.02 |
Erweitert die Haupttabelle um die Spalten IsReported und ReportReason |
AddReportTable |
01.00.00.03 |
Erstellt die eigenständige Report-Tabelle mit Fremdschlüssel zur Haupttabelle |
| Jede Migration definiert sowohl eine Aufwärts- als auch eine Abwärtsmethode, sodass ein Rollback möglich ist. |
Benutzeroberfläche (Razor-Komponenten)
Das Modul umfasst vier Blazor-Razor-Komponenten.
Index.razor – Übersichtsseite
Die Übersichtsseite zeigt alle veröffentlichten Einträge in einem responsiven Kartenlayout mit drei Spalten auf Desktop-Breite. Die Funktionalität umfasst eine Echtzeit-Textsuche über Name und Beschreibung, eine umschaltbare Sortierung nach Datum, Name oder Jahrgang sowie eine Kartenanzeige mit Bild, Name, Jahrgang und gekürzter Beschreibung. Administratorinnen und Administratoren sehen zusätzlich Warnmeldungen bei gemeldeten Einträgen und einen Lösch-Button. Angemeldete Benutzerinnen und Benutzer können über einen eigenen Button ihren Eintrag erstellen oder bearbeiten.
Edit.razor – Erstellungs- und Bearbeitungsseite
Die Edit-Komponente dient sowohl zum Erstellen als auch zum Bearbeiten eines Eintrags. Sie bietet Formularfelder für Name, Jahrgang, Beschreibung (mit Live-Zeichenzähler), Foto-Upload und Link. Über zwei Speicheroptionen kann zwischen Entwurf und Veröffentlichung gewählt werden. Eine Eigentümerprüfung verhindert das Bearbeiten fremder Einträge, und eine Duplikatprüfung verhindert das Erstellen mehrerer Einträge pro Person.
Details.razor – Detailseite
Die Details-Komponente zeigt einen einzelnen Eintrag in einem zweispaltigen Layout mit unscharfem Bildhintergrund. Administratorinnen und Administratoren sehen bei gemeldeten Einträgen eine Liste aller Meldungen mit Lösch-Button. Ein modaler Dialog ermöglicht die PDF-Vorschau sowie den Download. Die Meldefunktion wird über die zentrale IReportUI-Komponente eingebunden.
Settings.razor – Moduleinstellungen
Die Settings-Komponente bietet eine einfache Oberfläche für Moduleinstellungen über Oqtanes Setting-Service.
Gemeinsame Melde-Komponente (IReportUI)
Die Meldefunktion in der Detailseite ist nicht direkt im Hall-of-Fame-Modul implementiert, sondern wird über eine zentrale Schnittstelle aus dem Interfaces-Paket eingebunden. Das Hall-of-Fame-Modell implementiert das Interface IReportable, das eine Entität als meldbar kennzeichnet. In der Detailseite wird per Dependency Injection eine IReportUI-Implementierung injiziert – die konkrete ReportComponent stammt dabei aus dem Admin-Modul und stellt den Melden-Button samt modalem Dialog bereit. Die Komponente wird über Blazors DynamicComponent dynamisch gerendert. Ist keine Implementierung im Container registriert, wird die Meldefunktion schlicht nicht angezeigt. Dieses Konzept ermöglicht es, die Melde-Oberfläche zentral zu pflegen und in beliebig vielen weiteren Modulen wiederzuverwenden, ohne dass die einzelnen Module die Melde-Logik selbst implementieren müssen.
PDF-Export mit QuestPDF
Für die Generierung der PDF-Dokumente wird die Open-Source-Bibliothek QuestPDF in der Community-Edition eingesetzt. Im Server-Projekt wurde ein benutzerdefiniertes MSBuild-Target erstellt, das nach jedem Build automatisch die QuestPDF-DLL sowie die plattformspezifischen nativen Bibliotheken in das bin-Verzeichnis des Oqtane-Servers kopiert. Dies ist notwendig, weil Oqtane Module zur Laufzeit dynamisch lädt und QuestPDF native Abhängigkeiten (unter anderem die SkiaSharp-Rendering-Engine) benötigt. Das PDF-Design folgt einem Glasmorphismus-Ansatz. Jede Seite hat das Format DIN A4 ohne Ränder. Über die Layers-API von QuestPDF wird das Hintergrundbild von der Inhaltsebene getrennt. Der Name wird in 36 Punkt ExtraBold mit Großbuchstaben und Zeichenabstand dargestellt, der Jahrgang in 15 Punkt mit erhöhtem Zeichenabstand und die Beschreibung in 11 Punkt mit 1,5-fachem Zeilenabstand. Der Glaseffekt wird durch halbtransparente dunkle Hintergründe mit mehrschichtigen Rahmen unterschiedlicher Transparenz erzeugt.