Admin USD Wallet Transaction Detail View
Goal: add a detail screen for each row in Admin > USD Wallets so admins can:
- view complete transaction data (not only in/out direction),
- make faster approve/reject decisions for pending withdrawals,
- debug balance/fee/reversal discrepancies.
Data Scope Reviewedβ
- The admin list currently reads from API
GET /admin/usd-wallets/ledger. - Each ledger row is a
UsdWalletTransactionrecord withusdWalletrelation. - Main field sources:
kioskgaming_backend/src/database/models/UsdWalletTransaction.jskioskgaming_backend/src/controllers/admin/usdWalletManagementController.jskioskgaming_backend/src/controllers/shop/shopUsdWalletController.jskioskgaming_backend/src/controllers/agent/agentUsdWalletController.jskioskgaming_backend/src/controllers/superAgent/superAgentUsdWalletController.jskioskgaming_backend/src/services/core/depositSettlementCoreService.js
Target Usersβ
- Finance operations admins.
- Withdrawal approval admins.
- Technical admins investigating ledger/metadata consistency.
UX Principle: Avoid Raw IDs as Primary Displayβ
Raw IDs are useful for debugging, but they should not be the primary surface for operational users. For day-to-day workflows, the UI should prioritize human-readable labels and keep technical IDs secondary.
Recommended principle:
- Primary line: human-readable identity (
name,email,phone, short transaction code). - Secondary line: technical identifier (
id, UUID, wallet id) in smaller monospace text. - Always provide copy for technical IDs, but do not force users to read them first.
Recommended User Flow (List to Detail)β
- Open
Admin > USD wallets. - Filter by owner/date and click
Load. - In the
Actionscolumn, clickViewon the target row. - Open
Transaction detail(modal or dedicated page). - Review sections in this order:
Header(transaction identity),Money(amounts and balance snapshots),Reference(linked transaction context),Operational(payout/admin decision),Raw metadata(deep debugging).
- If the transaction is a
pendingwithdrawal, proceed toApprove/Reject.
Fields to Display on Transaction Detailβ
1) Identity + Owner (Always Visible)β
id(UUID ledger row)transactionId(idempotency/business transaction id)type(deposit|withdrawal|adjustment|reversal)status(pending|completed|failed|cancelled)providerreferenceTypereferenceIdusdWallet.idusdWallet.ownerTypeusdWallet.ownerIdusdWallet.currencycreatedAtupdatedAt
Display guidance:
- Put
transactionIdin a prominent position with a one-click copy control (icon). - Render
typeandstatusas color badges (green/red/amber/gray). - Provide owner navigation link (
shop/agent/super-agent) when route mapping exists. - Do not show
ownerIdalone. Show display text first, e.g.:Shop Β· Lucky Star (shop@...)Agent Β· John Doe (+1-***-***-1234)Super agent Β· Alpha Group
- Keep
ownerIdas secondary/debug text only.
2) Amount + Balance Snapshot (Always Visible)β
amountGrossamountNetbalanceGrossBeforebalanceGrossAfterbalanceNetBeforebalanceNetAfter
Display guidance:
- Show both formatted values and raw values (for debugging precision issues).
- Show visual delta sign (+/-) based on
type. - Add summary lines:
Net change:balanceNetAfter - balanceNetBeforeGross change:balanceGrossAfter - balanceGrossBefore
3) Common Metadata (Render if Key Exists)β
metadata.notemetadata.createdBymetadata.sourcemetadata.matchedFeeMethodId
Display guidance:
- Render dynamically by existing keys (do not hardcode one shape).
- Long values should support expand/collapse.
4) Portal Withdrawal-Specific Metadataβ
Applies to type=withdrawal rows (especially pending/completed/cancelled):
metadata.payoutNetworkmetadata.payoutWalletAddressmetadata.requestedNetUsdmetadata.computedFeeRatemetadata.computedFeeUsdmetadata.computedGrossDebitUsd
Display guidance:
- Group these into a
Withdrawal payout infosection. - Add copy control for
payoutWalletAddress. - Show fee as both percentage and USD amount.
5) Admin Decision Metadata (Approve/Reject)β
metadata.adminApproval.approvedAtmetadata.adminApproval.approvedByAdminIdmetadata.adminApproval.notemetadata.adminRejection.rejectedAtmetadata.adminRejection.rejectedByAdminIdmetadata.adminRejection.note
Display guidance:
- Split into small
ApprovalandRejectionblocks. - If both are missing, show:
No admin decision yet.
6) Reversal Metadata for Rejected Withdrawalβ
For type=reversal rows (created by admin rejection):
metadata.sourceWithdrawalIdmetadata.sourceWithdrawalTransactionIdmetadata.note
Display guidance:
- Show backlink to source withdrawal if route exists.
- Add label:
Auto-generated reversal.
7) Deposit Settlement Metadata (Payer Side)β
Common on type=deposit rows:
metadata.feeKnownmetadata.platformFeeAmountmetadata.platformFeeRatemetadata.originalCurrencymetadata.buyerTypemetadata.buyerIdmetadata.creditComputedmetadata.costRateAtPurchasemetadata.usedCallbackNetUsdmetadata.receivedNetUsd
Display guidance:
- Group under a
Settlement snapshotsection. - Add tooltips for technical keys such as
usedCallbackNetUsd.
Detailed UI Proposal (User Guidance)β
A. Header bar (sticky if full page)β
- Left:
Type badge+Status badge. - Center:
transactionId(monospace + copy icon control). - Right:
CreatedAt,UpdatedAt,Backbutton.
UX objective:
- Admin identifies the transaction and current state in under 2 seconds.
B. Section "Owner & Context"β
- Show:
- Owner type, owner id, currency.
- Wallet id.
- Provider.
- Add
Open owner profileif route mapping exists.
UX objective:
- Quickly confirm ownership and avoid acting on the wrong account.
C. Section "Money Movement" (Most Important)β
- Card 1:
Amount(amountGross,amountNet). - Card 2:
Before balance(balanceGrossBefore,balanceNetBefore). - Card 3:
After balance(balanceGrossAfter,balanceNetAfter). - Card 4:
Delta(gross/net).
UX objective:
- Let admins validate before/after balances at a glance.
D. Section "Reference"β
referenceType,referenceId.- Deep-link / embed when
referenceType = payment_transaction(see catalog below: inline detail + optional βopen full pageβ). - If no route mapping, provide a copy control (icon button with tooltip /
aria-label) forreferenceId.
UX objective:
- Jump quickly to related source transaction for investigation.
Display refinement for end users:
- Prefer business-friendly label over raw reference id when possible:
- Example:
Payment transaction #PTX-2026-000123instead of UUID-only.
- Example:
- Show full raw
referenceIdonly in expandable debug row or tooltip.
E. Section "Operational Details" (conditional)β
- Render only when relevant keys exist:
Withdrawal payout info(network/address/fee).Admin decision(approve/reject).Settlement snapshot(deposit settlement metadata).Reversal trace(source withdrawal).
UX objective:
- Reduce noise by showing only data-backed blocks.
F. Section "Raw Metadata JSON"β
- JSON viewer read-only.
- Include copy-as-JSON control (icon + accessible label, e.g. βCopy metadata as JSONβ) +
Expand allwhere supported. - Place at the bottom.
UX objective:
- Support deep technical debugging without disrupting primary review flow.
Field Rendering Rulesβ
- Do not hardcode one schema; prefer key-existence rendering.
- Mandatory blocks: identity, owner, amounts, balance snapshots, timestamps.
- Metadata is optional: render only existing keys.
- Long strings (
payoutWalletAddress, notes) must support wrap + copy. - Numeric formatting should be consistent:
- UI display: 2-8 decimals depending on field.
- Hover/tooltip: full raw value.
Identity display rules (important):
- Never use UUID as the only visible identity in primary rows/cards.
- Default label priority for owner:
nameemail- masked
phone - short-form id (only if no better identity exists)
- Keep full IDs in:
- copy control (icon + label),
- tooltip,
- debug section (
Raw metadata/Technical details).
Masking guidance:
- Email: partially masked in dense table context (full in detail if permission allows).
- Phone: masked by default (
***), full value only for authorized roles.
States and User Messagesβ
Loading: section-level skeletons (avoid full-page blocking if previous data exists).Not found: "Transaction does not exist or has been archived."No metadata: "No additional metadata recorded."Permission denied: "You do not have permission to view this transaction detail."
Suggested Microcopyβ
- Title:
USD Wallet Transaction Detail - Subtitle:
Review amounts, balances, references, and operational metadata. - Copy success toast:
Copied to clipboard. - Empty block:
No data available for this section. - Technical row label:
Technical ID - Human label row:
Display name
Reference Type Catalog (Display Reference)β
The following catalog defines each known referenceType, business meaning, and how the UI should display it.
1) payment_transactionβ
- Business meaning:
- USD wallet ledger row is linked to a payment transaction flow (deposit/withdrawal/settlement source).
- Display reference:
- Primary label:
Payment transaction - Secondary: technical
referenceId(copyable).
- Primary label:
- Navigation:
- Prefer inline embed in the same USD wallet transaction detail panel: call
GET /admin/transactions/:idwithid = referenceId(numeric internal id) and render the same payment-transaction detail cards used on the full transaction page (variant="embedded"), so admins see ledger + linked flow without leaving the modal. - Keep a secondary action: deep link
/transactions/:referenceId(βOpen full pageβ) for bookmarking, sharing, or side-by-side review.
- Prefer inline embed in the same USD wallet transaction detail panel: call
2) balance_to_creditsβ
- Business meaning:
- Ledger relates to converting balance into credits.
- Display reference:
- Primary label:
Balance to credits - Secondary: technical
referenceId.
- Primary label:
- Navigation:
- No direct route mapping currently.
3) usd_wallet_transactionβ
- Business meaning:
- Ledger row references another USD wallet transaction (common in reversal/chained operations).
- Display reference:
- Primary label:
USD wallet transaction - Secondary: technical
referenceId.
- Primary label:
- Navigation:
- If/when detail route exists, should point to USD wallet transaction detail by id.
- Current state: text + copy only.
4) balance_to_credits_settlementβ
- Business meaning:
- Settlement stage for balance-to-credits process.
- Display reference:
- Primary label:
Balance to credits settlement - Secondary: technical
referenceId.
- Primary label:
- Navigation:
- No route mapping currently.
5) usd_withdrawal_requestβ
- Business meaning:
- Row created from online-balance USD withdrawal request (portal initiated).
- Display reference:
- Primary label:
USD withdrawal request - Secondary: technical
referenceId.
- Primary label:
- Navigation:
- No dedicated route mapping currently.
- Operational details are mainly read from metadata (
payoutNetwork,payoutWalletAddress, fee fields).
6) online_debt_settlementβ
- Business meaning:
- Related to online debt settlement workflow.
- Display reference:
- Primary label:
Online debt settlement - Secondary: technical
referenceId.
- Primary label:
- Navigation:
- No direct route mapping currently.
7) admin_shop_adjustmentβ
- Business meaning:
- Admin-triggered shop adjustment flow.
- Display reference:
- Primary label:
Admin shop adjustment - Secondary: technical
referenceId.
- Primary label:
- Navigation:
- No direct route mapping currently.
8) hierarchy_withdrawalβ
- Business meaning:
- Withdrawal within hierarchy flow (agent/super-agent tier withdrawal handling).
- Display reference:
- Primary label:
Hierarchy withdrawal - Secondary: technical
referenceId.
- Primary label:
- Navigation:
- No direct route mapping currently.
9) null / empty reference typeβ
- Business meaning:
- Source reference not recorded or not applicable for that row.
- Display reference:
- Primary label:
Reference - Secondary: show
referenceIdonly if present, otherwiseβ.
- Primary label:
- Navigation:
- No deep link.
UI rule for all reference typesβ
- Always show human-readable label first (primary).
- Keep raw
referenceIdas technical secondary row with a copy control (prefer icon +aria-label/titleover large text buttons). - Only render deep link / inline embed for types explicitly mapped (currently
payment_transactionfor embed + full page). - Unknown or legacy
referenceTypevalues (including rows written before a reference convention changed) should auto-fallback to:- primary label =
referenceTypetransformed from snake_case (orReferencewhen empty), - secondary = raw
referenceId.
- primary label =
API for Detail Viewβ
Current option (reuse list payload):
- Open modal/page detail directly from selected list row data.
If you need dedicated API for SSR/deep-link:
- Add endpoint
GET /admin/usd-wallets/ledger/:idreturning:- full
UsdWalletTransactionfields, - relation
usdWallet - (optional) resolved owner display name (shop/agent/super-agent) to reduce extra calls.
- full
UI Implementation Checklist (Suggested)β
- Detail route or detail modal is accessible from list.
- All always-visible fields are rendered.
- Metadata rendering is dynamic by key existence.
- Copy controls (e.g. icon buttons with labels) exist for
transactionId,referenceId,walletAddress, raw JSON. - Deep-link is available for mapped
referenceType. - Clear loading/error/not-found states are implemented.
- Color badges exist for
typeandstatus. - Layout is responsive (desktop and small laptop widths).
- Owner and reference are shown with human-readable labels first; raw IDs are secondary.
- Masking and permission-based visibility are applied for sensitive contact fields.