import { test, expect, type Page } from '@playwright/test'; import { seedAuthenticatedSession } from '../helpers/session'; async function openRowAction(page: Page, id: string, label: RegExp) { await page.getByTestId(`row-actions-${id}`).click(); await page.getByRole('menuitem', { name: label }).click(); } /** Radix Select in edit dialogs — ensure option chosen so Save enables. */ async function pickDialogOption(page: Page, dialogTestId: string, comboboxIndex: number, option: string) { const dialog = page.getByTestId(dialogTestId); await dialog.getByRole('combobox').nth(comboboxIndex).click(); await page.getByRole('option', { name: option, exact: true }).click(); } test.describe('content explore (mock)', () => { test.beforeEach(async ({ page }) => { await seedAuthenticatedSession(page); }); test('users: список, поиск, detail, edit, delete', async ({ page }) => { await page.goto('/users'); await expect(page.getByTestId('page-users')).toBeVisible(); await page.getByTestId('view-rows').click(); await expect(page.getByTestId('row-user-e2e-1')).toBeVisible(); await page.getByTestId('filter-users-search-input').fill('Alice'); await page.getByTestId('filter-users-search').locator('button[type="submit"]').click(); await expect(page.getByTestId('row-user-e2e-1')).toBeVisible(); await openRowAction(page, 'user-e2e-1', /редакт|edit/i); await expect(page.getByTestId('dialog-edit-user')).toBeVisible(); await page.getByLabel(/ник|nickname/i).fill('Alice E2E'); await pickDialogOption(page, 'dialog-edit-user', 0, 'user'); await pickDialogOption(page, 'dialog-edit-user', 1, 'active'); await expect(page.getByTestId('btn-save')).toBeEnabled(); await page.getByTestId('btn-save').click(); await expect(page.getByTestId('dialog-edit-user')).toHaveCount(0); await page.goto('/users/user-e2e-1'); await expect(page.getByTestId('page-user-detail')).toBeVisible(); await page.goto('/users'); await page.getByTestId('view-rows').click(); await openRowAction(page, 'user-e2e-2', /удал|delete/i); await expect(page.getByTestId('dialog-delete-user')).toBeVisible(); await page.getByTestId('btn-delete-confirm').click(); await expect(page.getByTestId('row-user-e2e-2')).toHaveCount(0); }); test('calendars: edit и detail', async ({ page }) => { await page.goto('/calendars'); await page.getByTestId('view-rows').click(); await expect(page.getByTestId('row-cal-e2e-1')).toBeVisible(); await openRowAction(page, 'cal-e2e-1', /редакт|edit/i); await expect(page.getByTestId('dialog-edit-calendar')).toBeVisible(); await page.getByTestId('dialog-edit-calendar').locator('input').first().fill('E2E Calendar'); await pickDialogOption(page, 'dialog-edit-calendar', 0, 'personal'); await pickDialogOption(page, 'dialog-edit-calendar', 1, 'active'); await expect(page.getByTestId('btn-save')).toBeEnabled(); await page.getByTestId('btn-save').click(); await expect(page.getByTestId('dialog-edit-calendar')).toHaveCount(0); await page.goto('/calendars/cal-e2e-1'); await expect(page.getByTestId('page-calendar-detail')).toBeVisible(); }); test('events: edit и detail', async ({ page }) => { await page.goto('/events'); await page.getByTestId('view-rows').click(); await expect(page.getByTestId('row-evt-e2e-1')).toBeVisible(); await openRowAction(page, 'evt-e2e-1', /редакт|edit/i); await expect(page.getByTestId('dialog-edit-event')).toBeVisible(); await page.getByTestId('dialog-edit-event').locator('input').first().fill('E2E Workout'); await pickDialogOption(page, 'dialog-edit-event', 0, 'single'); await pickDialogOption(page, 'dialog-edit-event', 1, 'active'); await expect(page.getByTestId('btn-save')).toBeEnabled(); // Tall dialog: footer can sit outside viewport; submit via form API. await page.getByTestId('dialog-edit-event').locator('form').evaluate((form) => { (form as HTMLFormElement).requestSubmit(); }); await expect(page.getByTestId('dialog-edit-event')).toHaveCount(0); await page.goto('/events/evt-e2e-1'); await expect(page.getByTestId('page-event-detail')).toBeVisible(); }); test('subscriptions: edit и delete', async ({ page }) => { await page.goto('/subscriptions'); await page.getByTestId('view-rows').click(); await expect(page.getByTestId('row-sub-e2e-1')).toBeVisible(); await openRowAction(page, 'sub-e2e-1', /редакт|edit/i); await expect(page.getByTestId('dialog-edit-subscription')).toBeVisible(); await pickDialogOption(page, 'dialog-edit-subscription', 0, 'monthly'); await pickDialogOption(page, 'dialog-edit-subscription', 1, 'active'); await page.getByTestId('btn-save').click(); await expect(page.getByTestId('dialog-edit-subscription')).toHaveCount(0); await openRowAction(page, 'sub-e2e-1', /удал|delete/i); await expect(page.getByTestId('dialog-delete-subscription')).toBeVisible(); await page.getByTestId('btn-delete-confirm').click(); await expect(page.getByTestId('row-sub-e2e-1')).toHaveCount(0); }); test('banned-words: список и add', async ({ page }) => { await page.goto('/banned-words'); await expect(page.getByTestId('page-banned-words')).toBeVisible(); await expect(page.getByTestId('row-spamword')).toBeVisible(); await page.getByTestId('input-banned-word').fill('newbad'); await page.getByTestId('btn-add-banned-word').click(); await expect(page.getByTestId('row-newbad')).toBeVisible(); }); });