onFeaturePaid wertet den Fall aus markPaid aus. Trifft die Zahlung eine Funktion, die schon freigeschaltet, in Einrichtung oder abgeschaltet ist, geht nur eine Team-Meldung raus (T16 Block bereits_aktiv, bei Abo-Ende vor der Einrichtung T19), kein Ticket und keine K15. Beide Meldungen laufen genau einmal je Dokument: unter feature-meldung:<id> frisch lesen, Marker zahlungMeldung gemeldet erst nach gesendeter Mail. Scheitert der Versand, wirft onFeaturePaid (Webhook 500), Stripe wiederholt und der naechste Versuch sendet genau einmal. meldeErstattung ist die einzige Stelle fuer T19 (Zahlung nach dem Abo-Ende und spaeter die Meldung des Abo-Abgleichs), wirft nie. Bei Funktionen mit Wartungs-Abo-Pflicht zeigt T16 nach der Verbuchung den Block kein_abo, wenn das Abo nicht mehr laeuft; ein Lesefehler laesst den Block aus und blockiert nichts. customerOf und projectName sind exportiert. Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
Webklar Kundenbereich
Kundenportal für Website-Projekte. Liest ausschließlich aus woms-database auf ticket.webklar.com (Ticketsystem). Es gibt keine eigene Portal-Datenbank mehr.
- Keine Kundenanlage im Portal
- Keine Admin-Funktionen
- Login über Appwrite Auth (ein User pro Kunde, verknüpft über
customers.appwriteUserId)
Verwaltung (Kunden, Passwörter, Projekte, Freischaltung): Ticketsystem.
Struktur
server/ Express-API, Appwrite, Gitea-Webhook
public/ Login & Dashboard (statisch)
Schnellstart
cp .env.example .env
# SESSION_SECRET (min. 32 Zeichen) und APPWRITE_API_KEY setzen
npm install
npm run dev
Öffnen: http://localhost:3000
API
| Methode | Pfad | Beschreibung |
|---|---|---|
| POST | /api/auth/login |
Appwrite Login + Portal-Prüfungen |
| POST | /api/auth/logout |
Session beenden |
| GET | /api/auth/me |
Aktueller Kunde |
| GET | /api/projects |
Eigene websiteProjects |
| GET | /api/features |
Eigene portalFeatures (enabled) |
| POST | /webhook/gitea?token=… |
Gitea Push → Deploy + DB-Update |
Appwrite
Schema und Collection-Anlage: siehe APPWRITE_SCHEMA.md.
Endpoint: https://ticket.webklar.com/v1
Project: 6a1058610003c5a13a05
Database: woms-database
Gitea / Preview
- Template: https://git.webklar.com/knso/webklar-preview-template.git
- Webhook-URL:
https://project.webklar.com/webhook/gitea - Secret:
GITEA_WEBHOOK_TOKENin.env - Vorschau:
https://<subdomain>.project.webklar.com
customerId wird im Ticketsystem am websiteProjects-Eintrag gesetzt, nicht im Webhook.
E-Mails
Alle automatischen Mails sind HTML-Vorlagen mit Textfassung in server/mail-templates/
(K01–K11 an Kunden, T01–T11 ans Team; Design aus Claude Design). Jede Vorlage nennt im
Kopfkommentar Betreff, Platzhalter ({{name}}) und optionale Blöcke
(<!-- WENN x --> … <!-- ENDE x -->). Eine neue Fassung aus dem Design kann die Datei direkt
ersetzen, solange Platzhalter und Blöcke gleich heißen; npm test prüft das. Das Logo in den
Mails liegt unter public/webklar-logo.png.
Deployment
npm start
# Reverse Proxy (nginx) → Port 3000
# PREVIEW_DEPLOY_ROOT für statische Vorschau-Dateien