- Add DISCOVERY_LOG_LEVEL=debug - Add DISCOVERY_SHOW_PROGRESS=true - Temporary changes for debugging InitializerProcessor fixes on production
9.2 KiB
Architekturübersicht
Diese Dokumentation bietet einen Überblick über die Architektur des Frameworks und erklärt die grundlegenden Konzepte und Designentscheidungen.
Architekturprinzipien
Das Framework wurde nach folgenden Prinzipien entwickelt:
- Modularität: Das Framework ist in unabhängige Module aufgeteilt, die einzeln verwendet oder ausgetauscht werden können.
- Erweiterbarkeit: Alle Komponenten sind so konzipiert, dass sie einfach erweitert oder angepasst werden können.
- Testbarkeit: Die Architektur ermöglicht einfaches Testen durch klare Schnittstellen und Dependency Injection.
- Leistung: Leistungsoptimierungen sind ein integraler Bestandteil des Designs, nicht nur eine nachträgliche Überlegung.
- Sicherheit: Sicherheitsmaßnahmen sind standardmäßig aktiviert und in die Kernkomponenten integriert.
Schichtenarchitektur
Das Framework verwendet eine mehrschichtige Architektur, die eine klare Trennung der Verantwortlichkeiten ermöglicht:
+-------------------+
| Anwendung | <-- Anwendungsspezifischer Code (Controller, Models, Services)
+-------------------+
| Framework | <-- Framework-Komponenten (Routing, Validierung, Datenbank)
+-------------------+
| Infrastruktur | <-- Infrastrukturkomponenten (HTTP, Dateisystem, Cache)
+-------------------+
Anwendungsschicht
Die Anwendungsschicht enthält den anwendungsspezifischen Code, der die Geschäftslogik implementiert. Diese Schicht umfasst:
- Controller: Verarbeiten HTTP-Anfragen und geben Antworten zurück
- Models: Repräsentieren Geschäftsobjekte und Datenstrukturen
- Services: Implementieren komplexe Geschäftslogik
- Repositories: Kapseln den Datenzugriff
Framework-Schicht
Die Framework-Schicht stellt die Kernfunktionalität bereit, die von der Anwendungsschicht verwendet wird. Diese Schicht umfasst:
- Routing: Leitet Anfragen an die entsprechenden Controller weiter
- Validierung: Überprüft Benutzereingaben
- Datenbank: Bietet Datenbankabstraktion und ORM-Funktionalität
- Authentifizierung: Verwaltet Benutzerauthentifizierung und -autorisierung
- Caching: Implementiert verschiedene Caching-Strategien
Infrastrukturschicht
Die Infrastrukturschicht bietet grundlegende Dienste und Abstraktionen für die darüber liegenden Schichten. Diese Schicht umfasst:
- HTTP: Verarbeitet HTTP-Anfragen und -Antworten
- Dateisystem: Bietet Abstraktionen für Dateisystemoperationen
- Cache: Implementiert verschiedene Cache-Backends
- Logging: Bietet Logging-Funktionalität
- Events: Implementiert ein Event-System
Anfragelebenszyklus
Der Lebenszyklus einer Anfrage im Framework durchläuft mehrere Phasen:
- Bootstrapping: Die Anwendung wird initialisiert, Konfigurationen werden geladen und Dienste registriert.
- Routing: Die Anfrage wird an den entsprechenden Controller weitergeleitet.
- Middleware: Die Anfrage durchläuft die konfigurierten Middleware-Komponenten.
- Controller: Der Controller verarbeitet die Anfrage und gibt eine Antwort zurück.
- Middleware (rückwärts): Die Antwort durchläuft die Middleware-Komponenten in umgekehrter Reihenfolge.
- Antwort: Die Antwort wird an den Client gesendet.
+----------------+ +------------+ +------------+ +------------+ +----------------+
| | | | | | | | | |
| Bootstrapping | --> | Routing | --> | Middleware | --> | Controller | --> | Antwort senden |
| | | | | | | | | |
+----------------+ +------------+ +------------+ +------------+ +----------------+
Dependency Injection
Das Framework verwendet Dependency Injection (DI), um Abhängigkeiten zwischen Komponenten zu verwalten. Der DI-Container ist verantwortlich für:
- Registrierung: Dienste werden im Container registriert.
- Auflösung: Der Container löst Abhängigkeiten automatisch auf.
- Lebenszyklus: Der Container verwaltet den Lebenszyklus von Diensten (Singleton, Transient, etc.).
Beispiel für die Verwendung des DI-Containers:
// Registrierung eines Dienstes
$container->bind(UserRepositoryInterface::class, UserRepository::class);
// Auflösung eines Dienstes
$userRepository = $container->get(UserRepositoryInterface::class);
Service Provider
Service Provider sind Klassen, die Dienste im DI-Container registrieren und konfigurieren. Sie bieten einen strukturierten Weg, um Komponenten zu initialisieren und zu konfigurieren.
Beispiel für einen Service Provider:
class DatabaseServiceProvider implements ServiceProviderInterface
{
public function register(Container $container): void
{
$container->singleton(ConnectionInterface::class, function () {
return new Connection(config('database'));
});
$container->bind(QueryBuilderInterface::class, QueryBuilder::class);
}
public function boot(Container $container): void
{
// Initialisierungscode, der nach der Registrierung ausgeführt wird
}
}
Ereignissystem
Das Framework implementiert ein Ereignissystem, das die Entkopplung von Komponenten ermöglicht. Das Ereignissystem besteht aus:
- Events: Objekte, die Informationen über ein Ereignis enthalten.
- Listeners: Klassen, die auf bestimmte Ereignisse reagieren.
- Dispatcher: Verantwortlich für das Versenden von Ereignissen an registrierte Listener.
Beispiel für die Verwendung des Ereignissystems:
// Definieren eines Events
class UserRegistered
{
public function __construct(public readonly User $user) {}
}
// Definieren eines Listeners
class SendWelcomeEmail implements ListenerInterface
{
public function handle(UserRegistered $event): void
{
// E-Mail an den neuen Benutzer senden
}
}
// Registrieren des Listeners
$eventDispatcher->addListener(UserRegistered::class, SendWelcomeEmail::class);
// Auslösen des Events
$eventDispatcher->dispatch(new UserRegistered($user));
Middleware-Pipeline
Das Framework verwendet eine Middleware-Pipeline, um Anfragen zu verarbeiten. Middleware-Komponenten können:
- Anfragen vor der Verarbeitung durch den Controller modifizieren.
- Antworten nach der Verarbeitung durch den Controller modifizieren.
- Den Anfrage-/Antwort-Zyklus vollständig abbrechen.
Beispiel für eine Middleware:
class AuthenticationMiddleware implements MiddlewareInterface
{
public function process(Request $request, RequestHandlerInterface $handler): Response
{
if (!$this->isAuthenticated($request)) {
return new RedirectResponse('/login');
}
return $handler->handle($request);
}
private function isAuthenticated(Request $request): bool
{
// Überprüfen, ob der Benutzer authentifiziert ist
}
}
Konfigurationssystem
Das Framework verwendet ein flexibles Konfigurationssystem, das verschiedene Konfigurationsquellen unterstützt:
- Umgebungsvariablen: Konfiguration über
.env-Dateien. - Konfigurationsdateien: PHP-Dateien, die Konfigurationsarrays zurückgeben.
- Laufzeitkonfiguration: Dynamische Konfiguration zur Laufzeit.
Das Konfigurationssystem unterstützt auch umgebungsspezifische Konfigurationen, sodass verschiedene Einstellungen für Entwicklung, Test und Produktion verwendet werden können.
Erweiterbarkeit
Das Framework ist so konzipiert, dass es einfach erweitert werden kann:
- Interfaces: Alle Kernkomponenten definieren Interfaces, die implementiert werden können.
- Abstrakte Klassen: Viele Komponenten bieten abstrakte Basisklassen, die erweitert werden können.
- Hooks: Das Framework bietet Hooks, an denen benutzerdefinierter Code ausgeführt werden kann.
- Plugins: Das Plugin-System ermöglicht die einfache Integration von Drittanbietercode.
Sicherheitsarchitektur
Die Sicherheitsarchitektur des Frameworks umfasst mehrere Schichten:
- Eingabevalidierung: Validierung aller Benutzereingaben.
- Ausgabebereinigung: Automatische Bereinigung von Ausgaben, um XSS zu verhindern.
- CSRF-Schutz: Schutz vor Cross-Site Request Forgery.
- Authentifizierung: Flexible Authentifizierungsmechanismen.
- Autorisierung: Rollenbasierte und fähigkeitsbasierte Zugriffskontrolle.
- Web Application Firewall (WAF): Integrierte WAF zum Schutz vor gängigen Angriffen.
Leistungsoptimierungen
Das Framework implementiert verschiedene Leistungsoptimierungen:
- Caching: Mehrschichtiges Caching für Konfiguration, Routen, Views, etc.
- Lazy Loading: Komponenten werden erst geladen, wenn sie benötigt werden.
- Kompilierung: Views und Konfigurationen werden für schnelleren Zugriff kompiliert.
- Pooling: Verbindungspooling für Datenbanken und andere Ressourcen.
- Optimierte Autoloading: PSR-4-konformes Autoloading mit Optimierungen.
Weitere Informationen
- Komponenten: Detaillierte Informationen zu den Hauptkomponenten des Frameworks.
- Entwurfsmuster: Erläuterung der im Framework verwendeten Entwurfsmuster.
- Komponentendokumentation: Dokumentation der einzelnen Komponenten.