4174b33016
feat: Subscriber-Repository mit Double-Opt-In und Consent-Tracking (Finding 3)
...
- createSubscriber: SHA256-Hash, DOI-Token, Consent-IP/UA
- confirmDoi: setzt status=active, löscht Token
- deleteSubscriber: DSGVO Art. 17
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com >
2026-04-17 17:37:30 +00:00
9b6e9d8383
migration: subscribers-Tabelle mit DOI-Feldern und Consent-Tracking (Finding 3)
...
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com >
2026-04-17 17:36:25 +00:00
ee83705527
fix: Suppression-Check nutzt SHA256-Hash statt Klartext-E-Mail (Finding 1)
...
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com >
2026-04-17 17:36:11 +00:00
e5db71ead1
fix: Bug 1+2+3 — SQL Cross-Join, PATCH 404 vs 400, API-Test-Skip
...
- getCampaignRecipients: EXISTS-Subquery statt Cross-Join verhindert Mehrfachversand
- updateCampaign: SELECT vor UPDATE unterscheidet 'nicht gefunden' (404) von 'nicht im Draft' (400)
- campaigns-api.test.ts: describe.skip entfernt, Mocks für DB-Abhängigkeiten ergänzt
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com >
2026-04-17 17:34:18 +00:00
ca0c65352e
fix: DSGVO-Findings 5+7+6 — Tenant-Guard, APP_URL-Pflichtcheck, Constraint-Migration
...
- getTenantId wirft bei fehlendem Header statt silent fallback auf 'default'
- Alle API-Routes fangen den Fehler ab und antworten mit 401
- Worker gibt err() zurück wenn APP_URL nicht konfiguriert ist
- Migration: recipient_has_one Constraint schließt NULL/NULL-Zeilen aus
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com >
2026-04-17 16:42:50 +00:00
25889a5419
fix: Rollback auf draft bei Versand-Fehlern, Fehlermeldung updateCampaign
...
- send/route.ts: try/catch + Rollback auf draft wenn Empfänger-Query oder Queue-Enqueue fehlschlägt
- campaigns.ts: Fehlermeldung 'Kampagne nicht im Draft-Status' (zuvor enthielt sie 'nicht gefunden' — verursachte falschen 404 in PATCH)
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com >
2026-04-17 13:50:21 +00:00
889bfad085
fix: API Routes — Ergebnisprüfung, Suppression-Check vor Enqueue, Bulk-Enqueue, Status-Codes, Draft-Guard
...
- getTenantId in shared Utility src/lib/tenant-header.ts ausgelagert (alle 4 Route-Dateien)
- send/route.ts: updateCampaignStatus-Ergebnis geprüft (C1), addBulk statt sequentiellem await (C2), Suppression-Check vor Enqueue (C3)
- [id]/route.ts: GET unterscheidet 404/500, PATCH unterscheidet 404/400
- schedule/route.ts: immediate-Typ abgelehnt (I4), Draft-Guard hinzugefügt (I5)
- .eslintrc.json ergänzt (next/core-web-vitals) — fehlte im Projekt
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com >
2026-04-17 13:44:42 +00:00
e2f2ce6a56
feat: API Routes — Campaign CRUD, sofortiger Versand, Zeitplan
...
Implementiert vier Next.js App-Router API-Routen für das Campaign-Management:
- GET/POST /api/campaigns (Liste + Erstellen)
- GET/PATCH /api/campaigns/[id] (Einzeln abrufen + Aktualisieren)
- POST /api/campaigns/[id]/send (Sofortiger Versand — nur Draft-Status)
- POST /api/campaigns/[id]/schedule (Zeitplan setzen — once/cron/immediate)
Alle Routen lesen Tenant-ID aus x-tenant-id Header, nutzen das Result-Pattern
und validieren Eingaben über Zod-Schemas. Der Smoke-Test ist mit describe.skip
markiert, da next/server in Vitest nicht verfügbar ist.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com >
2026-04-17 13:39:46 +00:00
e49552236d
fix: safeInsertEvent verhindert Doppelversand, Union-Typ für eventType, Privacy-Tests ergänzt
2026-04-17 12:13:31 +00:00
8bf143735e
feat: BullMQ Worker — Suppression-Check vor SMTP, ClickHouse-Event-Insert, RFC-8058-Header
...
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com >
2026-04-17 12:09:04 +00:00
5340e76630
fix: Typ-Generic in checkSuppression, SMTP_PASS Fallback, Logging-Test prüft console.error, tenantId-Fehler-Test
2026-04-17 10:53:56 +00:00
a60b08876c
feat: Suppression-Check (normalisiert, parametrisiert) und SMTP-Client mit RFC-8058-Header
...
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com >
2026-04-17 10:51:26 +00:00
5b24c9f129
fix: DI statt Singleton, Queue-Name email-send (BullMQ v5 kein Doppelpunkt), err bei fehlender Job-ID
2026-04-17 10:36:04 +00:00
7baeb004c6
feat: BullMQ email:send Queue — enqueueEmailSend mit maxAttempts 3, exponentielles Backoff
...
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com >
2026-04-17 10:32:40 +00:00
4a54d31bd0
fix: updateCampaignStatus überschreibt keine bestehenden Scheduling-Daten, fehlende Tests ergänzt
2026-04-17 09:55:45 +00:00
4245a1fbde
feat: Campaign Repository — CRUD mit Tenant-Isolation und Result-Pattern
...
Implementiert createCampaign, getCampaign, listCampaigns, updateCampaign und
updateCampaignStatus mit withTenant-Context, snake_case→camelCase Mapping und
Result-Pattern. 10 Unit-Tests, alle grün.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com >
2026-04-17 09:52:55 +00:00
c4d3c348c1
fix: CREATE OR REPLACE TRIGGER (idempotent), FK-Indizes für campaign_recipients und campaign_triggers
2026-04-17 08:59:38 +00:00
5a144e0ce4
feat: Migrationen für campaigns-Tabellen (PostgreSQL) und email_events (ClickHouse)
...
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com >
2026-04-17 08:57:37 +00:00
3c3088e66b
fix: execute mit optionalen Params, release(error) bei reset-Fehler, Tests ergänzt
2026-04-17 08:35:31 +00:00
4f739f7b1e
fix: release() absichern, DATABASE_URL Startup-Check, execute-Test hinzugefügt
2026-04-17 08:33:07 +00:00
c01befa477
fix: Einzelner shared Pool, finally-Block verschluckt nicht Original-Fehler, Pool-Error-Handler
...
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com >
2026-04-17 08:30:57 +00:00
cdfdd025d2
fix: Pool-Connection-Isolation in withTenant, SQL-Injection-Schutz, ClickHouse env-var-Check
...
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com >
2026-04-17 08:28:21 +00:00
ad0febe2cf
fix: QueryResultRow-Constraint für db.query<T> unter TypeScript strict
2026-04-17 08:24:15 +00:00
506197623a
feat: PostgreSQL withTenant-Helper und ClickHouse-Client
...
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com >
2026-04-17 08:20:25 +00:00
7c7fc23b8c
chore: CLAUDE.md, PROMPT.md und Planungs-Docs hinzufügen
2026-04-17 08:17:18 +00:00
689fbac795
fix: TriggerType-Typisierung, z.infer-Exporte, fehlende Tests für Result und hashEmail
...
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com >
2026-04-17 08:15:13 +00:00
b63ce058a0
feat: Projekt-Scaffold + Core Utilities — Result Pattern, hashEmail, Zod-Schemas, Campaign-Typen
...
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com >
2026-04-17 08:11:54 +00:00