Michael Schiemer 26f87060d5
All checks were successful
Test Runner / test-php (push) Successful in 41s
Deploy Application / deploy (push) Successful in 2m58s
Test Runner / test-basic (push) Successful in 7s
fix(deploy): add build parameter to ensure Docker images are rebuilt
The deployment was only pulling code via git but not rebuilding the
Docker images, causing containers to run with stale code from the
registry image. This fixes the debug error pages still showing on
staging despite APP_DEBUG=false.
2025-11-25 04:23:38 +01:00
2025-07-17 16:24:20 +02:00
2025-07-17 16:24:20 +02:00
2025-07-17 16:24:20 +02:00
2025-11-25 04:13:25 +01:00
2025-07-17 16:24:20 +02:00
2025-05-24 07:09:22 +02:00
2025-05-18 17:03:57 +02:00
2025-07-17 16:24:20 +02:00
2025-11-08 12:15:36 +01:00

Custom PHP Framework

Ein modulares und erweiterbares PHP-Framework mit API-Client-Integration, Attribut-basiertem Routing und Production-Ready Infrastructure.

🚀 Quick Start

Development Setup

# Repository klonen
git clone https://github.com/username/framework.git
cd framework

# Mit Docker starten
make up

# Console Commands ausführen (empfohlen)
./bin/console          # Docker-Wrapper für Console
./bin/console routes:list
./bin/console db:migrate

# Oder: Manuelle Installation
composer install
npm install
# Neue Base+Override Struktur: .env.base + .env.local
# Siehe ENV_SETUP.md für Details
# Für Backward Compatibility: cp .env.example .env (wird als Fallback geladen)

📝 Hinweis zu Permissions: Verwende immer ./bin/console für Console-Commands statt php console.php. Details: docs/PERMISSIONS.md

Production Deployment

Neu im Projekt? Starte hier:

📖 Quick Start Guide - Deployment in 30 Minuten

Vollständige Deployment-Dokumentation:

Anwendung starten

Das Framework kann entweder mit dem eingebauten PHP-Webserver oder mit einem Webserver wie Apache oder Nginx ausgeführt werden.

Eingebauter PHP-Webserver

php -S localhost:8000 -t public/

Nginx-Konfiguration

server {
    listen 80;
    server_name yourdomain.com;
    root /path/to/framework/public;

    index index.php;

    location / {
        try_files $uri $uri/ /index.php?$query_string;
    }

    location ~ \.php$ {
        fastcgi_pass unix:/var/run/php/php8.1-fpm.sock;
        fastcgi_index index.php;
        fastcgi_param SCRIPT_FILENAME $realpath_root$fastcgi_script_name;
        include fastcgi_params;
    }
}

Production-Ready Features

Monitoring & Health Checks

  • 🏥 Multiple Health Endpoints - /health/summary, /health/detailed, /health/category/{category}
  • 📊 Prometheus Metrics - /metrics endpoint for monitoring integration
  • 🔍 Auto-Discovery - Automatic health check registration via attributes
  • Real-time Monitoring - Grafana dashboards for production visibility

Security

  • 🔒 SSL/TLS - Automatic Let's Encrypt certificate management
  • 🔐 Vault Integration - Encrypted secrets management
  • 🛡️ WAF - Web Application Firewall with OWASP protection
  • 🚨 Security Headers - CSP, HSTS, X-Frame-Options, etc.
  • 🔑 CSRF Protection - Automatic token-based protection

Logging

  • 📝 Structured Logging - JSON-formatted logs with context
  • 🎯 Multiple Strategies - Production, High-Performance, Debug, Staging
  • 📈 Log Aggregation - Reduce log volume by 70-90%
  • 🔄 Log Rotation - Automatic rotation with configurable retention
  • 📊 Performance Metrics - Built-in performance tracking

Deployment

  • 🚀 Zero-Downtime - Blue-green deployment support
  • 🔄 Rollback Support - Safe migration rollback architecture
  • 📦 Docker Compose - Production-ready container orchestration
  • 🤖 Ansible - Optional infrastructure as code
  • Health-Verified - Automated health checks during deployment

Architektur

Das Framework folgt einer modularen Architektur mit den folgenden Hauptkomponenten:

Core

  • Application: Steuert den Anwendungslebenszyklus
  • Container: Dependency Injection Container
  • Router: Attribute-basiertes Routing
  • Middleware: HTTP-Middleware-Chain

HTTP

DateTime-Modul für das Framework

Dieses Modul bietet eine umfassende Unterstützung für DateTime-Operationen im Framework mit einem Fokus auf Testbarkeit, Immutabilität und Zeitzonen-Unterstützung.

Hauptkomponenten

Clock-Interface

Das Clock-Interface abstrahiert den Zugriff auf die aktuelle Zeit und stellt sicher, dass Anwendungscode testbar bleibt:

// Produktionscode verwendet SystemClock
$clock = new SystemClock();
$now = $clock->now();

// Testcode kann FrozenClock verwenden
$clock = new FrozenClock('2021-01-01 00:00:00');
$frozenTime = $clock->now(); // Gibt immer das gleiche Datum zurück

FrozenClock für Tests

Die FrozenClock-Klasse ist besonders nützlich für Tests, bei denen Sie die Zeit kontrollieren müssen:

