import { test, expect } from '@playwright/test';

test.beforeEach(async ({ page }) => {
  await page.goto('/');
  await page.evaluate(async () => {
    indexedDB.deleteDatabase('ttrpg-manager');
    localStorage.clear();
  });
  await page.reload();
});

test('encounter tip suggests and applies a deterministic balance fix', async ({ page }) => {
  // Sample campaign: 2 level-3 PCs + a "Goblin Ambush" with 3 goblins.
  await page.getByLabel('Settings').click();
  await page.getByRole('button', { name: 'Load sample campaign' }).click();
  await expect(page.getByRole('heading', { name: 'Sample: Lost Mine' })).toBeVisible();

  // Open the seeded encounter in the combat tracker.
  await page.getByLabel('Primary').getByRole('link', { name: 'Combat' }).click();
  await page.getByText('Goblin Ambush').click();

  // The contextual balance tip is present (LLM off → deterministic path).
  const tip = page.getByTestId('encounter-tip');
  await expect(tip).toBeVisible();

  // Each combatant row has a "Dmg" button — use it to count combatants.
  const hpControls = page.getByRole('button', { name: 'Dmg' });
  const before = await hpControls.count();

  await tip.getByRole('button', { name: 'Suggest a fix' }).click();
  await expect(tip.getByRole('button', { name: 'Add to encounter' })).toBeVisible();
  await tip.getByRole('button', { name: 'Add to encounter' }).click();

  // Suggestion closes and at least one combatant was added.
  await expect(tip.getByRole('button', { name: 'Add to encounter' })).toBeHidden();
  await expect.poll(async () => hpControls.count()).toBeGreaterThan(before);
});

test('encounter tip uses the AI path when a provider is configured', async ({ page }) => {
  // Stub the Anthropic endpoint with a canned structured response.
  await page.route('**/v1/messages', async (route) => {
    await route.fulfill({
      status: 200,
      contentType: 'application/json',
      body: JSON.stringify({
        content: [{ type: 'text', text: JSON.stringify({
          reasoning: 'An ettin raises the threat to match the party.',
          add: [{ name: 'Ettin', count: 1 }],
          targetDifficulty: 'Hard',
        }) }],
      }),
    });
  });

  await page.getByLabel('Settings').click();
  await page.getByRole('button', { name: 'Load sample campaign' }).click();
  await expect(page.getByRole('heading', { name: 'Sample: Lost Mine' })).toBeVisible();

  // Enable the assistant with a dummy key (network is stubbed).
  await page.getByLabel('Settings').click();
  await page.getByLabel('Enable AI assistant').check();
  await page.getByLabel('API key', { exact: true }).fill('sk-stub');

  await page.getByLabel('Primary').getByRole('link', { name: 'Combat' }).click();
  await page.getByText('Goblin Ambush').click();

  const tip = page.getByTestId('encounter-tip');
  await tip.getByRole('button', { name: 'Suggest a fix (AI)' }).click();
  // The canned AI reasoning + the "AI suggestion" label render.
  await expect(tip.getByText('AI suggestion')).toBeVisible();
  await expect(tip.getByText('An ettin raises the threat to match the party.')).toBeVisible();
  await expect(tip.getByText('1× Ettin')).toBeVisible();
});
