Skip to content

Deposits history

Purpose

The Deposits screen is a read-only audit log of every player deposit (crypto, fiat, Skindeck steam-skins). Operators use it to confirm received amounts, investigate "I deposited but balance didn't update" complaints, and reconcile against vault inflow.

Audience

Customer support (primary), finance (reconciliation), risk (chargeback investigation). No write actions on this screen.

Path in admin-fe

Screen URL Page
Deposits list /deposits ebit-admin-fe/src/app/(dashboard)/deposits/page.tsxcomponents/pages/deposits/

Backing API endpoints

Endpoint Source
GET /admin/payments/deposit (list) apps/api/src/payment/deposit/admin.deposit.controller.ts:20
GET /admin/payments/deposit/:id apps/api/src/payment/deposit/admin.deposit.controller.ts:31

Frontend wiring: ebit-admin-fe/src/queries/deposit-history/.

Key actions

Action Required permission API call DB tables touched Audit-logged?
List deposits deposits.view GET /admin/payments/deposit Deposit, User (joined) yes
View one deposit deposits.view GET /admin/payments/deposit/:id Deposit, provider raw payload yes

There is no admin re-credit endpoint on this screen. To compensate a player for a stuck deposit, use the tip flow on user-profile.md (POST /admin/admin-tips) — that path is auditable and SuperAdmin-only.

Filters and views

  • StatusPENDING, CONFIRMED, FAILED, EXPIRED.
  • User ID — drill-in from a profile.
  • Provider — NowPayments, CCPayment, Skindeck.
  • Currency / network — BTC, ETH, USDT-erc20, etc.
  • Amount range (USD-equiv).
  • Date range.
  • SortCREATED_AT, AMOUNT_USD.

Common workflows

  1. "I deposited but my balance didn't update." CS asks for tx hash. Filter /deposits by user, look for matching tx. If status=PENDING, advise the player to wait for confirmations. If status=CONFIRMED but balance not credited, escalate (this is the flows/deposit-flow failure mode — see flows/).
  2. Reconcile a vault deposit. Finance picks a date range, exports CSV, sums by currency, cross-checks against on-chain ledger and Vault* tables visible on dashboard.md → finances tab.
  3. Investigate a chargeback. Compliance opens the deposit by ID, copies the provider tx ref, opens provider dashboard for full chain proof. Cross-links to player profile for follow-up restrictions.
  4. Find Skindeck deposits stuck. Filter provider=skindeck AND status=PENDING. Skindeck has its own BullMQ queue and known timing variability — see project_evologger_trace_correlation memory.
  5. Monthly first-time-deposit (FTD) cohort. Filter status=CONFIRMED AND first deposit per user. Cross-reference dashboard.md FTD KPI for sanity.

Edge cases / gotchas

  • PENDING can sit for hours on slow networks (BTC). Don't escalate before checking confirmations on-chain.
  • Skindeck deposits ride a separate webhook + BullMQ queue. State transitions are async; UI may show stale data for ~30s. Refresh.
  • Provider paymentId is NOT Deposit.id. They are separate identifiers; player ID must come from the Deposit.userId join. Don't paste a Deposit.id into the provider dashboard.
  • No "credit manually" button. This is intentional. To credit a player off-flow, use the admin-tips path. There is no audit-equivalent direct-credit on Deposit.
  • No CSV export from the API. The frontend table component supports browser-side CSV. There is no ?format=csv param on GET /admin/payments/deposit.
  • Exchange rate at time of deposit is fixed. Deposit.amountUsd is computed at confirmation time. Later FX changes do not retro-update — finance uses this on purpose for daily P&L.

Sequence — investigating a stuck deposit

sequenceDiagram
    actor admin
    participant admin-fe
    participant api
    participant pg as Postgres
    participant provider as Payment provider
    admin->>admin-fe: open /deposits, filter user=123, status=PENDING
    admin-fe->>api: GET /admin/payments/deposit?userId=123&status=PENDING
    api->>api: PermissionGuard('deposits.view')
    api->>pg: SELECT Deposit JOIN User WHERE userId=123 AND status=PENDING
    pg-->>api: 1 row
    api-->>admin-fe: list
    admin->>admin-fe: click row → drill-in
    admin-fe->>api: GET /admin/payments/deposit/:id
    api->>pg: SELECT Deposit by id (with raw provider payload)
    pg-->>api: row + payload JSON
    api-->>admin-fe: full record
    admin->>provider: open provider dashboard with tx ref
    provider-->>admin: 12 confirms — should have credited
    admin->>admin-fe: escalate via Telegram + incident channel