Gründer-Tickets: 50%-Rabatt-Weitergabe pro Gründer gedeckelt + Pro-Wording korrigiert

Rene: 'ungern jemandem auf ewig die Möglichkeit geben 50% Rabatt zu vergeben —
bei 100 Gründern ein großer Faktor. Ich hätte jedem 25–50 Tickets gegeben.'

- users.founder_referral_tickets (Default 25): Kontingent an 50%-Rabatten,
  die ein Gründer an Geworbene weitergeben kann. Technisch = die ersten N
  VERIFIZIERTEN Geworbenen (nach Anmeldedatum) bekommen 50%, danach 0.
  Unbestätigte verbrauchen kein Ticket. In scheduler.py (Rechnung) + admin.py
  (Vorschau) konsistent.
- BUGFIX nebenbei: admin.py zeigte für referred_by_founder fälschlich 100%
  statt 50% (scheduler war korrekt) — jetzt beide 50%.
- Admin: Grant-Formular bekommt Feld 'Gründer-Tickets' (0–200, Vorbelegung
  aus User-Stand); Endpoint /grant akzeptiert founder_tickets.
- Gründer-Seite + Settings + Admin-Hilfe: 'sobald Bezahlfunktionen aktiv sind'
  raus (Pro kostet bereits); Vorteil 'lebenslang Pro gratis' + '25 Freunde
  zum halben Preis' (Ticket-Framing).
- Tests: test_founder_tickets.py (Cap, Unverified-Schutz, 50%-Bugfix, Grant).
  Suite: 64 passed.
This commit is contained in:
rene 2026-06-08 06:20:19 +02:00
parent 98ec6c36c6
commit 60fb866283
13 changed files with 154 additions and 35 deletions

View file

@ -1352,10 +1352,19 @@ def _get_discount_info(conn, user_id: int) -> dict:
referred_by = row["referred_by"] or 0
if referred_by > 0:
referrer = conn.execute(
"SELECT is_founder, is_founder_pending FROM users WHERE id=?", (referred_by,)
"SELECT is_founder, is_founder_pending, founder_referral_tickets FROM users WHERE id=?", (referred_by,)
).fetchone()
if referrer and (referrer["is_founder"] or referrer["is_founder_pending"]):
return {"discount_pct": 100, "reason": "referred_by_founder", "referral_count": row["referral_count"]}
# 50%-Weitergabe nur innerhalb des Ticket-Kontingents des Gründers
# (Rang unter den verifizierten Geworbenen ≤ Tickets). 50%, NICHT 100%.
rank = conn.execute(
"""SELECT COUNT(*) FROM users
WHERE referred_by=? AND email_verified=1
AND created_at <= (SELECT created_at FROM users WHERE id=?)""",
(referred_by, user_id)
).fetchone()[0]
if rank <= (referrer["founder_referral_tickets"] or 0):
return {"discount_pct": 50, "reason": "referred_by_founder", "referral_count": row["referral_count"]}
count = row["referral_count"]
for threshold, pct in [(50, 50), (20, 30), (10, 20)]: