SilentChat

Empfehlungs-Programm — Stripe-Integration

Zuletzt aktualisiert: 14. Mai 2026

Reward-Wege

Drei Reward-Typen, drei verschiedene Stripe-Mechaniken.

credit — Customer-Balance-Transaction

Ein customer.balance_transaction mit negativem Betrag wird auf den Werber-Customer gebucht. Stripe wendet das Guthaben automatisch auf die nächste Rechnung an (negative Position „Empfehlungs-Gutschrift").

  • Werbedauer: solange der Stripe-Customer existiert.
  • Multi-Currency: Stripe wandelt automatisch auf die Customer-Currency um; den Konvertierungs-Kurs loggen wir in den Referral-Notes.
  • Wird bei aktivem Stripe Tax als Pre-Tax-Rabatt behandelt — die Umsatzsteuer reduziert sich proportional.

coupon — Subscription-Discount

Der konfigurierte Stripe-Coupon wird via subscription.update (Feld discounts) auf die aktive Subscription des Werbers gelegt. Wirkt auf die nächste Rechnung.

  • Wichtig: Stripe stackt nicht zwei Coupons; ein neues Add ersetzt einen vorigen Coupon auf derselben Subscription.
  • Coupon muss existieren: bei Aktivierung eines neuen Reward- Setups einmal manuell testen (Werbung auf Test-Tenant qualifizieren
    • granten).

trial_extension — Subscription-trial-end-update

subscription.update mit neuem trial_end (alter Wert + konfigurierte Tage). proration_behavior=none damit keine Mid-Cycle-Berechnung ausgelöst wird.

  • Nur wirksam wenn subscription.status == trialing; konvertierte Subscriptions sind no-op (Grant-Routine sollte dann auf credit fallback'en — derzeit wird der Lifecycle-Status auf rewarded gesetzt mit reward_days snapshot, aber keine Stripe-Mutation).

Idempotency

Jeder Stripe-Call carries einen deterministischen Idempotency-Key:

  • Grant: referral_grant_<referral_id>
  • Clawback: referral_clawback_<referral_id>

Bedeutet: ein zweiter Cron-Tick oder ein manueller Klick auf „Reward auszahlen" produziert keine doppelte Buchung — Stripe erkennt den Key und gibt dieselbe Transaktion zurück.

Clawback

Der customer.subscription.deleted-Webhook (oder charge.refunded / charge.dispute.created) ruft ClawbackOnChurn(tenantID) auf. Pro rewarded Werbung im Clawback-Fenster:

  • Credit: gegenläufige balance_transaction mit positivem Betrag.
  • Coupon / Trial-Extension: nicht retro-reversibel — Werbung wird nur lokal als Storniert markiert + auditiert.

Stripe-Outage

Wenn der Grant-Stripe-Call fehlschlägt:

  1. Referral bleibt auf Status Qualifiziert (nicht auf Rewarded).
  2. Die Notes-Spalte bekommt einen Zeitstempel + Fehler-Grund.
  3. referral.grant_failed Audit-Event wird geschrieben.
  4. Der nächste Cron-Tick versucht es erneut — der Idempotency-Key garantiert keine Doppel-Buchung.

Wenn ein einzelner Werber dauerhaft keinen Stripe-Customer hat (z.B. Manual-Subscription ohne Stripe-Setup): der Grant schlägt jedes Mal fehl. Lösung: entweder Stripe-Customer manuell anlegen, oder die Werbung manuell stornieren.

Coupon-Konflikte

  • Stripe-Coupon hat max_redemptions=1 und wurde schon woanders eingelöst → Grant schlägt fehl, Admin-Alert.
  • Stripe-Coupon wurde gelöscht → Grant schlägt fehl, Admin-Alert.
  • Stripe-Coupon ist abgelaufen (redeem_by Zeitpunkt überschritten) → Grant schlägt fehl.

In allen drei Fällen: Werbung bleibt Qualifiziert; Admin repariert den Coupon und triggert den nächsten Cron-Tick (oder klickt manuell „Reward auszahlen" auf der Detailseite).

Empfehlungs-Programm — Stripe-Integration — Help Center — SilentChat | SilentChat