fix(ui): показывать подтверждённые данные месячного отчёта

This commit is contained in:
Denozordec committed 2026-09-24 01:36:36 +07:00
1 parent 24313340d5
commit 8ac40ba78a
4 files changed
+71 -52

No files matched your search

+28 -1
View File
@@ -8,6 +8,7 @@ async function setup(page: Page) {
await page.route('**/health', r => r.fulfill({ json: { ok: true } }))
await page.route('**/api/**', async route => {
const url = new URL(route.request().url()), path = url.pathname, range = url.searchParams.get('range')
if (path === '/api/traffic/flow/monthly') return route.fulfill({ json: { month: url.searchParams.get('month'), bytes: 1500, countries: [{ id: 'RU', label: 'Россия', bytes: 1500, packets: 1, bps: 0, percent: 100 }], services: [], asns: [] } })
if (path === '/api/traffic/flow/analytics') {
if (control.hold === range) await gate
if (control.fail) return route.fulfill({ status: 500, json: { error: 'Срез временно недоступен' } })
@@ -17,7 +18,7 @@ async function setup(page: Page) {
if (path === '/api/traffic/flow/exporters' && control.failList) return route.fulfill({ status: 403, json: { error: 'Нет доступа к экспортёрам' } })
const json = path === '/api/auth/config' ? { required: false }
: path === '/api/traffic/flow/exporters' ? { exporters: [card] }
: path === '/api/traffic/flow/clients' ? { clients: [] }
: path === '/api/traffic/flow/clients' ? { clients: [{ ...card, id: 'client1', name: 'Клиент тест' }] }
: path === '/api/traffic/flows' ? { exportersOnline: 1, bytesPerMin: 1, uniqueSrc: 1, uniqueDst: 1, topProto: 'TCP', talkers: [], listenerBound: true }
: path === '/api/traffic/servers' ? { servers: [] }
: path.endsWith('/interfaces') || path.endsWith('/bound-interfaces') ? { interfaces: [] }
@@ -75,3 +76,29 @@ test('Flow: завершённый SSE не помечает последние
await expect(page.getByText('Последние данные · live недоступен', { exact: true }).filter({ visible: true })).toHaveCount(2)
await expect(page.getByText('live', { exact: true })).toHaveCount(0)
})
test('Flow: месяц показывает только доступные агрегаты и не применяется к клиенту', async ({ page }) => {
await setup(page)
const monthlyRequest = page.waitForRequest(r => r.url().includes('/flow/monthly?'))
await page.getByRole('button', { name: 'Текущий месяц', exact: true }).click()
const url = new URL((await monthlyRequest).url())
expect(url.searchParams.get('serverId')).toBe('1')
expect(url.searchParams.get('month')).toMatch(/^\d{4}-\d{2}$/)
expect([...url.searchParams.keys()].sort()).toEqual(['month', 'serverId'])
const report = page.getByRole('region', { name: 'Месячный отчёт' })
await expect(report).toContainText('1.5 КБ')
await expect(report.getByRole('columnheader').filter({ hasText: 'Скорость' })).toHaveCount(0)
await expect(page.getByLabel('Скорость потоков')).toHaveCount(0)
await expect(page.getByLabel('Сводка трафика')).toHaveCount(0)
await expect(page.getByRole('switch', { name: 'Без дублей' })).toBeDisabled()
await expect(page.getByRole('switch', { name: 'Без overlay' })).toBeDisabled()
await expect(page.getByRole('switch', { name: 'Без mesh' })).toBeDisabled()
const clientRequest = page.waitForRequest(r => r.url().includes('/flow/analytics?') && r.url().includes('userId=client1'))
await page.getByRole('group', { name: 'Источник потоков' }).getByRole('button', { name: 'Клиенты', exact: true }).click()
expect(new URL((await clientRequest).url()).searchParams.get('range')).toBe('1h')
await expect(page.getByLabel('Скорость потоков')).toBeVisible()
await expect(report).toHaveCount(0)
await expect(page.getByRole('button', { name: 'Текущий месяц', exact: true })).toHaveCount(0)
await expect(page.getByRole('switch', { name: 'Без дублей' })).toBeEnabled()
})