import { fireEvent, render, screen, waitFor } from '@testing-library/react'; import { beforeEach, expect, test, vi } from 'vitest'; import ServicesPage from '@/pages/Services'; import { apiRequest } from '@/services/api'; vi.mock('@/services/api', () => ({ apiRequest: vi.fn(), jsonOptions: vi.fn((method, body) => ({ method, body: JSON.stringify(body) })), })); const emptyPage = { items: [], total: 0, page: 1, page_size: 20 }; beforeEach(() => { vi.mocked(apiRequest).mockImplementation(async (path) => { if (path === '/directory/fulfillment-metrics') { return { counts: {}, valid_requests: 12, quoted_requests: 9, confirmed_requests: 6, request_submission_rate: 1, quote_rate: 0.75, customer_confirmation_rate: 0.6667, match_success_rate: 0.5, fulfillment_rate: 0.8333, cancellation_rate: 0.1, cancellation_distribution: { customer: 1, technician: 0 }, scope_note: '仅统计平台服务单;直接 Telegram 私聊成交不在统计范围。', }; } if (path === '/directory/service-settings') { return { customer_max_open_orders: 3, customer_daily_request_limit: 10, review_qr_expiry_hours: 24, review_forum_chat_id: '-1001234567890', review_forum_username: 'public_reviews', }; } if (path.startsWith('/directory/package-templates')) { return { items: [ { template_id: 'tpl1', version: 2, name: '基础护理模板', status: 'enabled', sort_order: 1, created_at: '2026-07-26T00:00:00Z', updated_at: '2026-07-26T00:00:00Z', package: { package_id: 'pkg1', name: '基础护理', category: '护理', description: '标准服务', tags: ['护理'], service_modes: ['at_store'], price_mode: 'fixed', currency: 'CNY', price_unit: 'per_service', min_price: '100.00', max_price: '100.00', price_display: '100 元/次', duration_minutes: 60, addons: [], travel_fee: { mode: 'quoted', description: '无额外费用' }, }, }, ], total: 1, }; } if (path.startsWith('/directory/service-orders')) return emptyPage; if (path.startsWith('/directory/reviews')) return emptyPage; if (path.startsWith('/directory/review-qrs')) return emptyPage; if (path.startsWith('/directory/leaderboard')) return emptyPage; if (path.startsWith('/directory/customer-blocks')) return emptyPage; if (path.startsWith('/directory/reports')) return emptyPage; if (path === '/directory/review-template') { return { template_id: 'review1', version: 1, status: 'active', published_at: '2026-07-26T00:00:00Z', questions: [ { question_id: 'effect', type: 'single_choice', label: '服务效果', required: true, weight: 100, options: [ { value: 'good', label: '满意', score: 5 }, { value: 'bad', label: '不满意', score: 1 }, ], }, ], }; } throw new Error(`Unexpected request: ${path}`); }); }); test('展示咨询评价说明、公开群设置和服务模板', async () => { render(); expect(screen.getByText('技师咨询与评价')).toBeInTheDocument(); expect(screen.getByText('咨询平台模式')).toBeInTheDocument(); expect(await screen.findByText('12')).toBeInTheDocument(); await waitFor(() => { expect(screen.getByLabelText('公开群 Chat ID')).toHaveValue('-1001234567890'); }); expect(screen.getByText('仅统计平台服务单;直接 Telegram 私聊成交不在统计范围。')).toBeInTheDocument(); fireEvent.click(screen.getByRole('tab', { name: /套餐模板/ })); expect(await screen.findByText('基础护理模板')).toBeInTheDocument(); expect(screen.getByText('护理 · V2')).toBeInTheDocument(); fireEvent.click(screen.getByRole('button', { name: '新建模板' })); expect(await screen.findByLabelText('默认服务价格')).toBeInTheDocument(); expect(screen.getByLabelText('默认额外费用说明')).toBeInTheDocument(); });