/**
 * Sprint UI-deep, пункт 14: mobile viewport 375x667 smoke.
 * Проходим базовые шаги (signup→nav→ products page) на iPhone-size,
 * проверяем что:
 *  - Sidebar схлопывается, есть гамбургер
 *  - Drawer открывается и закрывается
 *  - Таблицы не вылазят горизонтально
 *  - Формы (товар create) помещаются
 *  - ConfirmDialog читается
 */
import { test, expect, devices } from '@playwright/test'
import { apiSignup, attachSession, watchPage, expectNoErrors } from '../lib/ui.js'

const mobileViewport = { width: 375, height: 667 }

test.describe('UI-14 mobile viewport 375x667', () => {
  test.describe.configure({ mode: 'serial' })
  test.use({ viewport: mobileViewport })

  test('14.1 dashboard на mobile: sidebar схлопнут, гамбургер виден', async ({ page }) => {
    const sess = await apiSignup('mob141')
    const errs = watchPage(page)
    await attachSession(page, sess, '/dashboard')
    await page.waitForLoadState('networkidle')

    // Гамбургер «Открыть меню»
    const burger = page.getByRole('button', { name: /открыть меню|menu/i }).first()
    await expect(burger).toBeVisible({ timeout: 5_000 })

    // Sidebar (aside) на mobile должен быть hidden (md:flex)
    const sidebar = page.locator('aside.hidden').first()
    // Любая aside в скрытом состоянии — допустимо
    const hasHiddenAside = await sidebar.count() > 0
    expect(hasHiddenAside, 'на mobile desktop-sidebar должен быть hidden').toBeTruthy()

    expectNoErrors(errs, 'mobile dashboard')
  })

  test('14.2 drawer открывается и закрывается', async ({ page }) => {
    const sess = await apiSignup('mob142')
    const errs = watchPage(page)
    await attachSession(page, sess, '/dashboard')
    await page.waitForLoadState('networkidle')

    await page.getByRole('button', { name: /открыть меню|menu/i }).first().click()
    // Drawer теперь виден (role dialog)
    const drawer = page.locator('[role="dialog"][aria-modal="true"]').first()
    await expect(drawer).toBeVisible({ timeout: 5_000 })
    // Внутри — nav-ссылка «Товары»
    await expect(drawer.getByRole('link', { name: 'Товары' }).first()).toBeVisible()

    // Закрыть кнопкой X
    await drawer.getByRole('button', { name: /закрыть/i }).first().click()
    await expect(drawer).not.toBeVisible({ timeout: 3_000 })

    expectNoErrors(errs, 'mobile drawer')
  })

  test('14.3 products list на mobile: таблица не вылазит за экран', async ({ page }) => {
    const sess = await apiSignup('mob143')
    const errs = watchPage(page)
    await attachSession(page, sess, '/catalog/products')
    await page.waitForLoadState('networkidle')

    // Главное: body не должен горизонтально скроллиться больше viewport
    const scrollWidth = await page.evaluate(() => document.documentElement.scrollWidth)
    expect(scrollWidth, 'horizontal overflow на mobile').toBeLessThanOrEqual(mobileViewport.width + 2)

    expectNoErrors(errs, 'mobile products list')
  })

  test('14.4 create product форма помещается, поля видимы', async ({ page }) => {
    const sess = await apiSignup('mob144')
    const errs = watchPage(page)
    await attachSession(page, sess, '/catalog/products/new')
    await page.waitForLoadState('networkidle')

    // Название должно быть доступно для заполнения
    const nameInput = page.getByLabel('Название *')
    await expect(nameInput).toBeVisible({ timeout: 5_000 })
    await nameInput.fill('Mobile Product')
    // Розничная цена
    await page.getByLabel(/розничная/i).first().fill('500')

    // Кнопка Сохранить enabled — visible
    const saveBtn = page.locator('button[type="submit"]').last()
    await expect(saveBtn).toBeEnabled({ timeout: 5_000 })

    // Сравним: вся форма влезает (нет жуткого horizontal overflow)
    const scrollWidth = await page.evaluate(() => document.documentElement.scrollWidth)
    expect(scrollWidth).toBeLessThanOrEqual(mobileViewport.width + 2)

    expectNoErrors(errs, 'mobile create product')
  })

  test('14.5 ConfirmDialog на mobile рендерится корректно', async ({ page }) => {
    const sess = await apiSignup('mob145')
    const errs = watchPage(page)
    // Создадим товар через API → откроем edit → нажмём Удалить
    const { request } = await import('@playwright/test')
    const ctx = await request.newContext({
      baseURL: process.env.E2E_ADMIN_URL ?? 'https://test.admin.food-market.kz',
      ignoreHTTPSErrors: true,
      extraHTTPHeaders: { Authorization: `Bearer ${sess.accessToken}` },
    })
    type Paged<T> = { items: T[] }
    const units = await (await ctx.get('/api/catalog/units-of-measure?pageSize=200')).json() as Paged<{ id: string; code: string }>
    const groups = await (await ctx.get('/api/catalog/product-groups')).json() as Paged<{ id: string }>
    const pts = await (await ctx.get('/api/catalog/price-types')).json() as Paged<{ id: string; isRetail: boolean }>
    const curs = await (await ctx.get('/api/catalog/currencies')).json() as Paged<{ id: string; code: string }>
    const r = await ctx.post('/api/catalog/products', {
      data: {
        name: 'MobileDel', article: `MOB-${Date.now()}`,
        unitOfMeasureId: units.items.find(u => u.code === '796')!.id,
        vat: 12, vatEnabled: true,
        productGroupId: groups.items[0].id, packaging: 1,
        prices: [{ priceTypeId: pts.items.find(p => p.isRetail)!.id, amount: 100, currencyId: curs.items.find(c => c.code === 'KZT')!.id }],
        barcodes: [{ code: '1200000000017', type: 1, isPrimary: true }],
      },
    })
    const prod = await r.json() as { id: string }
    await ctx.dispose()

    await attachSession(page, sess, `/catalog/products/${prod.id}`)
    await page.waitForLoadState('networkidle')
    await page.getByRole('button', { name: /удалить/i }).first().click()
    const dialog = page.locator('[aria-labelledby="confirm-dialog-title"]').first()
    await expect(dialog).toBeVisible({ timeout: 5_000 })
    // На мобиле диалог должен помещаться
    const dialogBox = await dialog.boundingBox()
    expect(dialogBox?.width).toBeLessThanOrEqual(mobileViewport.width)

    expectNoErrors(errs, 'mobile confirm dialog')
  })
})
