Skip to content

VIP Program

Purpose

The VIP Program screen manages VIP applications and the VIP tier catalog. Players apply for VIP via the player site; compliance + partnerships review applications here. The screen also exposes the per-tier perks (cashback %, dedicated host flag, withdrawal cap bumps).

Audience

VIP / partnerships, compliance (KYC tier prerequisite), risk (vetting application).

Path in admin-fe

Screen URL Page
VIP applications list /vip-program ebit-admin-fe/src/app/(dashboard)/vip-program/page.tsx
VIP application detail /vip-program/[id] ebit-admin-fe/src/app/(dashboard)/vip-program/[id]/page.tsx

Backing API endpoints

Endpoint Source
GET /admin/vip-program/all (list applications) apps/api/src/vip-program/admin/vip-program-admin.controller.ts:30
GET /admin/vip-program/:id (one application) apps/api/src/vip-program/admin/vip-program-admin.controller.ts:36
PATCH /admin/vip-program/:id/status (approve / reject / pending) apps/api/src/vip-program/admin/vip-program-admin.controller.ts:42
DELETE /admin/vip-program/:id (drop application) apps/api/src/vip-program/admin/vip-program-admin.controller.ts:53

Frontend wiring: ebit-admin-fe/src/queries/vip-program/.

Key actions

Action Required permission API call DB tables touched Audit-logged?
List VIP applications vip.application.view GET /admin/vip-program/all VipApplication, User yes
View one application vip.application.view GET /admin/vip-program/:id VipApplication, UserStats yes
Set status (approve / reject / hold) vip.application.action PATCH /admin/vip-program/:id/status VipApplication.status, VipMember (on approve) yes
Delete application vip.application.action DELETE /admin/vip-program/:id VipApplication yes

The VIP tier catalog (VipLevel records — bronze / silver / gold / platinum / diamond, with cashback %, perks) is read by the player UI; the admin panel doesn't expose a tier-editor screen — schema changes go through engineering.

Filters and views

  • StatusPENDING / APPROVED / REJECTED / ON_HOLD.
  • Tier requested — bronze / silver / gold / platinum / diamond.
  • Date range.
  • Search by user — username / email.
  • SortcreatedAt, wageredUSD.

Common workflows

  1. Daily VIP application triage. Partnerships opens /vip-program, filters PENDING. For each, opens detail. Reviews KYC level (must be ≥ 2), wager total, deposit total, country status. Approves via PATCH .../status { status: APPROVED, tier: ... }.
  2. Auto-tier from wagering. No automatic promotion in code. Operator sees a player has crossed wagering threshold for next tier; manually applies.
  3. Reject ineligible application. Player applied with KYC=0. Reject with reason note. Player gets in-app notification (rt service).
  4. Promote existing VIP to a higher tier. No "edit tier" endpoint. Operator deletes the existing VIP record, creates a new application at higher tier, approves. Or engineering does it via raw DB. Improvement tracked.
  5. De-VIP a player. Set status REJECTED (effective revoke) or DELETE to drop the record. Player loses cashback % at next bet.

Edge cases / gotchas

  • No tier-edit endpoint. Approving creates a VipMember at the requested tier; you cannot promote in place. Workaround above.
  • VIP perks (cashback %) ride on VipLevel.cashbackPercent — bet-settle flow reads this. Editing the VipLevel catalog requires a deploy.
  • Approval does NOT bump withdraw limits automatically — those still come from KYC. VIP affects perks only (cashback, host).
  • Application carries free-text reason for rejection / hold; player sees it in their account history.
  • Application has no time-to-live. Stale PENDINGs accumulate. Operations should sweep weekly.
  • Bot users cannot apply. Player-side endpoint blocks User.isBot=true.
  • VIP host assignment is a flag on VipMember, no per-host workload view in the admin UI.
  • Per-user VIP status: user-profile.md → VIP tab
  • Wager / deposit prerequisites: dashboard.md → users-stats
  • KYC tier prerequisite: kyc-limits.md
  • Player-side VIP application endpoint: apps/api/src/vip-program/players/vip-program.controller.ts
  • Audit: admin-logs.md
  • Permission keys: libs/auth/src/permissions/const.ts:228-235

Sequence — approving a VIP application

sequenceDiagram
    actor partner
    participant admin-fe
    participant api
    participant pg as Postgres
    partner->>admin-fe: open /vip-program, filter PENDING
    admin-fe->>api: GET /admin/vip-program/all?status=PENDING
    api->>api: PermissionGuard('vip.application.view')
    api->>pg: SELECT VipApplication WHERE status=PENDING JOIN User
    pg-->>api: rows
    api-->>admin-fe: applications
    partner->>admin-fe: open one, review KYC + wager, click Approve gold
    admin-fe->>api: PATCH /admin/vip-program/:id/status { status: APPROVED, tier: gold }
    api->>api: PermissionGuard('vip.application.action')
    api->>pg: UPDATE VipApplication SET status=APPROVED
    api->>pg: INSERT VipMember (userId, tier=gold, cashbackPercent from VipLevel)
    api->>pg: INSERT AdminActionLog
    api-->>admin-fe: 200 OK
    admin-fe-->>partner: row removed from PENDING