import { MantineProvider } from "@mantine/core"; import { QueryClient, QueryClientProvider } from "@tanstack/react-query"; import { fireEvent, render, screen, waitFor } from "@testing-library/react"; import { HttpResponse, http } from "msw"; import { MemoryRouter, Route, Routes } from "react-router"; import { describe, expect, it, vi } from "vitest"; import type { BrokerageOperation } from "@/entities/broker-operation"; import { server } from "@/test/server"; import { AccountOperationsPage, OperationRow } from "./AccountOperationsPage"; vi.mock("@/features/auth", () => ({ useAuth: () => ({ accessToken: "token" }), })); const operation: BrokerageOperation = { id: "operation-1", occurredAt: "2026-08-14T10:00:00Z", type: "OPERATION_TYPE_BUY", category: "trade", description: "Покупка акций", figi: null, instrumentUid: null, ticker: "SBER", instrumentType: "share", payment: null, quantity: "2", price: { currency: "RUB", value: "100" }, accruedInterest: null, commission: { currency: "RUB", value: "1" }, }; describe("OperationRow", () => { it("marks cashless operations without rendering operation details", () => { render( , ); expect(screen.getByText("Без движения денег")).toBeInTheDocument(); expect( screen.queryByRole("button", { name: "Показать детали" }), ).toBeNull(); expect(screen.queryByText("Цена: 100 ₽")).toBeNull(); expect(screen.queryByText("Количество: 2")).toBeNull(); }); }); describe("AccountOperationsPage", () => { it("resets cursor pagination when filters change", async () => { const searches: string[] = []; server.use( http.get( "*/api/v1/brokerage-accounts/:accountId/operations", ({ request }) => { const url = new URL(request.url); searches.push(url.search); return HttpResponse.json({ accountId: "account-1", items: [operation], nextCursor: url.searchParams.get("cursor") ? null : "next-1", hasNext: !url.searchParams.get("cursor"), observedAt: "2026-08-14T00:00:00Z", }); }, ), ); render( } /> , ); fireEvent.click(await screen.findByRole("button", { name: "Далее" })); await waitFor(() => expect(searches.at(-1)).toContain("cursor=next-1")); fireEvent.click(screen.getByRole("checkbox", { name: "Налог" })); await waitFor(() => expect(searches.at(-1)).toContain("categories=tax")); expect(searches.at(-1)).not.toContain("cursor="); }); it("renders an error state", async () => { server.use( http.get("*/api/v1/brokerage-accounts/:accountId/operations", () => HttpResponse.json({ code: "TBANK_UNAVAILABLE" }, { status: 503 }), ), ); render( } /> , ); expect( await screen.findByText("Не удалось загрузить журнал"), ).toBeInTheDocument(); }); });