/**
 * USER_JOURNEYS.md §8 — grid-view search & filter chips. Verifies the OR / AND
 * combination rules end-to-end by seeding uploads with known captions/uploaders,
 * activating chips, and counting the resulting grid tiles.
 *
 * (The pure combination logic is also unit-tested in
 * frontend/src/lib/feed-filter.test.ts.)
 */
import { test, expect } from '../../fixtures/test';
import { seedUpload } from '../../helpers/seed';
import type { Page } from '@playwright/test';

/** Grid tiles render as buttons labelled "Upload anzeigen". */
const tiles = (page: Page) => page.getByRole('button', { name: 'Upload anzeigen' });

async function switchToGrid(page: Page) {
  await page.getByRole('button', { name: 'Rasteransicht' }).click();
}

/** Type a query into the grid search box and click the matching suggestion. */
async function addFilter(page: Page, query: string, suggestionName: string | RegExp) {
  const search = page.getByPlaceholder('Nutzer oder #Tag suchen…');
  await search.click();
  await search.fill(query);
  await page.getByRole('button', { name: suggestionName }).click();
}

test.describe('Feed — filter & search', () => {
  test('two hashtag chips combine with OR', async ({ page, guest, signIn }) => {
    const a = await guest('OrUser');
    await seedUpload(a.jwt, { caption: 'pic #wedding' });
    await seedUpload(a.jwt, { caption: 'pic #party' });
    await seedUpload(a.jwt, { caption: 'pic #other' });

    await signIn(page, a); // lands on /feed
    await switchToGrid(page);
    await expect(tiles(page)).toHaveCount(3);

    // One tag → only its card.
    await addFilter(page, '#wedding', /wedding/i);
    await expect(tiles(page)).toHaveCount(1);

    // Adding a second tag widens the result (OR), not narrows it.
    await addFilter(page, '#party', /party/i);
    await expect(tiles(page)).toHaveCount(2);
  });

  test('uploader chip + hashtag chip combines with AND', async ({ page, guest, signIn }) => {
    const alice = await guest('AndAlice');
    const bob = await guest('AndBob');
    await seedUpload(alice.jwt, { caption: 'pic #wedding' }); // Alice + wedding
    await seedUpload(bob.jwt, { caption: 'pic #wedding' }); //   Bob   + wedding
    await seedUpload(alice.jwt, { caption: 'pic #party' }); //   Alice + party

    await signIn(page, alice); // feed is event-wide → sees all three
    await switchToGrid(page);
    await expect(tiles(page)).toHaveCount(3);

    // Filter by uploader → Alice's two uploads.
    await addFilter(page, 'AndAlice', 'AndAlice');
    await expect(tiles(page)).toHaveCount(2);

    // Add a tag → must satisfy BOTH (Alice AND #wedding) → just the one.
    await addFilter(page, '#wedding', /wedding/i);
    await expect(tiles(page)).toHaveCount(1);
  });

  test('feed page renders without crashing for an authed user', async ({ page, guest, signIn }) => {
    const h = await guest('SmokeFeed');
    await signIn(page, h);
    await page.goto('/feed');
    // No items yet — the page should still mount and show the empty state.
    await expect(page.getByRole('link', { name: 'Galerie' })).toBeVisible();
  });
});
