feat(signup+admin): aliniere formular signup la landing + plan cerut, GDPR, control tier/trial in panou

Signup:
- /signup aliniat ca format la formularul din landing (campuri, etichete,
  placeholder-uri, select plan, checkbox GDPR, buton). Eticheta `name` = "Companie"
  (corecta: backendul salveaza nume de firma), uniform si in landing.
- Consimtamant GDPR validat server-side (functional, nu doar client-side) + salvat
  cu marca temporala (accounts.consent_at).
- Plan ales la signup salvat in accounts.requested_plan (intentie, NU drept): tier
  ramane sursa de adevar pentru gate-ul API; coloana pregateste integrarea platilor.
- landing: valorile `plan` = coduri tier (free/standard/pro/premium), data-plan
  sincronizat pe butoanele de pret; checkbox consimtamant primeste name.

Schema/DB:
- accounts: coloane noi requested_plan + consent_at (cu migrare aditiva in db.py).

Panou admin:
- Coloane noi: Plan curent (plan EFECTIV acum + zile trial ramase) si Plan cerut.
- Buton "Aplica" (POST /admin/set-tier): aloca plan real si INCHEIE trial-ul
  (efect imediat; altfel trial-ul Pro universal de 30z masca alegerea).
- Control "Trial Pro N zile" (POST /admin/set-trial via accounts.set_trial):
  acorda/prelungeste trial fara a schimba tier-ul de baza.

Teste: signup (consent obligatoriu, requested_plan persistat, tier ramane free),
panou admin (set-tier incheie trial, free opreste Pro imediat, set-trial, validari
+ CSRF). Call-site-urile existente POST /signup actualizate cu consent.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
Claude Agent
2026-06-29 16:02:37 +00:00
parent a29896a790
commit 851f76ca16
14 changed files with 528 additions and 42 deletions

View File

@@ -65,6 +65,7 @@ def test_signup_fara_cui_422(client):
"cui": "",
"email": "fara_cui@test.com",
"parola": "parolasecreta123",
"consent": "1",
"csrf_token": token,
})
# trebuie sa returneze 422 (sau sa randeze formularul cu eroare)
@@ -96,6 +97,7 @@ def test_signup_scrie_email_pe_account(client):
"cui": "RO9999001",
"email": "cu_email@test.com",
"parola": "parolasecreta123",
"consent": "1",
"csrf_token": token,
})
assert resp.status_code == 200
@@ -131,6 +133,7 @@ def test_signup_email_duplicat_mesaj_email(client):
"cui": make_test_cui("email-dup-c1"),
"email": "emaildup@test.com",
"parola": "parolasecreta123",
"consent": "1",
"csrf_token": token,
})
assert resp1.status_code == 200
@@ -145,6 +148,7 @@ def test_signup_email_duplicat_mesaj_email(client):
"cui": cui_nou,
"email": "emaildup@test.com",
"parola": "parolasecreta456",
"consent": "1",
"csrf_token": token2,
})
@@ -179,6 +183,7 @@ def test_signup_cui_existent_mesaj_prietenos(client):
"cui": "RO8888001",
"email": "firma1@test.com",
"parola": "parolasecreta123",
"consent": "1",
"csrf_token": token,
})
@@ -190,6 +195,7 @@ def test_signup_cui_existent_mesaj_prietenos(client):
"cui": "RO8888001",
"email": "firma2@test.com",
"parola": "parolasecreta456",
"consent": "1",
"csrf_token": token2,
})