$clock = new FrozenClock('2021-01-01 00:00:00');

// Zeit vorstellen
$clock->moveForward('PT1H'); // Eine Stunde vorstellen

// Zeit zurückstellen
$clock->moveBackward('P1D'); // Einen Tag zurückstellen

// Zeit direkt setzen
$clock->setTo('2022-01-01 00:00:00');

DateTimeFormatter

Der DateTimeFormatter bietet bequeme Methoden zum konsistenten Formatieren von Datums- und Zeitwerten:

$formatter = new DateTimeFormatter();

// ISO8601-Format (für APIs und JSON)
$iso = $formatter->formatIso8601($date); // 2021-01-01T12:34:56+00:00

// SQL-Format
$sql = $formatter->formatSql($date); // 2021-01-01 12:34:56

// Nur Datum
$dateOnly = $formatter->formatDate($date); // 2021-01-01

// Benutzerdefiniertes Format
$custom = $formatter->format($date, 'd.m.Y H:i'); // 01.01.2021 12:34

DateRange

Die DateRange-Klasse ermöglicht die einfache Arbeit mit Zeiträumen:

// Zeitraum erstellen
$range = DateRange::fromStrings('2021-01-01', '2021-01-31');

// Prüfen, ob ein Datum im Bereich liegt
$isInRange = $range->contains($someDate);

// Prüfen, ob sich Bereiche überschneiden
$doOverlap = $range->overlaps($otherRange);

// Dauer berechnen
$seconds = $range->getDurationInSeconds();

DI-Container Integration

Das Modul lässt sich nahtlos in den DI-Container des Frameworks integrieren:

// In Ihrer Bootstrap-Datei oder Service-Provider
$container->singleton(Clock::class, SystemClock::class);
$container->singleton(DateTimeFormatter::class, DateTimeFormatter::class);

// Oder den bereitgestellten ServiceProvider verwenden
$dateTimeServiceProvider = new DateTimeServiceProvider();
$dateTimeServiceProvider->register($container);

Testunterstützung

Für Tests kann die FrozenClock einfach registriert werden:

// In Ihrem Test-Setup
$frozenClock = new FrozenClock('2021-01-01 00:00:00');
$container->instance(Clock::class, $frozenClock);

// Zeit während des Tests manipulieren
$frozenClock->moveForward('PT1H');
  • Request/Response: HTTP-Nachrichten
  • HttpClient: HTTP-Client für API-Anfragen

API

  • ApiRequestTrait: Hilfsklasse für API-Clients
  • Integrierte Clients: RapidMail, Shopify

Features

  • Attribut-basiertes Routing: Deklaratives Routing mit PHP 8 Attributen
  • Dependency Injection: Automatische Auflösung von Abhängigkeiten
  • Middleware-System: Erweiterbare HTTP-Middleware-Chain
  • API-Clients: Integrierte Clients für gängige APIs
  • Konfigurationsmanagement: Flexible Konfiguration mit Umgebungsvariablen

Beispiele

Controller mit Routing

<?php

namespace App\Application\Example;

use App\Framework\Attributes\Route;
use App\Framework\Router\Result\JsonResult;

final class ExampleController
{
    #[Route(path: '/api/example', method: 'GET')]
    public function getExample(): JsonResult
    {
        return new JsonResult([
            'success' => true,
            'message' => 'Hello World!'
        ]);
    }
}

API-Client verwenden

<?php

namespace App\Application\Newsletter;

use App\Framework\Attributes\Route;use App\Framework\Http\Status;use App\Framework\Router\Result\JsonResult;use App\Infrastructure\Api\RapidMailClient;use Archive\Config\ApiConfig;

final class NewsletterController
{
    private RapidMailClient $client;

    public function __construct()
    {
        $this->client = new RapidMailClient(
            ApiConfig::RAPIDMAIL_USERNAME->value,
            ApiConfig::RAPIDMAIL_PASSWORD->value
        );
    }

    #[Route(path: '/newsletter/register', method: 'POST')]
    public function register(NewsletterRequest $request): JsonResult
    {
        $result = $this->client->addRecipient(
            $request->name,
            $request->email,
            ApiConfig::getRapidmailListId()
        );

        return new JsonResult(
            ['success' => true, 'data' => $result],
            Status::CREATED
        );
    }
}

Erweiterung

Das Framework kann durch eigene Komponenten und Module erweitert werden:

  • Eigene Middleware: Erstellen Sie benutzerdefinierte Middleware-Klassen
  • Attribute: Definieren Sie eigene Attribute und Mapper
  • API-Clients: Integrieren Sie zusätzliche APIs mit dem ApiRequestTrait

Lizenz

MIT

# Starten
make up

# Logs anzeigen
make logs

# Setup-Playbook (Server einmalig vorbereiten)
make setup

# Deployment (Code + Compose auf Server bringen)
make deploy
# CI/CD Pipeline Test - Fri Nov  7 08:54:41 PM CET 2025
# CI/CD Pipeline Test Production - Sat Nov  8 12:15:35 PM CET 2025
Description
Main application repository
Readme 89 MiB
Languages
PHP 88.3%
JavaScript 6%
Hack 2.9%
Shell 1.1%
CSS 1.1%
Other 0.4%