253 lines
9.0 KiB
TypeScript
253 lines
9.0 KiB
TypeScript
import { afterEach, expect, test, vi } from "vitest";
|
|
import { setAccessToken } from "@/shared/api/request";
|
|
import {
|
|
createCoinAdjustment,
|
|
createFullServerNoticeFanout,
|
|
exportCoinSellerLedger,
|
|
getGiftDiamondRatios,
|
|
getWheelConfig,
|
|
getWheelDrawSummary,
|
|
listCoinAdjustments,
|
|
listCoinSellerLedger,
|
|
listWheelDraws,
|
|
lookupCoinAdjustmentTarget,
|
|
updateGiftDiamondRatios,
|
|
updateWheelConfig,
|
|
} from "./api";
|
|
|
|
afterEach(() => {
|
|
setAccessToken("");
|
|
vi.unstubAllGlobals();
|
|
});
|
|
|
|
test("gift diamond ratio APIs use operations paths", async () => {
|
|
vi.stubGlobal(
|
|
"fetch",
|
|
vi.fn(async () => new Response(JSON.stringify({ code: 0, data: { regionId: 1001, items: [] } }))),
|
|
);
|
|
|
|
await getGiftDiamondRatios(1001);
|
|
await updateGiftDiamondRatios({
|
|
regionId: 1001,
|
|
ratios: { lucky: "40.00", normal: "30.00", super_lucky: "50.00" },
|
|
returnCoinRatios: { lucky: "10.00", normal: "30.00", super_lucky: "1.00" },
|
|
});
|
|
|
|
const [getUrl, getInit] = vi.mocked(fetch).mock.calls[0];
|
|
const [putUrl, putInit] = vi.mocked(fetch).mock.calls[1];
|
|
|
|
expect(String(getUrl)).toContain("/api/v1/admin/operations/gift-diamond-ratios?");
|
|
expect(String(getUrl)).toContain("region_id=1001");
|
|
expect(getInit?.method).toBe("GET");
|
|
expect(String(putUrl)).toContain("/api/v1/admin/operations/gift-diamond-ratios");
|
|
expect(putInit?.method).toBe("PUT");
|
|
expect(JSON.parse(String(putInit?.body))).toMatchObject({
|
|
regionId: 1001,
|
|
ratios: { lucky: "40.00", normal: "30.00", super_lucky: "50.00" },
|
|
returnCoinRatios: { lucky: "10.00", normal: "30.00", super_lucky: "1.00" },
|
|
});
|
|
});
|
|
|
|
test("full server notice fanout API uses operations path", async () => {
|
|
vi.stubGlobal(
|
|
"fetch",
|
|
vi.fn(
|
|
async () =>
|
|
new Response(
|
|
JSON.stringify({
|
|
code: 0,
|
|
data: {
|
|
command_id: "admin_notice_test",
|
|
created: true,
|
|
job_id: "mfan_test",
|
|
message_type: "system",
|
|
status: "pending",
|
|
target_scope: "all_active_users",
|
|
},
|
|
}),
|
|
),
|
|
),
|
|
);
|
|
|
|
await createFullServerNoticeFanout({
|
|
action_type: "app_h5",
|
|
action_param: "https://example.com",
|
|
batch_size: 500,
|
|
command_id: "admin_notice_test",
|
|
message_type: "system",
|
|
summary: "今晚 23:00 维护",
|
|
target_scope: "all_active_users",
|
|
title: "维护通知",
|
|
});
|
|
|
|
const [url, init] = vi.mocked(fetch).mock.calls[0];
|
|
|
|
expect(String(url)).toContain("/api/v1/admin/operations/full-server-notices/fanout");
|
|
expect(init?.method).toBe("POST");
|
|
expect(JSON.parse(String(init?.body))).toMatchObject({
|
|
action_param: "https://example.com",
|
|
action_type: "app_h5",
|
|
command_id: "admin_notice_test",
|
|
message_type: "system",
|
|
target_scope: "all_active_users",
|
|
title: "维护通知",
|
|
});
|
|
});
|
|
|
|
test("coin adjustment APIs use generated admin paths", async () => {
|
|
vi.stubGlobal(
|
|
"fetch",
|
|
vi.fn(
|
|
async () => new Response(JSON.stringify({ code: 0, data: { items: [], page: 1, pageSize: 20, total: 0 } })),
|
|
),
|
|
);
|
|
|
|
await listCoinAdjustments({ page: 1, page_size: 20, user_keyword: "1001" });
|
|
await lookupCoinAdjustmentTarget("1001");
|
|
await createCoinAdjustment({
|
|
amount: 500,
|
|
commandId: "coin-adjustment-test",
|
|
reason: "运营发放",
|
|
targetUserId: "1001",
|
|
});
|
|
|
|
const [listUrl, listInit] = vi.mocked(fetch).mock.calls[0];
|
|
const [lookupUrl, lookupInit] = vi.mocked(fetch).mock.calls[1];
|
|
const [createUrl, createInit] = vi.mocked(fetch).mock.calls[2];
|
|
|
|
expect(String(listUrl)).toContain("/api/v1/admin/operations/coin-adjustments?");
|
|
expect(String(listUrl)).toContain("user_keyword=1001");
|
|
expect(listInit?.method).toBe("GET");
|
|
expect(String(lookupUrl)).toContain("/api/v1/admin/operations/coin-adjustments/target?");
|
|
expect(String(lookupUrl)).toContain("user_id=1001");
|
|
expect(lookupInit?.method).toBe("GET");
|
|
expect(String(createUrl)).toContain("/api/v1/admin/operations/coin-adjustments");
|
|
expect(createInit?.method).toBe("POST");
|
|
});
|
|
|
|
test("coin seller ledger API uses generated admin path and filters", async () => {
|
|
vi.stubGlobal(
|
|
"fetch",
|
|
vi.fn(
|
|
async () => new Response(JSON.stringify({ code: 0, data: { items: [], page: 1, pageSize: 20, total: 0 } })),
|
|
),
|
|
);
|
|
|
|
await listCoinSellerLedger({
|
|
ledger_type: "seller_transfer",
|
|
page: 1,
|
|
page_size: 20,
|
|
seller_user_id: "3001",
|
|
});
|
|
|
|
const [listUrl, listInit] = vi.mocked(fetch).mock.calls[0];
|
|
|
|
expect(String(listUrl)).toContain("/api/v1/admin/operations/coin-seller-ledger?");
|
|
expect(String(listUrl)).toContain("seller_user_id=3001");
|
|
expect(String(listUrl)).toContain("ledger_type=seller_transfer");
|
|
expect(listInit?.method).toBe("GET");
|
|
});
|
|
|
|
test("coin seller ledger export API sends current filters without pagination", async () => {
|
|
vi.stubGlobal(
|
|
"fetch",
|
|
vi.fn(async () => new Response("seller,amount\n", { status: 200 })),
|
|
);
|
|
|
|
await exportCoinSellerLedger({
|
|
end_at_ms: "2000",
|
|
ledger_type: "admin_stock_credit",
|
|
seller_keyword: "HUNTER",
|
|
start_at_ms: "1000",
|
|
});
|
|
|
|
const [exportUrl, exportInit] = vi.mocked(fetch).mock.calls[0];
|
|
|
|
expect(String(exportUrl)).toContain("/api/v1/admin/operations/coin-seller-ledger/export?");
|
|
expect(String(exportUrl)).toContain("seller_keyword=HUNTER");
|
|
expect(String(exportUrl)).toContain("ledger_type=admin_stock_credit");
|
|
expect(String(exportUrl)).toContain("start_at_ms=1000");
|
|
expect(String(exportUrl)).toContain("end_at_ms=2000");
|
|
expect(String(exportUrl)).not.toContain("page=");
|
|
expect(exportInit?.method).toBe("GET");
|
|
});
|
|
|
|
test("wheel APIs use activity paths and generated methods", async () => {
|
|
vi.stubGlobal(
|
|
"fetch",
|
|
vi.fn(async () => new Response(JSON.stringify({ code: 0, data: { items: [], page: 1, pageSize: 20, total: 0 } }))),
|
|
);
|
|
|
|
await getWheelConfig("default");
|
|
await updateWheelConfig({
|
|
draw_price_coins: 10000,
|
|
effective_from_ms: 0,
|
|
enabled: true,
|
|
initial_pool_coins: 0,
|
|
max_single_rtp_payout: 0,
|
|
pool_rate_percent: 90,
|
|
pool_reserve_coins: 0,
|
|
settlement_window_draws: 1000,
|
|
target_rtp_percent: 90,
|
|
tiers: [
|
|
{
|
|
display_name: "金币",
|
|
enabled: true,
|
|
metadata_json: "{}",
|
|
probability_percent: 70,
|
|
reward_coins: 10000,
|
|
reward_count: 1,
|
|
reward_id: "",
|
|
reward_type: "coin",
|
|
rtp_value_coins: 10000,
|
|
tier_id: "coin",
|
|
},
|
|
{
|
|
display_name: "礼物",
|
|
enabled: true,
|
|
metadata_json: "{}",
|
|
probability_percent: 20,
|
|
reward_coins: 0,
|
|
reward_count: 1,
|
|
reward_id: "gift_1001",
|
|
reward_type: "gift",
|
|
rtp_value_coins: 5000,
|
|
tier_id: "gift",
|
|
},
|
|
{
|
|
display_name: "装扮",
|
|
enabled: true,
|
|
metadata_json: "{}",
|
|
probability_percent: 10,
|
|
reward_coins: 0,
|
|
reward_count: 1,
|
|
reward_id: "dress_1001",
|
|
reward_type: "dress",
|
|
rtp_value_coins: 0,
|
|
tier_id: "dress",
|
|
},
|
|
],
|
|
wheel_id: "default",
|
|
});
|
|
await listWheelDraws({ page: 1, page_size: 20, status: "granted", user_id: "1001", wheel_id: "default" });
|
|
await getWheelDrawSummary({ status: "granted", user_id: "1001", wheel_id: "default" });
|
|
|
|
const [getUrl, getInit] = vi.mocked(fetch).mock.calls[0];
|
|
const [putUrl, putInit] = vi.mocked(fetch).mock.calls[1];
|
|
const [drawsUrl, drawsInit] = vi.mocked(fetch).mock.calls[2];
|
|
const [summaryUrl, summaryInit] = vi.mocked(fetch).mock.calls[3];
|
|
|
|
expect(String(getUrl)).toContain("/api/v1/admin/activity/wheel/config?");
|
|
expect(String(getUrl)).toContain("wheel_id=default");
|
|
expect(getInit?.method).toBe("GET");
|
|
expect(String(putUrl)).toContain("/api/v1/admin/activity/wheel/config?");
|
|
expect(putInit?.method).toBe("PUT");
|
|
expect(JSON.parse(String(putInit?.body))).toMatchObject({ enabled: true, wheel_id: "default" });
|
|
expect(String(drawsUrl)).toContain("/api/v1/admin/activity/wheel/draws?");
|
|
expect(String(drawsUrl)).toContain("user_id=1001");
|
|
expect(String(drawsUrl)).toContain("status=granted");
|
|
expect(drawsInit?.method).toBe("GET");
|
|
expect(String(summaryUrl)).toContain("/api/v1/admin/activity/wheel/draw-summary?");
|
|
expect(summaryInit?.method).toBe("GET");
|
|
});
|