// apps/client/test/e2e/ws-kill-reconnect.e2e.test.ts
// [int->REQ-CLI-09] [int->REQ-CLI-04]
//
// Plan 06-15 Task 3 — WS-kill within-grace reconnect regression test.
// UAT Test 5 reproducer: login, force-close the WS socket, wait for SDK
// auto-reconnect within the Phase 4 D-22 grace window (10s), then assert
// GameScene is still ready and chat round-trips.
//
// Assertions use window.__rebno deterministic test hook (D-35, exposed by
// 06-14 Task 3 in dev/test mode only). Room slug asserted as 'mvp-room' per D-30.
// Secondary defect (06-12 §5): InputDispatcher.setRoom() is called on every
// reconnect so movement commands reach the new room object after reauth.

import { test, expect, loginAs, waitForGameReady } from './fixtures.js';

test('WS-kill: login → kill WS → SDK reconnects within grace → canvas still truthy + chat round-trips', async ({
  page,
  accountA,
  inviteSuffix,
}) => {
  // 1. Login and confirm initial game-ready state.
  await loginAs(page, accountA, inviteSuffix);
  await waitForGameReady(page);

  // 2. Force-close the WebSocket connection to trigger the reconnect path.
  //    Tries the Colyseus SDK transport first, falls back to connection.close().
  await page.evaluate(() => {
    const w = window as unknown as {
      __rebno?: {
        room?: {
          connection?: {
            transport?: { ws?: { close?: () => void } };
            close?: () => void;
          };
        };
      };
    };
    const conn = w.__rebno?.room?.connection;
    if (conn?.transport?.ws?.close) {
      conn.transport.ws.close();
    } else if (conn?.close) {
      conn.close();
    }
  });

  // 3. Brief pause to let the disconnect surface (banner may appear).
  await page.waitForTimeout(2_000);

  // 4. Wait for SDK auto-reconnect within the Phase 4 D-22 grace window (12s total).
  //    data-game-ready should still be truthy after reconnect completes.
  await expect(page.locator('canvas[data-game-ready="true"]')).toBeVisible({
    timeout: 12_000,
  });

  // 5. Confirm room ID is still correct via __rebno hook (D-35 + D-30).
  const postReconnectRoomId = await page.evaluate(
    () => (window as unknown as { __rebno?: { roomId?: string } }).__rebno?.roomId,
  );
  expect(postReconnectRoomId).toBe('mvp-room');

  // 6. Chat round-trip post-reconnect — confirms message dispatch goes through
  //    the new room object (InputDispatcher.setRoom fix, 06-12 §5).
  await page.keyboard.press('Enter');
  await page.locator('[data-chat-input]').waitFor({ timeout: 5_000 });
  await page.fill('[data-chat-input]', 'hello-after-reconnect');
  await page.locator('[data-chat-input]').press('Enter');
  await expect(
    page.locator('[data-chat-line]').filter({ hasText: 'hello-after-reconnect' }),
  ).toBeVisible({ timeout: 5_000 });
});
