first commit
This commit is contained in:
commit
405df0a122
3083 changed files with 69203 additions and 0 deletions
590
dev/presswave/MIGRATION-TO-LARAVEL.md
Normal file
590
dev/presswave/MIGRATION-TO-LARAVEL.md
Normal file
|
|
@ -0,0 +1,590 @@
|
|||
# Migration der Presswave Landingpage zu Laravel/Livewire
|
||||
|
||||
Dokumentation der Konvertierung der React/TypeScript Presswave-Landingpage zu Laravel Blade + Livewire für Business Portal 24.
|
||||
|
||||
**Datum:** 15. Oktober 2025
|
||||
**Ziel-Domain:** businessportal24.test
|
||||
**Theme-Farben:** Primary #cf3628 (Rot), Secondary #f0834a (Orange)
|
||||
|
||||
---
|
||||
|
||||
## 1. Analyse der Quellstruktur
|
||||
|
||||
### Ursprüngliche React-Struktur (dev/presswave)
|
||||
```
|
||||
src/
|
||||
├── pages/
|
||||
│ └── Index.tsx # Haupt-Landingpage
|
||||
├── components/
|
||||
│ ├── Header.tsx # Navigation & Suche
|
||||
│ ├── FilterBar.tsx # Filter-Komponente
|
||||
│ ├── PressReleaseCard.tsx # Karten-Komponente für Pressemitteilungen
|
||||
│ └── BurgerMenu.tsx # Mobile Navigation
|
||||
└── assets/
|
||||
└── *.jpg # Bilder
|
||||
```
|
||||
|
||||
### Hauptkomponenten identifiziert:
|
||||
1. **Header** - Sticky Navigation mit Logo, Suchleiste und CTA-Buttons
|
||||
2. **FilterBar** - Sticky Filter mit Zeitraum, Branche, Region und Sortierung
|
||||
3. **Hero Section** - Gradient-Banner mit Überschrift
|
||||
4. **Featured Section** - 3-spaltiges Grid mit hervorgehobenen Releases
|
||||
5. **Main Grid** - 3-spaltiges Responsive Grid mit allen Releases
|
||||
6. **Footer** - 4-spaltige Link-Struktur mit Social Media
|
||||
|
||||
---
|
||||
|
||||
## 2. Laravel Blade Struktur erstellt
|
||||
|
||||
### Haupt-Blade-Datei
|
||||
**Pfad:** `resources/views/web/businessportal24.blade.php`
|
||||
|
||||
```blade
|
||||
@extends('web.layouts.web-master')
|
||||
|
||||
@section('content')
|
||||
<main class="min-h-screen flex flex-col">
|
||||
<livewire:web.header />
|
||||
<livewire:web.filter-bar />
|
||||
<!-- Hero Banner -->
|
||||
<!-- Featured Section -->
|
||||
<livewire:web.featured-releases />
|
||||
<!-- Main Grid -->
|
||||
<livewire:web.press-releases-grid />
|
||||
<livewire:web.footer />
|
||||
</main>
|
||||
@endsection
|
||||
```
|
||||
|
||||
**Features:**
|
||||
- Verwendet CSS-Variablen für Theme-Farben: `var(--color-primary)` und `var(--color-secondary)`
|
||||
- Animationen via CSS Keyframes (`@keyframes fade-in-up`)
|
||||
- Responsive Design mit Tailwind CSS
|
||||
- Alpine.js für interaktive Elemente
|
||||
|
||||
---
|
||||
|
||||
## 3. Livewire-Komponenten erstellt
|
||||
|
||||
### 3.1 Header-Komponente
|
||||
**Pfad:** `resources/views/livewire/web/header.blade.php`
|
||||
|
||||
**Funktionen:**
|
||||
- Sticky Header mit Gradient-Border-Top
|
||||
- Responsive Suchleiste (Desktop & Mobile)
|
||||
- Burger-Menü für Mobile
|
||||
- Logo mit dynamischem Gradient
|
||||
- CTA-Buttons: "Anmelden" und "Veröffentlichen"
|
||||
|
||||
**Livewire Properties:**
|
||||
```php
|
||||
public $searchQuery = '';
|
||||
public $showMobileSearch = false;
|
||||
```
|
||||
|
||||
**Alpine.js Integration:**
|
||||
- Mobile Search Toggle
|
||||
- Smooth Transitions
|
||||
|
||||
---
|
||||
|
||||
### 3.2 FilterBar-Komponente
|
||||
**Pfad:** `resources/views/livewire/web/filter-bar.blade.php`
|
||||
|
||||
**Funktionen:**
|
||||
- Sticky Position unterhalb Header (top-16)
|
||||
- 4 Filter-Dropdowns: Zeitraum, Branche, Region, Sortierung
|
||||
- Active Filters Display mit Remove-Buttons
|
||||
- "Alle zurücksetzen" Button
|
||||
- Live-Wire: Real-time Filtering
|
||||
|
||||
**Livewire Properties:**
|
||||
```php
|
||||
public $timeframe = '7';
|
||||
public $industry = 'all';
|
||||
public $region = 'all';
|
||||
public $sortBy = 'newest';
|
||||
public $activeFilters = [];
|
||||
```
|
||||
|
||||
**Events:**
|
||||
```php
|
||||
$this->dispatch('filters-updated', [...]);
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### 3.3 PressReleaseCard-Komponente
|
||||
**Pfad:** `resources/views/components/web/press-release-card.blade.php`
|
||||
|
||||
**Props:**
|
||||
- `title`, `teaser`, `company`, `industry`, `region`, `date`
|
||||
- `hasImage`, `hasPdf`, `companyLogo`, `slug`, `imageUrl`
|
||||
|
||||
**Features:**
|
||||
- Image Preview mit Lazy Loading
|
||||
- Company Logo Overlay
|
||||
- Meta-Informationen (Branche, Region, Datum)
|
||||
- Badges für Medien (Bild, PDF)
|
||||
- Hover-Effekte: Scale & Border-Color
|
||||
- Transition-Animationen (300ms)
|
||||
|
||||
**CSS-Klassen:**
|
||||
```css
|
||||
.card {
|
||||
@apply hover:scale-[1.02] hover:border-primary/20;
|
||||
@apply transition-all duration-300;
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### 3.4 Featured Releases-Komponente
|
||||
**Pfad:** `resources/views/livewire/web/featured-releases.blade.php`
|
||||
|
||||
**Layout:**
|
||||
- 3-spaltiges Grid (lg:grid-cols-3)
|
||||
- Linke Seite: 1 große Featured Card (lg:col-span-2)
|
||||
- Rechte Seite: 2 gestapelte Cards
|
||||
|
||||
**Mock-Daten:**
|
||||
- 3 Releases mit unterschiedlichen Bildern (Unsplash)
|
||||
- Verschiedene Branchen: IT, Energie, Finanzen
|
||||
|
||||
---
|
||||
|
||||
### 3.5 Press Releases Grid-Komponente
|
||||
**Pfad:** `resources/views/livewire/web/press-releases-grid.blade.php`
|
||||
|
||||
**Layout:**
|
||||
- Responsive Grid: 1 col (mobile), 2 cols (md), 3 cols (lg)
|
||||
- 6 Mock-Releases
|
||||
|
||||
**Features:**
|
||||
- Verwendet `x-web.press-release-card` Komponente
|
||||
- Loop durch `$releases` Array
|
||||
|
||||
---
|
||||
|
||||
### 3.6 Footer-Komponente
|
||||
**Pfad:** `resources/views/livewire/web/footer.blade.php`
|
||||
|
||||
**Layout:**
|
||||
- 4-spaltiges Grid (md:grid-cols-4)
|
||||
- Spalten: Unternehmen, Services, Rechtliches, Social Media
|
||||
- Theme-Toggle Button (Alpine.js)
|
||||
|
||||
**Links:**
|
||||
- Interne Links: `/ueber-uns`, `/kontakt`, `/preise`, etc.
|
||||
- Externe Links: LinkedIn, Twitter (target="_blank")
|
||||
|
||||
---
|
||||
|
||||
## 4. Theme & Styling
|
||||
|
||||
### 4.1 CSS-Theme-Datei
|
||||
**Pfad:** `resources/css/web/theme-businessportal24.css`
|
||||
|
||||
**Farb-Variablen (HSL):**
|
||||
```css
|
||||
--primary: 4 61% 49%; /* #cf3628 */
|
||||
--secondary: 22 84% 61%; /* #f0834a */
|
||||
```
|
||||
|
||||
**Dark Mode Support:**
|
||||
```css
|
||||
.dark {
|
||||
--background: 4 20% 10%;
|
||||
--primary: 4 61% 49%;
|
||||
/* ... */
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### 4.2 Animationen
|
||||
|
||||
**Keyframes definiert:**
|
||||
```css
|
||||
@keyframes fade-in-up {
|
||||
from { opacity: 0; transform: translateY(20px); }
|
||||
to { opacity: 1; transform: translateY(0); }
|
||||
}
|
||||
@keyframes fade-in-down { /* ... */ }
|
||||
@keyframes slide-in-right { /* ... */ }
|
||||
@keyframes scale-in { /* ... */ }
|
||||
```
|
||||
|
||||
**Utility-Klassen:**
|
||||
```css
|
||||
.animate-fade-in-up { animation: fade-in-up 0.6s ease-out forwards; }
|
||||
.animation-delay-200 { animation-delay: 0.2s; opacity: 0; }
|
||||
```
|
||||
|
||||
**Verwendung in Blade:**
|
||||
```html
|
||||
<h1 class="animate-fade-in-up">Titel</h1>
|
||||
<p class="animate-fade-in-up animation-delay-200">Text</p>
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### 4.3 Component Styles
|
||||
|
||||
**Buttons:**
|
||||
```css
|
||||
.btn-primary {
|
||||
@apply bg-gradient-to-r from-primary to-secondary;
|
||||
@apply shadow-md hover:shadow-lg;
|
||||
@apply transition-all duration-300;
|
||||
}
|
||||
```
|
||||
|
||||
**Cards:**
|
||||
```css
|
||||
.card {
|
||||
@apply rounded-xl border shadow-sm hover:shadow-lg;
|
||||
@apply transition-all duration-300;
|
||||
}
|
||||
```
|
||||
|
||||
**Badges:**
|
||||
```css
|
||||
.badge-primary {
|
||||
@apply bg-primary/10 text-primary border border-primary/20;
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 5. React → Blade/Livewire Konvertierung
|
||||
|
||||
### Mapping-Tabelle
|
||||
|
||||
| React-Konzept | Laravel-Äquivalent | Beispiel |
|
||||
|---------------|-------------------|----------|
|
||||
| `useState()` | `public $property` | `public $searchQuery = '';` |
|
||||
| `props` | `@props([...])` | `@props(['title', 'teaser'])` |
|
||||
| `onClick` | `wire:click` | `wire:click="search"` |
|
||||
| `onChange` | `wire:model.live` | `wire:model.live="timeframe"` |
|
||||
| `map()` | `@foreach` | `@foreach($releases as $release)` |
|
||||
| `x-show` (React) | `x-show` (Alpine) | `x-show="showMobileSearch"` |
|
||||
| `dispatch()` | `$this->dispatch()` | `$this->dispatch('event')` |
|
||||
| CSS-in-JS | Tailwind Classes | `class="bg-primary text-white"` |
|
||||
|
||||
---
|
||||
|
||||
### Spezifische Konvertierungen:
|
||||
|
||||
#### React Search Component:
|
||||
```tsx
|
||||
const [searchQuery, setSearchQuery] = useState('');
|
||||
|
||||
<input
|
||||
value={searchQuery}
|
||||
onChange={(e) => setSearchQuery(e.target.value)}
|
||||
/>
|
||||
```
|
||||
|
||||
#### Livewire Äquivalent:
|
||||
```php
|
||||
public $searchQuery = '';
|
||||
|
||||
<input wire:model="searchQuery" />
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
#### React Filter Update:
|
||||
```tsx
|
||||
const [timeframe, setTimeframe] = useState('7');
|
||||
|
||||
<select
|
||||
value={timeframe}
|
||||
onChange={(e) => setTimeframe(e.target.value)}
|
||||
>
|
||||
```
|
||||
|
||||
#### Livewire Äquivalent:
|
||||
```php
|
||||
public $timeframe = '7';
|
||||
|
||||
<select wire:model.live="timeframe">
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
#### React Conditional Rendering:
|
||||
```tsx
|
||||
{hasImage && (
|
||||
<Badge>Bild</Badge>
|
||||
)}
|
||||
```
|
||||
|
||||
#### Blade Äquivalent:
|
||||
```blade
|
||||
@if($hasImage)
|
||||
<span class="badge">Bild</span>
|
||||
@endif
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 6. Routing & Integration
|
||||
|
||||
### Route hinzufügen
|
||||
**Pfad:** `routes/web.php` oder `routes/domains.php`
|
||||
|
||||
```php
|
||||
Route::domain('businessportal24.test')->group(function () {
|
||||
Route::get('/', function () {
|
||||
return view('web.businessportal24');
|
||||
});
|
||||
});
|
||||
```
|
||||
|
||||
### Domain-Config
|
||||
**Pfad:** `config/domains.php`
|
||||
|
||||
```php
|
||||
'businessportal24' => [
|
||||
'domain_name' => 'businessportal24.test',
|
||||
'theme' => 'businessportal24',
|
||||
'view_prefix' => 'web',
|
||||
'assets_dir' => 'build/web',
|
||||
'color_scheme' => [
|
||||
'primary' => '#cf3628',
|
||||
'secondary' => '#f0834a',
|
||||
],
|
||||
'font' => 'Montserrat',
|
||||
],
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 7. Verbesserungen & Best Practices
|
||||
|
||||
### Implementierte Verbesserungen:
|
||||
|
||||
1. **Performance:**
|
||||
- Lazy Loading für Bilder (`loading="lazy"`)
|
||||
- CSS-Transitions statt JavaScript-Animationen
|
||||
- Livewire Live-Updates nur wo nötig
|
||||
|
||||
2. **Accessibility:**
|
||||
- `aria-label` für Icon-Buttons
|
||||
- Semantische HTML-Tags (`<header>`, `<footer>`, `<article>`)
|
||||
- Keyboard-Navigation Support
|
||||
|
||||
3. **SEO:**
|
||||
- Semantische Meta-Informationen
|
||||
- Alt-Texte für Bilder
|
||||
- Strukturierte Daten via `<article>`
|
||||
|
||||
4. **Responsive Design:**
|
||||
- Mobile-First Approach
|
||||
- Breakpoints: `sm:`, `md:`, `lg:`
|
||||
- Touch-optimierte Buttons
|
||||
|
||||
---
|
||||
|
||||
## 8. Testing & Debugging
|
||||
|
||||
### Lokales Testing:
|
||||
|
||||
1. **Vite Dev-Server starten:**
|
||||
```bash
|
||||
npm run dev:web
|
||||
```
|
||||
|
||||
2. **Laravel Dev-Server:**
|
||||
```bash
|
||||
php artisan serve
|
||||
```
|
||||
|
||||
3. **Domain-Simulation (.env):**
|
||||
```env
|
||||
DEV_SIMULATE_DOMAIN=true
|
||||
DEV_SIMULATED_DOMAIN=businessportal24.test
|
||||
```
|
||||
|
||||
4. **Browser öffnen:**
|
||||
```
|
||||
http://localhost:8000
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### Debug-Tipps:
|
||||
|
||||
**Livewire-Debugging:**
|
||||
```blade
|
||||
<div>
|
||||
{{ var_dump($searchQuery) }}
|
||||
@json($activeFilters)
|
||||
</div>
|
||||
```
|
||||
|
||||
**Alpine.js Debugging:**
|
||||
```html
|
||||
<div x-data="{ debug: true }">
|
||||
<template x-if="debug">
|
||||
<pre x-text="JSON.stringify($data, null, 2)"></pre>
|
||||
</template>
|
||||
</div>
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 9. Nächste Schritte
|
||||
|
||||
### Zu implementieren:
|
||||
|
||||
1. **Datenbank-Integration:**
|
||||
- Eloquent Model für `PressRelease`
|
||||
- Migration erstellen
|
||||
- Seeder für Test-Daten
|
||||
|
||||
2. **Pagination:**
|
||||
- Livewire Pagination implementieren
|
||||
- Infinite Scroll Option
|
||||
|
||||
3. **Suche:**
|
||||
- Laravel Scout Integration
|
||||
- Full-Text Search mit Meilisearch
|
||||
|
||||
4. **Filter-Persistenz:**
|
||||
- Query-Parameter für Filter
|
||||
- Browser-History Integration
|
||||
|
||||
5. **API:**
|
||||
- REST API für Releases
|
||||
- API-Dokumentation (Swagger)
|
||||
|
||||
6. **Admin-Panel:**
|
||||
- CRUD für Pressemitteilungen
|
||||
- Bild-Upload mit Media Library
|
||||
|
||||
---
|
||||
|
||||
## 10. Dateistruktur (Zusammenfassung)
|
||||
|
||||
```
|
||||
resources/
|
||||
├── views/
|
||||
│ ├── web/
|
||||
│ │ └── businessportal24.blade.php # Haupt-Blade
|
||||
│ ├── livewire/
|
||||
│ │ └── web/
|
||||
│ │ ├── header.blade.php
|
||||
│ │ ├── filter-bar.blade.php
|
||||
│ │ ├── featured-releases.blade.php
|
||||
│ │ ├── press-releases-grid.blade.php
|
||||
│ │ └── footer.blade.php
|
||||
│ └── components/
|
||||
│ └── web/
|
||||
│ └── press-release-card.blade.php
|
||||
└── css/
|
||||
└── web/
|
||||
└── theme-businessportal24.css # Theme-Styles
|
||||
|
||||
config/
|
||||
└── domains.php # Domain-Config
|
||||
|
||||
routes/
|
||||
└── domains.php # Routing
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 11. Lessons Learned
|
||||
|
||||
### Was gut funktioniert hat:
|
||||
|
||||
1. **Livewire für State Management:**
|
||||
- Einfache Syntax
|
||||
- Keine JS-Komplexität
|
||||
- Reaktive Updates
|
||||
|
||||
2. **Tailwind CSS:**
|
||||
- Schnelles Styling
|
||||
- Konsistentes Design
|
||||
- Responsive Utilities
|
||||
|
||||
3. **Alpine.js für UI-Interaktionen:**
|
||||
- Leichtgewichtig
|
||||
- Vue-ähnliche Syntax
|
||||
- Perfekt für kleine Interaktionen
|
||||
|
||||
### Herausforderungen:
|
||||
|
||||
1. **Komplexe React-Hooks → Livewire:**
|
||||
- Lösung: Einfachere State-Struktur
|
||||
|
||||
2. **CSS-in-JS → Tailwind:**
|
||||
- Lösung: Utility-Klassen + @layer
|
||||
|
||||
3. **React Context → Laravel:**
|
||||
- Lösung: View::share() & Config
|
||||
|
||||
---
|
||||
|
||||
## 12. Performance-Metriken
|
||||
|
||||
### Ziel-Metriken:
|
||||
|
||||
- **First Contentful Paint:** < 1.5s
|
||||
- **Time to Interactive:** < 3.5s
|
||||
- **Lighthouse Score:** > 90
|
||||
|
||||
### Optimierungen:
|
||||
|
||||
1. **Asset-Optimierung:**
|
||||
- Vite Build: Code-Splitting
|
||||
- Image Optimization (WebP)
|
||||
- CSS Minification
|
||||
|
||||
2. **Livewire-Optimierung:**
|
||||
- `wire:model.lazy` wo möglich
|
||||
- Polling vermeiden
|
||||
- Lazy-Loading von Komponenten
|
||||
|
||||
---
|
||||
|
||||
## 13. Maintenance & Updates
|
||||
|
||||
### Regelmäßige Updates:
|
||||
|
||||
1. **Dependencies:**
|
||||
```bash
|
||||
composer update
|
||||
npm update
|
||||
```
|
||||
|
||||
2. **Laravel Updates:**
|
||||
```bash
|
||||
php artisan migrate
|
||||
php artisan optimize:clear
|
||||
```
|
||||
|
||||
3. **Vite Rebuild:**
|
||||
```bash
|
||||
npm run build:web
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Kontakt & Support
|
||||
|
||||
**Entwickler:** Claude Code
|
||||
**Datum:** 15. Oktober 2025
|
||||
**Version:** 1.0.0
|
||||
|
||||
Bei Fragen oder Problemen:
|
||||
- CLAUDE.md im Root-Verzeichnis konsultieren
|
||||
- Laravel Dokumentation: https://laravel.com/docs
|
||||
- Livewire Dokumentation: https://livewire.laravel.com
|
||||
|
||||
---
|
||||
|
||||
**Ende der Dokumentation**
|
||||
Loading…
Add table
Add a link
Reference in a new issue