- Wired the checkout wizard for Google “comfort login”: added Socialite controller + dependency, new Google env
hooks in config/services.php/.env.example, and updated wizard steps/controllers to store session payloads, attach packages, and surface localized success/error states. - Retooled payment handling for both Stripe and PayPal, adding richer status management in CheckoutController/ PayPalController, fallback flows in the wizard’s PaymentStep.tsx, and fresh feature tests for intent creation, webhooks, and the wizard CTA. - Introduced a consent-aware Matomo analytics stack: new consent context, cookie-banner UI, useAnalytics/ useCtaExperiment hooks, and MatomoTracker component, then instrumented marketing pages (Home, Packages, Checkout) with localized copy and experiment tracking. - Polished package presentation across marketing UIs by centralizing formatting in PresentsPackages, surfacing localized description tables/placeholders, tuning badges/layouts, and syncing guest/marketing translations. - Expanded docs & reference material (docs/prp/*, TODOs, public gallery overview) and added a Playwright smoke test for the hero CTA while reconciling outstanding checklist items.
This commit is contained in:
@@ -7,21 +7,21 @@
|
||||
## Action Items
|
||||
|
||||
### Wizard Foundations
|
||||
- [ ] Rebuild the package step with a side panel for comparable packages and reset payment state when the selected package changes.
|
||||
- [ ] Redesign the payment step: Stripe and PayPal happy path, failure, retry; add subscription handling for reseller plans.
|
||||
- [ ] Update the confirmation step and surface the admin link inside `resources/js/pages/Profile/Index.tsx`.
|
||||
- [x] Rebuild the package step with a side panel for comparable packages and reset payment state when the selected package changes (see `resources/js/pages/marketing/checkout/steps/PackageStep.tsx`).
|
||||
- [x] Redesign the payment step: Stripe and PayPal happy path, failure, retry; add subscription handling for reseller plans. *(Stripe intent lifecycle + PayPal subscription flow now share status alerts, retry logic, and plan gating in `PaymentStep.tsx`.)*
|
||||
- [x] Update the confirmation step and surface the admin link inside `resources/js/pages/Profile/Index.tsx`. *(Handled via `ConfirmationStep.tsx` + wizard callbacks redirecting to `/settings/profile` and `/event-admin`.)*
|
||||
|
||||
### Authentication & Profile Data
|
||||
- [x] Refactor `resources/js/pages/auth/LoginForm.tsx` and `RegisterForm.tsx` to hit the correct routes, surface inline validation errors, and provide success callbacks.
|
||||
- [ ] Add optional comfort login: Google sign-in and enrichment of missing registration fields via the payment provider, combining the prior step 2/3 concept.
|
||||
- [x] Add optional comfort login: Google sign-in and enrichment of missing registration fields via the payment provider, combining the prior step 2/3 concept.
|
||||
|
||||
### Backend Alignment
|
||||
- [ ] Implement a dedicated `CheckoutController` plus marketing API routes, migrating any remaining checkout logic out of the marketing controller.
|
||||
- [ ] Audit existing marketing payment flows (`resources/js/pages/marketing/PurchaseWizard.tsx`, `PaymentForm.tsx`) and plan removals or migration.
|
||||
- [x] Implement a dedicated `CheckoutController` plus marketing API routes, migrating any remaining checkout logic out of the marketing controller. *(Controller + routes now live in `app/Http/Controllers/CheckoutController.php` / `routes/web.php`.)*
|
||||
- [x] Audit existing marketing payment flows (`resources/js/pages/marketing/PurchaseWizard.tsx`, `PaymentForm.tsx`) and plan removals or migration. *(Legacy components removed; new wizard replaces them.)*
|
||||
|
||||
### Quality & Rollout
|
||||
- [ ] Expand automated coverage: Playwright end-to-end scenarios for auth, payment success/failure, Google login; PHPUnit and webhook tests for new checkout endpoints.
|
||||
- [ ] Update docs (PRP, docs/changes) and plan a feature-flag rollout for the new wizard.
|
||||
- [x] Expand automated coverage: Playwright end-to-end scenarios for auth, payment success/failure, Google login; PHPUnit and webhook tests for new checkout endpoints. *(Feature + unit suites cover Stripe intents, PayPal webhooks, Google comfort login; Playwright CTA smoke in place—full payment journey available behind the `checkout` tag.)*
|
||||
- [x] Update docs (PRP, docs/changes) and plan a feature-flag rollout for the new wizard.
|
||||
|
||||
## Notes
|
||||
- Wizard auth now uses `/checkout/login` and `/checkout/register` JSON endpoints handled by `CheckoutController`.
|
||||
@@ -33,7 +33,7 @@
|
||||
### Payment Integration Plan
|
||||
- [x] Define provider-agnostic payment state machine (intent creation, approval, capture, failure). See docs/prp/marketing-checkout-payment-architecture.md.
|
||||
- [x] Scaffold checkout_sessions migration + service layer per docs/prp/marketing-checkout-payment-architecture.md.
|
||||
- [ ] Implement Stripe PaymentIntent endpoint returning `client_secret` scoped to wizard session.
|
||||
- [ ] Implement PayPal order creation/capture endpoints with metadata for tenant/package.
|
||||
- [ ] Add webhook handling matrix for Stripe invoice/payment events and PayPal subscription lifecycle.
|
||||
- [ ] Wire payment step UI to new endpoints with optimistic and retry handling.
|
||||
- [x] Implement Stripe PaymentIntent endpoint returning `client_secret` scoped to wizard session. *(Covered by `CheckoutController::createPaymentIntent`.)*
|
||||
- [x] Implement PayPal order creation/capture endpoints with metadata for tenant/package. *(Routes now exposed in `routes/web.php`; controller derives tenant context for authenticated users.)*
|
||||
- [x] Add webhook handling matrix for Stripe invoice/payment events and PayPal subscription lifecycle.
|
||||
- [x] Wire payment step UI to new endpoints with optimistic and retry handling. *(See `PaymentStep.tsx` for Stripe intent loading + PayPal order/subscription creation and capture callbacks.)*
|
||||
|
||||
@@ -1,14 +1,14 @@
|
||||
### Update 2025-09-25
|
||||
- Phase 3 credits scope: credit middleware on create/update, rate limiters for OAuth/tenant APIs, RevenueCat webhook + processing job live with idempotency tests.
|
||||
- Remaining: extend middleware to photo/other credit drains, admin ledger surfaces, document RevenueCat env vars in PRP.
|
||||
### Update 2025-10-21
|
||||
- Phase 3 credit scope delivered: tenant event creation now honours package allowances *and* credit balances (middleware + ledger logging), RevenueCat webhook signature checks ship with queue/backoff + env config, idempotency covered via unit tests.
|
||||
- Follow-up (separate): evaluate photo upload quota enforcement + SuperAdmin ledger visualisations once package analytics stabilise.
|
||||
# Backend-Erweiterung Implementation Roadmap (Aktualisiert: 2025-09-15 - Fortschritt)
|
||||
|
||||
## Implementierungsstand (Aktualisiert: 2025-09-15)
|
||||
Basierend auf aktueller Code-Analyse und Implementierung:
|
||||
- **Phase 1 (Foundation)**: ✅ Vollständig abgeschlossen – Migrationen ausgeführt, Sanctum konfiguriert, OAuthController (PKCE-Flow, JWT), Middleware (TenantTokenGuard, TenantIsolation) implementiert und registriert.
|
||||
- **Phase 2 (Core API)**: ✅ 100% abgeschlossen – EventController (CRUD, Credit-Check, Search, Bulk), PhotoController (Upload, Moderation, Stats, Presigned Upload), **TaskController (CRUD, Event-Assignment, Bulk-Operations, Search)**, **SettingsController (Branding, Features, Custom Domain, Domain-Validation)**, Request/Response Models (EventStoreRequest, PhotoStoreRequest, **TaskStoreRequest, TaskUpdateRequest, SettingsStoreRequest**), Resources (**TaskResource, EventTypeResource**), File Upload Pipeline (local Storage, Thumbnails via ImageHelper), API-Routen erweitert, **Feature-Tests (21 Tests, 100% Coverage)**, **TenantModelTest (11 Unit-Tests)**.
|
||||
- **Phase 3 (Business Logic)**: 40% implementiert – event_credits_balance Feld vorhanden, Credit-Check in EventController, **Tenant::decrementCredits()/incrementCredits() Methoden**, aber CreditMiddleware, CreditController, Webhooks fehlen.
|
||||
- **Phase 4 (Admin & Monitoring)**: 20% implementiert – **TenantResource erweitert (credits, features, activeSubscription)**, aber fehlend: subscription_tier Actions, PurchaseHistoryResource, Widgets, Policies.
|
||||
- **Phase 3 (Business Logic)**: 60% implementiert – event_credits_balance Feld vorhanden, Endpunkt/Controller stehen, Credit-Middleware aktiv, RevenueCat Webhook inkl. Queue/Retries produktionsreif; Token-Rotation folgt.
|
||||
- **Phase 4 (Admin & Monitoring)**: 45% implementiert – **TenantResource erweitert (credits, features, activeSubscription)**, PurchaseHistory/OAuthClient-Management sowie Dashboard-Widgets fertig; verbleibend sind Advanced Actions (subscription_tier) und erweiterte Monitoring-Policies.
|
||||
|
||||
**Gesamtaufwand reduziert**: Von 2-3 Wochen auf **4-5 Tage**, da Phase 2 vollständig abgeschlossen und Tests implementiert.
|
||||
|
||||
@@ -65,31 +65,21 @@ Basierend auf aktueller Code-Analyse und Implementierung:
|
||||
|
||||
### Implementierter Fortschritt
|
||||
- [x] Credit-Feld in Tenant-Model mit `event_credits_balance`
|
||||
- [x] **Tenant::decrementCredits()/incrementCredits() Methoden** implementiert
|
||||
- [x] Credit-Check in EventController (decrement bei Create)
|
||||
- [ ] CreditMiddleware für alle Event-Operationen
|
||||
- [x] **Tenant::decrementCredits()/incrementCredits() Methoden** inkl. Logging implementiert
|
||||
- [x] Credit-Middleware & Route-Alias greifen vor Event-Create; `Tenant::consumeEventAllowance()` nutzt zuerst Reseller-Pakete, sonst Credits
|
||||
- [x] RevenueCat-Webhook: Signatur-Validierung, Queue-Konfiguration, Retry (`tries/backoff`) + Produkt-Mapping
|
||||
|
||||
### Verbleibende Tasks
|
||||
1. **Credit-System erweitern (1 Tag)**
|
||||
- CreditMiddleware für alle Event-Create/Update
|
||||
- CreditController für Balance, Ledger, History
|
||||
- Tenant::decrementCredits() Methode mit Logging
|
||||
|
||||
2. **Webhook-Integration (1-2 Tage)**
|
||||
- RevenueCatController für Purchase-Webhooks
|
||||
- Signature-Validation, Balance-Update, Subscription-Sync
|
||||
- Queue-basierte Retry-Logic
|
||||
|
||||
3. **Security Implementation (1 Tag)**
|
||||
- Rate Limiting: 100/min tenant, 10/min oauth
|
||||
- Token-Rotation in OAuthController
|
||||
- IP-Binding für Refresh Tokens
|
||||
1. **Security Implementation (1 Tag)**
|
||||
- Rate Limiting: 100/min tenant, 10/min oauth *(aktiv)*
|
||||
- Token-Rotation in OAuthController *(KID-basierte Schlüssel & `oauth:rotate-keys`)*
|
||||
- IP-Binding für Refresh Tokens *(konfigurierbar, Subnetzrelax optional)*
|
||||
|
||||
### Milestones
|
||||
- [x] Credit-Check funktioniert (Event-Create scheitert bei 0)
|
||||
- [ ] Webhooks verarbeiten Purchases
|
||||
- [ ] Rate Limiting aktiv
|
||||
- [ ] Token-Rotation implementiert
|
||||
- [x] Webhooks verarbeiten Purchases
|
||||
- [x] Rate Limiting aktiv
|
||||
- [x] Token-Rotation implementiert
|
||||
|
||||
## Phase 4: Admin & Monitoring (In Arbeit, 4-5 Tage)
|
||||
### Ziele
|
||||
@@ -99,14 +89,14 @@ Basierend auf aktueller Code-Analyse und Implementierung:
|
||||
### Implementierter Fortschritt
|
||||
- [x] **TenantResource erweitert**: credits, features, activeSubscription Attribute
|
||||
- [x] **TenantModelTest**: 11 Unit-Tests für Beziehungen (events, photos, purchases), Attribute, Methoden
|
||||
- [ ] PurchaseHistoryResource, OAuthClientResource, Widgets, Policies
|
||||
- [x] PurchaseHistoryResource, OAuthClientResource, Widgets, Policies
|
||||
|
||||
### Verbleibende Tasks
|
||||
1. **Filament Resources erweitern (2 Tage)**
|
||||
- TenantResource: subscription_tier, Actions (add_credits, suspend), RelationsManager
|
||||
- PurchaseHistoryResource: CRUD, Filter, Export, Refund
|
||||
- OAuthClientResource: Client-Management
|
||||
- TenantPolicy mit superadmin before()
|
||||
- TenantResource: subscription_tier, Actions (add_credits, suspend), RelationsManager *(Credits-Aktion fertig; subscription_tier-Actions noch offen)*
|
||||
- PurchaseHistoryResource: CRUD, Filter, Export, Refund *(CRUD & Export umgesetzt; Refund via UI noch offen)*
|
||||
- OAuthClientResource: Client-Management *(implementiert)*
|
||||
- TenantPolicy mit superadmin before() *(implementiert)*
|
||||
|
||||
2. **Dashboard Widgets (1 Tag)**
|
||||
- RevenueChart, TopTenantsByRevenue, CreditAlerts
|
||||
@@ -121,9 +111,9 @@ Basierend auf aktueller Code-Analyse und Implementierung:
|
||||
|
||||
### Milestones
|
||||
- [x] TenantResource basis erweitert
|
||||
- [ ] PurchaseHistoryResource funktioniert
|
||||
- [ ] Widgets zeigen Stats
|
||||
- [ ] Policies schützen SuperAdmin
|
||||
- [x] PurchaseHistoryResource funktioniert
|
||||
- [x] Widgets zeigen Stats
|
||||
- [x] Policies schützen SuperAdmin
|
||||
- [ ] >80% Testabdeckung
|
||||
|
||||
## Gesamter Zeitplan
|
||||
@@ -133,7 +123,7 @@ Basierend auf aktueller Code-Analyse und Implementierung:
|
||||
| **1** | Foundation | ✅ Abgeschlossen |
|
||||
| **1** | Core API | ✅ Abgeschlossen |
|
||||
| **2** | Business Logic | 40% â³ In Arbeit |
|
||||
| **2** | Admin & Monitoring | 20% ðŸâ€Â„ In Arbeit |
|
||||
| **2** | Admin & Monitoring | 45% ✅ In Arbeit |
|
||||
|
||||
**Gesamtdauer:** **4-5 Tage** - Phase 2 vollständig abgeschlossen, Tests implementiert
|
||||
**Kritische Pfade:** Phase 3 (Business Logic) kann sofort starten
|
||||
@@ -157,4 +147,4 @@ Basierend auf aktueller Code-Analyse und Implementierung:
|
||||
6. **Deployment**: Staging-Environment, Monitoring-Setup
|
||||
|
||||
**Gesamtkosten:** Ca. 60-100 Stunden (weit reduziert durch bestehende Basis).
|
||||
**Erwartete Ergebnisse:** Voll funktionsfähige Multi-Tenant API mit Events/Photos, Freemium-Modell bereit für SuperAdmin-Management.
|
||||
**Erwartete Ergebnisse:** Voll funktionsfähige Multi-Tenant API mit Events/Photos, Freemium-Modell bereit für SuperAdmin-Management.
|
||||
|
||||
15
docs/piwik-trackingcode.txt
Normal file
15
docs/piwik-trackingcode.txt
Normal file
@@ -0,0 +1,15 @@
|
||||
<!-- Matomo -->
|
||||
<script>
|
||||
var _paq = window._paq = window._paq || [];
|
||||
/* tracker methods like "setCustomDimension" should be called before "trackPageView" */
|
||||
_paq.push(['trackPageView']);
|
||||
_paq.push(['enableLinkTracking']);
|
||||
(function() {
|
||||
var u="//piwik.sebfoto.de/";
|
||||
_paq.push(['setTrackerUrl', u+'matomo.php']);
|
||||
_paq.push(['setSiteId', '6']);
|
||||
var d=document, g=d.createElement('script'), s=d.getElementsByTagName('script')[0];
|
||||
g.async=true; g.src=u+'matomo.js'; s.parentNode.insertBefore(g,s);
|
||||
})();
|
||||
</script>
|
||||
<!-- End Matomo Code -->
|
||||
@@ -25,6 +25,16 @@ Guest Polling (no WebSockets in v1)
|
||||
- GET `/events/{token}/photos?since=<ISO8601|cursor>` — incremental gallery refresh.
|
||||
- Response: `{ data: Photo[], next_cursor?: string, latest_photo_at: ISO8601 }`.
|
||||
- Use `If-None-Match` or `If-Modified-Since` to return `304 Not Modified` when unchanged.
|
||||
- Legacy slug-based guest endpoints have been removed; tokens are mandatory for public access.
|
||||
|
||||
Webhooks
|
||||
- Payment provider events, media pipeline status, and deletion callbacks. All signed with shared secret per provider.
|
||||
- RevenueCat webhook: `POST /api/v1/webhooks/revenuecat` signed via `X-Signature` (HMAC SHA1/256). Dispatches `ProcessRevenueCatWebhook` to credit tenants and sync subscription expiry.
|
||||
|
||||
Public Gallery
|
||||
- `GET /gallery/{token}`: returns event snapshot + branding colors; responds with `410` once the package gallery window expires.
|
||||
- `GET /gallery/{token}/photos?cursor=&limit=`: cursor-based pagination of approved photos. Response shape `{ data: Photo[], next_cursor: string|null }`.
|
||||
- `GET /gallery/{token}/photos/{photo}/download`: streams or redirects to an approved original. Returns `404` if the asset is gone.
|
||||
|
||||
Tenant Admin Downloads
|
||||
- `GET /tenant/events/{event}/photos/archive`: authenticated ZIP export of all approved photos for an event. Returns `404` when none exist.
|
||||
|
||||
@@ -30,6 +30,7 @@ Core Features
|
||||
- Masonry grid, lazy-load, pull-to-refresh; open photo lightbox with swipe.
|
||||
- Like (heart) with optimistic UI; share system sheet (URL to CDN variant).
|
||||
- Filters: emotion, featured, mine (local-only tag for items uploaded from this device).
|
||||
- Public share: host can hand out `https://app.domain/g/{token}`; guests see a themed, read-only gallery with per-photo downloads.
|
||||
- Safety & abuse controls
|
||||
- Rate limits per device and IP; content-length checks; mime/type sniffing.
|
||||
- Upload moderation state: pending → approved/hidden; show local status.
|
||||
@@ -39,6 +40,7 @@ Core Features
|
||||
|
||||
Screens
|
||||
- Splash/Loading: event lookup + token validation; friendly skeleton.
|
||||
- Slug-based deep links are no longer accepted; guests must enter or scan a join token QR.
|
||||
- Terms & PIN: legal links, optional PIN input; remember choice per event.
|
||||
- Gallery: grid of approved photos; toolbar with filter, upload, settings.
|
||||
- Upload Picker: camera/library, selection preview, emotion/task tagging.
|
||||
|
||||
@@ -9,6 +9,15 @@ The Fotospiel platform supports multiple payment providers for package purchases
|
||||
- **Configuration**: Keys in `config/services.php` under `stripe`. Sandbox mode based on `APP_ENV`.
|
||||
- **Models**: `PackagePurchase` records all transactions with `provider_id` (Stripe PI ID), `status`, `metadata`.
|
||||
- **Frontend**: PurchaseWizard.tsx handles client-side Stripe Elements for card input and confirmation.
|
||||
- **Webhook Matrix**:
|
||||
|
||||
| Event | Purpose | Internal handler |
|
||||
| --- | --- | --- |
|
||||
| `payment_intent.succeeded` | Completes single-event package purchase | `StripeWebhookController@handlePaymentIntentSucceeded` |
|
||||
| `payment_intent.payment_failed` | Logs failure, triggers recovery emails | `handlePaymentIntentFailed` |
|
||||
| `invoice.paid` | Confirms subscription renewal, extends package | `handleInvoicePaid` |
|
||||
| `invoice.payment_failed` | Flags tenant for follow-up, sends alerts | `handleInvoicePaymentFailed` |
|
||||
| `customer.subscription.deleted` | Finalises cancellation/downgrade | `handleSubscriptionDeleted` |
|
||||
|
||||
## PayPal Integration
|
||||
- **SDK**: Migrated to PayPal Server SDK v1.0+ (`paypal/paypal-server-sdk`). Uses Builder pattern for requests and Controllers for API calls.
|
||||
@@ -17,6 +26,14 @@ The Fotospiel platform supports multiple payment providers for package purchases
|
||||
- **Differences**: One-time: Standard Order with payment_type ONE_TIME (default). Recurring: Order with StoredPaymentSource RECURRING to enable future charges without new approvals. plan_id stored in metadata for reference; no separate subscription ID from SDK.
|
||||
- **Client Setup**: OAuth2 Client Credentials flow. Builder: `PaypalServerSdkClientBuilder::init()->clientCredentialsAuthCredentials(ClientCredentialsAuthCredentialsBuilder::init(client_id, secret))->environment(Environment::SANDBOX/PRODUCTION)->build()`.
|
||||
- **Webhooks**: `PayPalWebhookController@verify` handles events like `PAYMENT.CAPTURE.COMPLETED` (process initial/renewal purchase), `BILLING.SUBSCRIPTION.CANCELLED` or equivalent order events (deactivate package). Simplified signature verification (TODO: Implement `VerifyWebhookSignature`).
|
||||
- **Webhook Matrix**:
|
||||
|
||||
| Event | Purpose | Internal handler |
|
||||
| --- | --- | --- |
|
||||
| `PAYMENT.CAPTURE.COMPLETED` | Confirms one-time order, activates tenant package | `handleCapture` |
|
||||
| `BILLING.SUBSCRIPTION.ACTIVATED`, `BILLING.SUBSCRIPTION.UPDATED` | Syncs reseller subscription status/expiry | `handleSubscription` |
|
||||
| `BILLING.SUBSCRIPTION.CANCELLED`, `BILLING.SUBSCRIPTION.EXPIRED` | Marks package inactive and downgrades tenant | `handleSubscription` |
|
||||
| `BILLING.SUBSCRIPTION.SUSPENDED` | Pauses package benefits pending review | `handleSubscription` |
|
||||
- **Idempotency**: Check `provider_id` in `PackagePurchase` before creation. Transactions for DB safety.
|
||||
- **Configuration**: Keys in `config/services.php` under `paypal`. Sandbox mode via `paypal.sandbox`.
|
||||
- **Migration Notes**: Replaced old Checkout SDK (`PayPalCheckoutSdk`). Updated imports, requests (e.g., OrdersCreateRequest -> OrderRequestBuilder, Subscriptions -> StoredPaymentSource in Orders). Responses: Use `getStatusCode()` and `getResult()`. Tests mocked new structures. No breaking changes in auth or metadata handling; recurring flows now unified under Orders API.
|
||||
|
||||
@@ -6,3 +6,20 @@
|
||||
- Logging: structured, no PII; add request/trace IDs; redact secrets.
|
||||
- GDPR: retention settings per tenant; deletion workflows; legal pages managed via CMS-like resource.
|
||||
- Rate limits: per-tenant, per-user, per-device; protect upload and admin mutations.
|
||||
|
||||
## 2025 Hardening Priorities
|
||||
|
||||
- **Identity & OAuth** — *Owner: Backend Platform*
|
||||
Track JWT key rotation via `oauth:rotate-keys`, roll out dual-key support (old/new KID overlap), surface refresh-token revocation tooling, and extend IP/device binding rules for long-lived sessions.
|
||||
- **Guest Join Tokens** — *Owner: Guest Platform*
|
||||
Hash stored join tokens, add anomaly metrics (usage spikes, stale tokens), and tighten gallery/photo rate limits with visibility in storage dashboards.
|
||||
- **Public API Resilience** — *Owner: Core API*
|
||||
Ensure gallery/download endpoints serve signed URLs, expand abuse throttles (token + IP), and document incident response runbooks in ops guides.
|
||||
- **Media Pipeline & Storage** — *Owner: Media Services*
|
||||
Introduce antivirus + EXIF scrubbing workers, stream uploads to disk to avoid buffering, and enforce checksum verification during hot→archive transfers with configurable alerts from `StorageHealthService`.
|
||||
- **Payments & Webhooks** — *Owner: Billing*
|
||||
Align legacy Stripe hooks with checkout sessions, add idempotency locks/signature expiry checks, and plug failed capture notifications into the credit ledger audit trail.
|
||||
- **Frontend & CSP** — *Owner: Marketing Frontend*
|
||||
Replace unsafe-inline allowances (Stripe/Matomo) with nonce or hashed CSP rules, gate analytics injection behind consent, and localise cookie-banner copy that discloses data sharing.
|
||||
|
||||
Progress updates belong in `docs/changes/` and roadmap status in `docs/implementation-roadmap.md`.
|
||||
|
||||
29
docs/prp/11-public-gallery.md
Normal file
29
docs/prp/11-public-gallery.md
Normal file
@@ -0,0 +1,29 @@
|
||||
# 11 — Public Guest Gallery
|
||||
|
||||
Purpose
|
||||
- Provide a shareable, mobile-friendly gallery for guests who only need to view and download approved photos.
|
||||
- Respect existing join-token security and automatically disable access once a package’s gallery duration expires.
|
||||
|
||||
Access Model
|
||||
- URL pattern: `https://<app-domain>/g/{joinToken}`. Tokens are the same join tokens tenants already issue; revoking or expiring a token immediately locks the gallery.
|
||||
- Tokens expire when the associated event package’s `gallery_expires_at` passes; guests receive an explanatory message (HTTP `410`).
|
||||
- Only *approved* photos appear; pending/rejected items remain hidden.
|
||||
|
||||
Client Experience
|
||||
- Responsive grid with lazy-loaded thumbnails (IntersectionObserver) and infinite scroll/pagination.
|
||||
- Event branding colours (primary, secondary, background) are applied via CSS custom properties fetched from the API.
|
||||
- Fullscreen lightbox shows creation timestamp + guest label when available and exposes a single-photo download button (streams the original asset).
|
||||
|
||||
API Touchpoints (see 03 — API Contract for details)
|
||||
- `GET /api/v1/gallery/{token}` → event snapshot + branding.
|
||||
- `GET /api/v1/gallery/{token}/photos` → cursor-based pagination of approved photos.
|
||||
- `GET /api/v1/gallery/{token}/photos/{photo}/download` → single-photo download/redirect.
|
||||
|
||||
Tenant Admin Support
|
||||
- Filament action “Download all photos” (Event resource) queues a server-side ZIP export via `GET /tenant/events/{event}/photos/archive` for authenticated tenants.
|
||||
- Only approved photos are included; failed assets are skipped with logging.
|
||||
|
||||
Future Enhancements
|
||||
- Background job + notification for large ZIP exports (current implementation streams synchronously).
|
||||
- Optional passcode/PIN layered on top of join tokens for sensitive events.
|
||||
- Aggregate analytics (views/downloads per photo) presented in Tenant Admin dashboards.
|
||||
@@ -12,6 +12,8 @@
|
||||
- **CheckoutAssignmentService** performs the idempotent write workflow (create/update TenantPackage, PackagePurchase, tenant subscription fields, welcome mail) once payment succeeds.
|
||||
- **Wizard API surface** (JSON routes under `/checkout/*`) is session-authenticated, CSRF-protected, and returns structured payloads consumed by the PWA.
|
||||
- **Webhooks** (Stripe, PayPal) map incoming provider events back to `CheckoutSession` rows to guarantee reconciliation and support 3DS / async capture paths.
|
||||
- **Feature Flag**: `config/checkout.php` exposes `CHECKOUT_WIZARD_ENABLED` and `CHECKOUT_WIZARD_FLAG` so the SPA flow can be toggled or gradual-rolled out during launch.
|
||||
- **Operational**: Rotate JWT signing keys with `php artisan oauth:rotate-keys` (updates key folder per KID; remember to bump `OAUTH_JWT_KID`).
|
||||
|
||||
## Payment State Machine
|
||||
State constants live on `CheckoutSession` (`status` column, enum):
|
||||
@@ -129,6 +131,5 @@ Stripe/PayPal routes remain under `routes/web.php` but call into new service cla
|
||||
|
||||
## Open Questions / Follow-Ups
|
||||
- Map package records to Stripe price ids and PayPal plan ids (store on `packages` table or config?).
|
||||
- Determine how Google sign-in enrichment (comfort login) feeds the checkout session once implemented.
|
||||
- Confirm legal copy updates for new checkout experience before GA.
|
||||
- Align email templates (welcome, receipt) with new assignment service outputs.
|
||||
|
||||
@@ -40,6 +40,7 @@ Ziel: Vollständige Migration zu Inertia.js für SPA-ähnliche Konsistenz, mit e
|
||||
- **Auth-Integration**: usePage().props.auth für CTAs (z.B. Login-Button im Header).
|
||||
- **Responsive Design**: Tailwind: block md:hidden für Mobile-Carousel in Packages.
|
||||
- **Fonts & Assets**: Vite-Plugin für Fonts/SVGs; preload in Layout.
|
||||
- **Analytics (Matomo)**: Aktivierung via `.env` (`MATOMO_ENABLED=true`, `MATOMO_URL`, `MATOMO_SITE_ID`). `AppServiceProvider` teilt die Konfiguration als `analytics.matomo`; `MarketingLayout` rendert `MatomoTracker`, der das Snippet aus `/docs/piwik-trackingcode.txt` nur bei erteilter Analyse-Zustimmung lädt, `disableCookies` setzt und bei jedem Inertia-Navigationsevent `trackPageView` sendet. Ein lokalisierter Consent-Banner (DE/EN) übernimmt die DSGVO-konforme Einwilligung und ist über den Footer erneut erreichbar.
|
||||
- **Tests**: E2E mit Playwright (z.B. navigate to /packages, check header/footer presence).
|
||||
|
||||
### 5. Diagramm: Layout-Struktur
|
||||
@@ -66,4 +67,4 @@ MarketingLayout.tsx
|
||||
- Styling-Konflikte: CSS-Isolation mit Tailwind-Prefix.
|
||||
- Performance: Code-Splitting für große Pages.
|
||||
|
||||
Dieser Plan basiert auf bestehender Struktur (docs/prp/ als Referenz). Nach Umsetzung: Update PRP (docs/prp/01-architecture.md).
|
||||
Dieser Plan basiert auf bestehender Struktur (docs/prp/ als Referenz). Nach Umsetzung: Update PRP (docs/prp/01-architecture.md).
|
||||
|
||||
28
docs/prp/public-entrypoints.md
Normal file
28
docs/prp/public-entrypoints.md
Normal file
@@ -0,0 +1,28 @@
|
||||
# Public Entry Points
|
||||
|
||||
This overview lists every user-facing URL surface, grouped by persona, and notes authentication/expiry rules.
|
||||
|
||||
## Marketing Site
|
||||
- `/` — marketing landing page.
|
||||
- `/packages` — package overview.
|
||||
- `/checkout/{package}` — checkout wizard (requires logged-in tenant or email login within flow).
|
||||
- `/blog`, `/contact`, `/impressum`, `/datenschutz`, `/agb` — legal and marketing content.
|
||||
|
||||
## Tenant Admin
|
||||
- `/event-admin/*` — protected Filament SPA (requires tenant credentials).
|
||||
- `/tenant/events/{event}/photos/archive` — authenticated ZIP export for approved photos (tenant ownership enforced).
|
||||
|
||||
## Guest PWA (event-bound)
|
||||
- `/event` — landing for new guests (code entry / QR).
|
||||
- `/e/{token}` — full guest experience (home, tasks, gallery, upload) gated by join token; token expiry revokes access.
|
||||
- `/g/{token}` — read-only public gallery (new). Shows approved photos themed by event branding; downloads allowed while token valid and gallery duration active.
|
||||
- `/setup/{token}` — onboarding/profile setup for guests.
|
||||
|
||||
## API (selected public endpoints)
|
||||
- `/api/v1/events/{token}` — event metadata for guest PWA.
|
||||
- `/api/v1/events/{token}/photos` — guest gallery polling (legacy PWA).
|
||||
- `/api/v1/gallery/{token}` — public gallery metadata (new).
|
||||
- `/api/v1/gallery/{token}/photos` — public gallery pagination (new).
|
||||
- `/api/v1/gallery/{token}/photos/{photo}/download` — single photo download (new).
|
||||
|
||||
All other `/api/v1/*` routes require authenticated tenant or super-admin access as documented in `docs/prp/03-api.md`.
|
||||
@@ -1,15 +1,22 @@
|
||||
# Detaillierte PRP für Tenant Admin App (Capacitor + Framework7)
|
||||
|
||||
## Status
|
||||
- **Aktiv**: Erste Version (2025-09-13)
|
||||
- **Version**: 1.0.0
|
||||
- **Autor**: Sonoma (AI Architect)
|
||||
- **Supersedes**: docs/prp/06-tenant-admin-pwa.md (erweitert und detailliert)
|
||||
- **Aktualisiert**: 2025-10-17 (Onboarding Fusion & QR Revamp)
|
||||
- **Version**: 1.2.0
|
||||
- **Autor**: Core Platform Team (Codex)
|
||||
- **Supersedes**: docs/prp/06-tenant-admin-pwa.md (legacy Framework7 reference)
|
||||
|
||||
## Überblick
|
||||
Diese detaillierte Product Requirement Plan (PRP) beschreibt die Spezifikationen für die Tenant Admin App. Die App ist eine store-ready mobile Anwendung, die mit Capacitor für iOS und Trusted Web Activity (TWA) für Android gepackt wird. Die UI basiert auf Framework7 für ein natives Mobile-Erlebnis. Die App ermöglicht Tenant-Admins (z.B. Event-Organisatoren) die vollständige Verwaltung ihrer Events, Galerien, Mitglieder, Einstellungen und Käufe über eine API-first Backend-Integration.
|
||||
|
||||
Die App ersetzt das frühere Filament-basierte Tenant-Panel und fokussiert auf Mobile-First-UX mit Offline-Fähigkeiten, Push-Notifications und sicherer Authentifizierung. Sie respektiert das Multi-Tenancy-Modell und GDPR-Anforderungen.
|
||||
Die App ersetzt das frühere Filament-basierte Tenant-Panel und fokussiert auf eine Mobile-First-UX mit Offline-Fähigkeiten, Push-Notifications und sicherer Authentifizierung. Sie respektiert das Multi-Tenancy-Modell und GDPR-Anforderungen. Seit Oktober 2025 wird das UI in React 19 + Vite + Tailwind/shadcn/ui umgesetzt; die alte Framework7-Schicht bleibt nur als historische Referenz erhalten.
|
||||
|
||||
## Aktuelle Highlights (Q4 2025)
|
||||
- **Geführtes Onboarding**: `/event-admin/welcome/*` orchestriert den Welcome Flow (Hero → How-It-Works → Paketwahl → Zusammenfassung → Event Setup). Guarding erfolgt über `onboarding_completed_at`.
|
||||
- **Direkter Checkout**: Stripe & PayPal sind in die Paketwahl des Welcome Flows eingebettet; Fortschritt wird im Onboarding-Context persistiert.
|
||||
- **Filament Wizard**: Für Super-Admins existiert ein paralleler QR/Join-Token-Wizard in Filament (Token-Generierung, Layout-Downloads, Rotation).
|
||||
- **Join Tokens only**: Gäste erhalten ausschließlich join-token-basierte Links/QRs; slug-basierte URLs wurden deaktiviert. QR-Drucklayouts liegen unter `resources/views/pdf/join-tokens/*`.
|
||||
- **OAuth Alignment**: `VITE_OAUTH_CLIENT_ID` + `/event-admin/auth/callback` werden seedingseitig synchron gehalten; siehe `docs/prp/tenant-app-specs/api-usage.md`.
|
||||
|
||||
## Kernziele
|
||||
- **Deliverables**: Voll funktionsfähige App mit CRUD-Operationen für Tenant-Ressourcen (Events, Photos, Tasks, etc.).
|
||||
@@ -40,4 +47,4 @@ Diese PRP erweitert die knappe Beschreibung in 06-tenant-admin-pwa.md um:
|
||||
- Detaillierte Settings und Capacitor-Integration.
|
||||
- Mobile-spezifische Features wie Push-Notifications und Offline-Sync.
|
||||
|
||||
Für Feedback oder Änderungen: Siehe TODO.md oder Issues.
|
||||
Für Feedback oder Änderungen: Siehe TODO.md oder Issues.
|
||||
|
||||
@@ -22,6 +22,7 @@ Diese Dokumentation beschreibt alle API-Endpunkte, die die Tenant Admin App mit
|
||||
- **Redirect URI**: Standardmaessig `${origin}/event-admin/auth/callback` (per Vite-Env anpassbar)
|
||||
- **Headers**: `Authorization: Bearer {access_token}`
|
||||
- **Response**: `{ id, email, tenant_id, role, name }`
|
||||
- **Hinweis**: `client_id` entspricht `VITE_OAUTH_CLIENT_ID`; Seeder `OAuthClientSeeder` synchronisiert Frontend und Backend.
|
||||
|
||||
## Dashboard
|
||||
|
||||
@@ -260,6 +261,7 @@ curl -H "Authorization: Bearer {token}" \
|
||||
- **VITE_API_URL**: Backend-API-URL (Pflicht)
|
||||
- **VITE_OAUTH_CLIENT_ID**: OAuth-Client-ID (Pflicht, muss mit `config/services.php` übereinstimmen – der Seeder legt damit den Client in `oauth_clients` an)
|
||||
- **VITE_REVENUECAT_PUBLIC_KEY**: Optional fuer In-App-Kaeufe (RevenueCat)
|
||||
- **REVENUECAT_WEBHOOK_SECRET / REVENUECAT_PRODUCT_MAPPINGS / REVENUECAT_APP_USER_PREFIX / REVENUECAT_WEBHOOK_QUEUE**: Backend-Konfiguration für RevenueCat-Webhooks, siehe `config/services.php`.
|
||||
|
||||
### Build & Deploy
|
||||
1. **Development**: `npm run dev`
|
||||
@@ -272,4 +274,3 @@ curl -H "Authorization: Bearer {token}" \
|
||||
|
||||
Für weitere Details siehe die spezifischen Dokumentationsdateien.
|
||||
|
||||
|
||||
|
||||
@@ -23,12 +23,14 @@ Die Admin-App muss folgende Kernfunktionen bereitstellen:
|
||||
|
||||
### Onboarding Journey
|
||||
- Routen `/event-admin/welcome/*` bilden den Flow.
|
||||
- Filament stellt einen korrespondierenden Onboarding-Wizard (QR/Join-Token, Layout-Download) bereit; Abschluss setzt `onboarding_completed_at` serverseitig.
|
||||
- `useOnboardingProgress` persistiert Fortschritt (localStorage) und synchronisiert mit Backend (`onboarding_completed_at`).
|
||||
- Paketwahl nutzt `GET /tenant/packages`; Stripe/PayPal-Fallbacks informieren bei fehlender Konfiguration.
|
||||
- Dashboard weist per CTA auf offenes Onboarding hin, bis ein erstes Event erstellt wurde.
|
||||
|
||||
### Event Lifecycle
|
||||
- Erstellung prüft Paketverfügbarkeit; generiert Join-Token.
|
||||
- Erstellung prüft Paketverfügbarkeit; generiert Join-Token (EventJoinToken-Service).
|
||||
- QR-Layouts und Token-Rotation erfolgen über `/event-admin/welcome` bzw. das Filament-Panel; slug-basierte QR-Links wurden deaktiviert.
|
||||
- Bearbeiten erlaubt Statuswechsel, Aufgaben, Emotions, Join-Token-Verwaltung.
|
||||
- Veröffentlichen schaltet Guest-PWA frei; Archivieren respektiert Retention-Policy.
|
||||
|
||||
|
||||
@@ -27,12 +27,12 @@ Replace slug-based guest access with opaque, revocable join tokens and provide p
|
||||
- [x] Build “QR & Invites” management UI (list tokens, usage stats, rotate/revoke).
|
||||
- [x] Hook Filament action + PWA screens to call new token endpoints.
|
||||
- [x] Generate five print-ready layouts (PDF/SVG) per token with download options.
|
||||
- [ ] Deprecate slug-based QR view; link tenants to new flow.
|
||||
- [x] Deprecate slug-based QR view; link tenants to new flow.
|
||||
|
||||
## Phase 4 – Migration & Cleanup
|
||||
- [ ] Remove slug parameters from public endpoints once traffic confirms token usage.
|
||||
- [ ] Update documentation (PRP, onboarding guides, runbooks) to reflect token process.
|
||||
- [ ] Add feature/integration tests covering expiry, rotation, and guest flows.
|
||||
- [x] Remove slug parameters from public endpoints (legacy slug URLs now return invalid_token).
|
||||
- [x] Update documentation (PRP, onboarding guides, runbooks) to reflect token process.
|
||||
- [x] Add feature/integration tests covering expiry, rotation, and guest flows.
|
||||
|
||||
## Open Questions
|
||||
- Decide on default token lifetime and rotation cadence.
|
||||
|
||||
42
docs/todo/security-hardening-epic.md
Normal file
42
docs/todo/security-hardening-epic.md
Normal file
@@ -0,0 +1,42 @@
|
||||
# Security Hardening Epic (Q4 2025)
|
||||
|
||||
## Goal
|
||||
Raise the baseline security posture across guest APIs, checkout, media storage, and identity flows so the platform can scale multi-tenant traffic with auditable, revocable access.
|
||||
|
||||
## Workstreams
|
||||
|
||||
1. **Identity & OAuth (Backend Platform)**
|
||||
- Dual-key rollout for JWT signing with rotation runbook and monitoring.
|
||||
- Refresh-token revocation tooling (per device/IP) and anomaly alerts.
|
||||
- Device fingerprint/subnet allowances documented and configurable.
|
||||
|
||||
2. **Guest Join Tokens (Guest Platform)**
|
||||
- Store hashed tokens with irreversible lookups; migrate legacy data.
|
||||
- Add per-token usage analytics, alerting on spikes or expiry churn.
|
||||
- Extend gallery/photo rate limits (token + IP) and surface breach telemetry in storage dashboards.
|
||||
|
||||
3. **Public API Resilience (Core API)**
|
||||
- Serve signed asset URLs instead of raw storage paths; expire appropriately.
|
||||
- Document incident response runbooks and playbooks for abuse mitigation.
|
||||
- Add synthetic monitors for `/api/v1/gallery/*` and upload endpoints.
|
||||
|
||||
4. **Media Pipeline & Storage (Media Services)**
|
||||
- Integrate antivirus/EXIF scrubbers and streaming upload paths to avoid buffering.
|
||||
- Verify checksum integrity on hot → archive transfers with alert thresholds.
|
||||
- Surface storage target health (capacity, latency) in Super Admin dashboards.
|
||||
|
||||
5. **Payments & Webhooks (Billing)**
|
||||
- Link Stripe/PayPal webhooks to checkout sessions with idempotency locks.
|
||||
- Add signature freshness validation + retry policies for provider outages.
|
||||
- Pipe failed capture events into credit ledger audits and operator alerts.
|
||||
|
||||
6. **Frontend & CSP (Marketing Frontend)**
|
||||
- Replace `unsafe-inline` allowances with nonce/hash policies for Stripe + Matomo.
|
||||
- Gate analytics script injection behind consent with localised disclosures.
|
||||
- Broaden cookie banner layout to surface GDPR/legal copy clearly.
|
||||
|
||||
## Deliverables
|
||||
- Updated docs (`docs/prp/09-security-compliance.md`, runbooks) with ownership & SLAs.
|
||||
- Feature flags / configuration toggles for rollouts (JWT KID, signed URLs, CSP nonces).
|
||||
- Monitoring dashboards + alerting coverage per workstream.
|
||||
- Integration and Playwright coverage validating the hardened flows.
|
||||
@@ -46,7 +46,7 @@ Owner: Codex (handoff)
|
||||
- [x] Rebrand the Filament tenant panel away from “Admin” by adjusting `AdminPanelProvider` (brand name, home URL, navigation visibility) and registering a new onboarding home page.
|
||||
- [x] Build the Filament onboarding wizard (welcome → task package selection → event name → color palette → QR layout) with persisted progress on the tenant record and guards that hide legacy resource menus until completion.
|
||||
- [x] Expose QR invite generation in Filament via a dedicated page/component that reuses the join-token flow from `EventDetailPage.tsx`, ensuring tokens stay in sync between PWA and Filament.
|
||||
- [ ] Update PRP/docs to cover the new welcome flow, OAuth alignment, Filament onboarding, and QR tooling; add regression notes + tests for the adjusted routes.
|
||||
- [x] Update PRP/docs to cover die neue Welcome Journey, OAuth-Ausrichtung, Filament-Onboarding und QR-Tooling; Regression Notes + Tests dokumentiert.
|
||||
|
||||
|
||||
|
||||
|
||||
Reference in New Issue
Block a user