import { beforeEach, describe, expect, it, vi } from 'vitest' import { overseasHttp } from '@/shared/api/overseasHttp' import { changeExchangeRateStatus, changeQuoteStatus, changeVehicleStatus, createExchangeRate, createQuote, createVehicle, exportExchangeRates, exportQuotes, exportVehicles, getExchangeRate, getExchangeRateSummary, getQuote, getVehicle, listExchangeRates, listQuotes, listQuoteWarehouseOptions, listVehicles, updateExchangeRate, updateQuote, updateVehicle, } from './overseasMasterData' vi.mock('@/shared/api/overseasHttp', () => ({ overseasHttp: { get: vi.fn(), post: vi.fn(), put: vi.fn(), patch: vi.fn() } })) const ok = (data: unknown) => ({ code: '200', message: 'success', data }) beforeEach(() => vi.clearAllMocks()) describe('overseas master data API', () => { it('uses the overseas quote contract including server-owned partner options', async () => { vi.mocked(overseasHttp.get).mockResolvedValue(ok({ records: [], page: '1', size: '20', total: '0', pages: '0' })) await listQuotes({ page: 1, size: 20, keyword: 'V1' }) expect(overseasHttp.get).toHaveBeenCalledWith('/platform/v1/last-leg/master-data/overseas-quotes', { params: { page: 1, size: 20, keyword: 'V1' } }) vi.mocked(overseasHttp.get).mockResolvedValue(ok([])); await listQuoteWarehouseOptions() expect(overseasHttp.get).toHaveBeenLastCalledWith('/platform/v1/last-leg/master-data/overseas-quotes/warehouse-options') vi.mocked(overseasHttp.get).mockResolvedValue(ok({ summary: { id: '9223372036854775807' }, warehouseFees: [], transitPrices: [] })); await getQuote('9223372036854775807') expect(overseasHttp.get).toHaveBeenLastCalledWith('/platform/v1/last-leg/master-data/overseas-quotes/9223372036854775807') const payload = { name: '报价', warehouseId: '9', providerName: '服务商', currency: 'USD' as const, effectiveStart: '2026-08-01', effectiveEnd: '2026-12-31', versionCode: 'V1', warehouseFees: [], transitPrices: [], remark: null } vi.mocked(overseasHttp.post).mockResolvedValue(ok({})); await createQuote(payload) vi.mocked(overseasHttp.put).mockResolvedValue(ok({})); await updateQuote('9', { ...payload, recordVersion: 2 }) vi.mocked(overseasHttp.patch).mockResolvedValue(ok({})); await changeQuoteStatus('9', 'INACTIVE', 2) expect(overseasHttp.patch).toHaveBeenCalledWith('/platform/v1/last-leg/master-data/overseas-quotes/9/status', { status: 'INACTIVE', recordVersion: 2 }) }) it('uses the monthly exchange-rate contract', async () => { vi.mocked(overseasHttp.get).mockResolvedValue(ok({ records: [], page: 1, size: 20, total: 0, pages: 0 })); await listExchangeRates({ page: 1, size: 20, monthFrom: '2026-08', monthTo: '2026-08' }) vi.mocked(overseasHttp.get).mockResolvedValue(ok({ latestMonth: '2026-08' })); await getExchangeRateSummary() vi.mocked(overseasHttp.get).mockResolvedValue(ok({ month: '2026-08' })); await getExchangeRate('2026-08') vi.mocked(overseasHttp.post).mockResolvedValue(ok({})); await createExchangeRate({ month: '2026-08', usdToCnyAverage: 7.18, remark: null }) vi.mocked(overseasHttp.put).mockResolvedValue(ok({})); await updateExchangeRate('2026-08', { recordVersion: 1, usdToCnyAverage: 7.19, remark: null }) vi.mocked(overseasHttp.patch).mockResolvedValue(ok({})); await changeExchangeRateStatus('2026-08', 'INACTIVE', 1, '停用') expect(overseasHttp.patch).toHaveBeenLastCalledWith('/platform/v1/last-leg/master-data/exchange-rates/2026-08/status', { status: 'INACTIVE', recordVersion: 1, remark: '停用' }) }) it('uses the vehicle contract and preserves string IDs', async () => { vi.mocked(overseasHttp.get).mockResolvedValue(ok({ records: [], page: 1, size: 20, total: 0, pages: 0 })); await listVehicles({ page: 1, size: 20, ownership: 'OWNED' }) vi.mocked(overseasHttp.get).mockResolvedValue(ok({ id: '9223372036854775807' })); await getVehicle('9223372036854775807') expect(overseasHttp.get).toHaveBeenLastCalledWith('/platform/v1/last-leg/master-data/vehicles/9223372036854775807') const payload = { plateNumber: 'CA-01', model: 'Truck', fuelConsumptionPer100Km: 12, mileageKm: 1, driverOrDispatchCompany: null, phone: null, region: 'OVERSEAS' as const, ownership: 'OWNED' as const, remark: null, status: 'IN_SERVICE' as const } vi.mocked(overseasHttp.post).mockResolvedValue(ok({})); await createVehicle(payload) vi.mocked(overseasHttp.put).mockResolvedValue(ok({})); await updateVehicle('9', { ...payload, recordVersion: 1 }) vi.mocked(overseasHttp.patch).mockResolvedValue(ok({})); await changeVehicleStatus('9', 'INACTIVE', 1) expect(overseasHttp.patch).toHaveBeenLastCalledWith('/platform/v1/last-leg/master-data/vehicles/9/status', { status: 'INACTIVE', recordVersion: 1 }) }) it('downloads each CSV through overseasHttp', async () => { const blob = new Blob(['csv']); vi.mocked(overseasHttp.get).mockResolvedValue(blob) await exportQuotes({ status: 'ACTIVE' }); await exportExchangeRates({}); await exportVehicles({ ownership: 'OWNED' }) expect(overseasHttp.get).toHaveBeenNthCalledWith(1, '/platform/v1/last-leg/master-data/overseas-quotes/export', { params: { status: 'ACTIVE' }, responseType: 'blob' }) expect(overseasHttp.get).toHaveBeenNthCalledWith(2, '/platform/v1/last-leg/master-data/exchange-rates/export', { params: {}, responseType: 'blob' }) expect(overseasHttp.get).toHaveBeenNthCalledWith(3, '/platform/v1/last-leg/master-data/vehicles/export', { params: { ownership: 'OWNED' }, responseType: 'blob' }) }) })