import { describe, it, expect, vi } from 'vitest'; import type { Page, Locator } from 'playwright'; import { PlaywrightAuthSessionService } from '../../../packages/infrastructure/adapters/automation/auth/PlaywrightAuthSessionService'; import { AuthenticationState } from '../../../packages/domain/value-objects/AuthenticationState'; import { BrowserAuthenticationState } from '../../../packages/domain/value-objects/BrowserAuthenticationState'; import type { ILogger } from '../../../packages/application/ports/ILogger'; import type { Result } from '../../../packages/shared/result/Result'; import type { PlaywrightBrowserSession } from '../../../packages/infrastructure/adapters/automation/core/PlaywrightBrowserSession'; import type { SessionCookieStore } from '../../../packages/infrastructure/adapters/automation/auth/SessionCookieStore'; import type { IPlaywrightAuthFlow } from '../../../packages/infrastructure/adapters/automation/auth/PlaywrightAuthFlow'; describe('PlaywrightAuthSessionService.verifyPageAuthentication', () => { function createService(deps: { pageUrl: string; hasLoginUi: boolean; hasAuthUi: boolean; cookieState: AuthenticationState; }) { const mockLogger: ILogger = { debug: vi.fn(), info: vi.fn(), warn: vi.fn(), error: vi.fn(), }; const mockLocator: Locator = { first: vi.fn().mockReturnThis(), isVisible: vi.fn().mockImplementation(async () => deps.hasLoginUi), } as unknown as Locator; const mockPage: Page = { url: vi.fn().mockReturnValue(deps.pageUrl), locator: vi.fn().mockReturnValue(mockLocator), } as unknown as Page; const mockBrowserSession: PlaywrightBrowserSession = { getPersistentContext: vi.fn().mockReturnValue(null), getContext: vi.fn().mockReturnValue(null), getPage: vi.fn().mockReturnValue(mockPage), } as unknown as PlaywrightBrowserSession; const mockCookieStore: SessionCookieStore = { read: vi.fn().mockResolvedValue({ cookies: [{ name: 'XSESSIONID', value: 'abc', domain: 'members-ng.iracing.com', path: '/', expires: -1 }], origins: [], }), validateCookies: vi.fn().mockReturnValue(deps.cookieState), getSessionExpiry: vi.fn(), write: vi.fn(), delete: vi.fn(), } as unknown as SessionCookieStore; const mockAuthFlow: IPlaywrightAuthFlow = { getLoginUrl: () => 'https://members-ng.iracing.com/login', getPostLoginLandingUrl: () => 'https://members-ng.iracing.com/web/racing/hosted/browse-sessions', isLoginUrl: (url: string) => url.includes('/login'), isAuthenticatedUrl: (url: string) => url.includes('/web/racing/hosted'), isLoginSuccessUrl: (url: string) => url.includes('/web/racing/hosted'), detectAuthenticatedUi: vi.fn().mockResolvedValue(deps.hasAuthUi), detectLoginUi: vi.fn(), navigateToAuthenticatedArea: vi.fn(), waitForPostLoginRedirect: vi.fn(), } as unknown as IPlaywrightAuthFlow; const service = new PlaywrightAuthSessionService( mockBrowserSession, mockCookieStore, mockAuthFlow, mockLogger, ); return { service, mockCookieStore, mockAuthFlow, mockPage }; } it('treats cookies-valid + login UI as EXPIRED (page wins over cookies)', async () => { const { service } = createService({ pageUrl: 'https://members-ng.iracing.com/web/racing/hosted/browse-sessions', hasLoginUi: true, hasAuthUi: false, cookieState: AuthenticationState.AUTHENTICATED, }); const result: Result = await service.verifyPageAuthentication(); expect(result.isOk()).toBe(true); const browserState = result.unwrap(); expect(browserState.getCookieValidity()).toBe(true); expect(browserState.getPageAuthenticationStatus()).toBe(false); expect(browserState.getAuthenticationState()).toBe(AuthenticationState.EXPIRED); expect(browserState.requiresReauthentication()).toBe(true); }); it('treats cookies-valid + authenticated UI without login UI as AUTHENTICATED', async () => { const { service } = createService({ pageUrl: 'https://members-ng.iracing.com/web/racing/hosted/browse-sessions', hasLoginUi: false, hasAuthUi: true, cookieState: AuthenticationState.AUTHENTICATED, }); const result: Result = await service.verifyPageAuthentication(); expect(result.isOk()).toBe(true); const browserState = result.unwrap(); expect(browserState.getCookieValidity()).toBe(true); expect(browserState.getPageAuthenticationStatus()).toBe(true); expect(browserState.getAuthenticationState()).toBe(AuthenticationState.AUTHENTICATED); expect(browserState.requiresReauthentication()).toBe(false); }); });