feat: 添加货币管理功能,更新国际化支持,移除报表相关代码

This commit is contained in:
2026-05-21 16:24:56 +08:00
parent 6ecbaf5fb4
commit 055c613a6d
87 changed files with 1615 additions and 1319 deletions

View File

@@ -35,6 +35,7 @@ import {
TableRow,
} from "@/components/ui/table";
import { Textarea } from "@/components/ui/textarea";
import { useAdminCurrencyCatalog } from "@/hooks/use-admin-currency-catalog";
import { useAdminDateTimeFormatter } from "@/hooks/use-admin-datetime-formatter";
import { adminHasAnyPermission } from "@/lib/admin-permissions";
import { formatAdminMinorUnits } from "@/lib/money";
@@ -69,6 +70,7 @@ function settlementReviewStatusText(value: string | null, t: (key: string) => st
export function SettlementBatchDetailsConsole({ batchId }: Props) {
const { t } = useTranslation(["settlement", "common"]);
const profile = useAdminProfile();
useAdminCurrencyCatalog();
const canReviewSettlement = adminHasAnyPermission(profile?.permissions, [PRD_PAYOUT_REVIEW]);
const canManagePayout = adminHasAnyPermission(profile?.permissions, [PRD_PAYOUT_MANAGE]);
const formatDt = useAdminDateTimeFormatter();
@@ -77,7 +79,7 @@ export function SettlementBatchDetailsConsole({ batchId }: Props) {
const [loading, setLoading] = useState(true);
const [err, setErr] = useState<string | null>(null);
const [page, setPage] = useState(1);
const [perPage, setPerPage] = useState(25);
const [perPage, setPerPage] = useState(10);
const [acting, setActing] = useState<string | null>(null);
const [pendingAction, setPendingAction] = useState<SettlementAction | null>(null);
const [reviewRemark, setReviewRemark] = useState("");
@@ -224,20 +226,26 @@ export function SettlementBatchDetailsConsole({ batchId }: Props) {
</p>
<p>
<span className="text-muted-foreground">{t("totalBet")}</span>{" "}
<span className="font-mono tabular-nums">{formatAdminMinorUnits(summary.total_bet_amount)}</span>
<span className="font-mono tabular-nums">
{formatAdminMinorUnits(summary.total_bet_amount, summary.currency_code ?? "NPR")}
</span>
</p>
<p>
<span className="text-muted-foreground">{t("actualDeduct")}</span>{" "}
<span className="font-mono tabular-nums">{formatAdminMinorUnits(summary.total_actual_deduct)}</span>
<span className="font-mono tabular-nums">
{formatAdminMinorUnits(summary.total_actual_deduct, summary.currency_code ?? "NPR")}
</span>
</p>
<p>
<span className="text-muted-foreground">{t("payoutAmount")}</span>{" "}
<span className="font-mono tabular-nums">{formatAdminMinorUnits(summary.total_payout_amount)}</span>
<span className="font-mono tabular-nums">
{formatAdminMinorUnits(summary.total_payout_amount, summary.currency_code ?? "NPR")}
</span>
</p>
<p>
<span className="text-muted-foreground">{t("jackpotPayout")}</span>{" "}
<span className="font-mono tabular-nums">
{formatAdminMinorUnits(summary.total_jackpot_payout_amount)}
{formatAdminMinorUnits(summary.total_jackpot_payout_amount, summary.currency_code ?? "NPR")}
</span>
</p>
<p>
@@ -248,7 +256,7 @@ export function SettlementBatchDetailsConsole({ batchId }: Props) {
summary.platform_profit < 0 ? "text-destructive" : "text-emerald-700",
)}
>
{formatAdminMinorUnits(summary.platform_profit)}
{formatAdminMinorUnits(summary.platform_profit, summary.currency_code ?? "NPR")}
</span>
</p>
<p>
@@ -322,10 +330,13 @@ export function SettlementBatchDetailsConsole({ batchId }: Props) {
</TableCell>
<TableCell className="text-xs">{r.matched_prize_tier ?? "—"}</TableCell>
<TableCell className="text-right font-mono text-xs tabular-nums">
{formatAdminMinorUnits(r.win_amount)}
{formatAdminMinorUnits(r.win_amount, r.currency_code ?? summary.currency_code ?? "NPR")}
</TableCell>
<TableCell className="text-right font-mono text-xs tabular-nums">
{formatAdminMinorUnits(r.jackpot_allocation_amount)}
{formatAdminMinorUnits(
r.jackpot_allocation_amount,
r.currency_code ?? summary.currency_code ?? "NPR",
)}
</TableCell>
</TableRow>
))}
@@ -375,9 +386,9 @@ export function SettlementBatchDetailsConsole({ batchId }: Props) {
<div className="space-y-3">
<p className="rounded-md border bg-muted/30 p-3 text-sm">
{t("confirmAmountLine", {
actual: formatAdminMinorUnits(summary.total_actual_deduct),
payout: formatAdminMinorUnits(summary.total_payout_amount),
profit: formatAdminMinorUnits(summary.platform_profit),
actual: formatAdminMinorUnits(summary.total_actual_deduct, summary.currency_code ?? "NPR"),
payout: formatAdminMinorUnits(summary.total_payout_amount, summary.currency_code ?? "NPR"),
profit: formatAdminMinorUnits(summary.platform_profit, summary.currency_code ?? "NPR"),
})}
</p>
{pendingAction !== "payout" ? (

View File

@@ -42,6 +42,7 @@ import {
TableRow,
} from "@/components/ui/table";
import { Textarea } from "@/components/ui/textarea";
import { useAdminCurrencyCatalog } from "@/hooks/use-admin-currency-catalog";
import { adminHasAnyPermission } from "@/lib/admin-permissions";
import { formatAdminMinorUnits } from "@/lib/money";
import { cn } from "@/lib/utils";
@@ -84,6 +85,7 @@ function settlementReviewStatusText(value: string | null, t: (key: string) => st
export function SettlementBatchesConsole() {
const { t } = useTranslation(["settlement", "common"]);
const profile = useAdminProfile();
useAdminCurrencyCatalog();
const canReviewSettlement = adminHasAnyPermission(profile?.permissions, [PRD_PAYOUT_REVIEW]);
const canManagePayout = adminHasAnyPermission(profile?.permissions, [PRD_PAYOUT_MANAGE]);
const [data, setData] = useState<AdminSettlementBatchListData | null>(null);
@@ -94,7 +96,7 @@ export function SettlementBatchesConsole() {
const [draftStatus, setDraftStatus] = useState(STATUS_ALL);
const [appliedStatus, setAppliedStatus] = useState(STATUS_ALL);
const [page, setPage] = useState(1);
const [perPage, setPerPage] = useState(20);
const [perPage, setPerPage] = useState(10);
const [actingId, setActingId] = useState<number | null>(null);
const [pendingAction, setPendingAction] = useState<PendingAction | null>(null);
const [reviewRemark, setReviewRemark] = useState("");
@@ -252,13 +254,13 @@ export function SettlementBatchesConsole() {
<TableCell className="font-mono text-xs">{row.id}</TableCell>
<TableCell className="font-mono text-sm">{row.draw_no ?? "—"}</TableCell>
<TableCell className="text-right font-mono text-xs tabular-nums">
{formatAdminMinorUnits(row.total_bet_amount)}
{formatAdminMinorUnits(row.total_bet_amount, row.currency_code ?? "NPR")}
</TableCell>
<TableCell className="text-right font-mono text-xs tabular-nums">
{formatAdminMinorUnits(row.total_actual_deduct)}
{formatAdminMinorUnits(row.total_actual_deduct, row.currency_code ?? "NPR")}
</TableCell>
<TableCell className="text-right font-mono text-xs tabular-nums">
{formatAdminMinorUnits(row.total_payout_amount)}
{formatAdminMinorUnits(row.total_payout_amount, row.currency_code ?? "NPR")}
</TableCell>
<TableCell
className={cn(
@@ -266,7 +268,7 @@ export function SettlementBatchesConsole() {
row.platform_profit < 0 ? "text-destructive" : "text-emerald-700",
)}
>
{formatAdminMinorUnits(row.platform_profit)}
{formatAdminMinorUnits(row.platform_profit, row.currency_code ?? "NPR")}
</TableCell>
<TableCell className="text-xs text-muted-foreground">
{settlementReviewStatusText(row.review_status, t)}
@@ -368,9 +370,18 @@ export function SettlementBatchesConsole() {
<div className="space-y-3">
<p className="rounded-md border bg-muted/30 p-3 text-sm">
{t("confirmAmountLine", {
actual: formatAdminMinorUnits(pendingAction.row.total_actual_deduct),
payout: formatAdminMinorUnits(pendingAction.row.total_payout_amount),
profit: formatAdminMinorUnits(pendingAction.row.platform_profit),
actual: formatAdminMinorUnits(
pendingAction.row.total_actual_deduct,
pendingAction.row.currency_code ?? "NPR",
),
payout: formatAdminMinorUnits(
pendingAction.row.total_payout_amount,
pendingAction.row.currency_code ?? "NPR",
),
profit: formatAdminMinorUnits(
pendingAction.row.platform_profit,
pendingAction.row.currency_code ?? "NPR",
),
})}
</p>
{pendingAction.action !== "payout" ? (