import { chromium } from 'playwright'; import fs from 'fs'; import path from 'path'; const BASE_URL = 'http://localhost:5174'; const OUTPUT_DIR = './test-results'; if (!fs.existsSync(OUTPUT_DIR)) { fs.mkdirSync(OUTPUT_DIR, { recursive: true }); } const pages = [ { name: 'ShadowRunQueue', url: '/model-ops/shadow-run-jobs', selectors: ['.shadow-run-queue', '.stats', '.filters', '.jobs-list'] }, { name: 'ModelList', url: '/model-ops/models-master', selectors: ['.model-list', '.filters', '.content', '.master-list'] }, { name: 'ApprovalQueue', url: '/governance/approvals', selectors: ['.approval-queue', '.stats', '.filters', '.content'] } ]; async function testPage(browser, pageConfig) { console.log(`\nTesting: ${pageConfig.name}`); const page = await browser.newPage(); const errors = []; page.on('console', msg => { if (msg.type() === 'error') { errors.push(msg.text()); } }); page.on('response', res => { if (res.status() >= 500) { errors.push(`HTTP ${res.status()}: ${res.url()}`); } }); try { const response = await page.goto(`${BASE_URL}${pageConfig.url}`, { waitUntil: 'domcontentloaded', timeout: 15000 }); console.log(` Response: ${response.status()}`); // Wait for rendering await page.waitForTimeout(2000); // Check DOM elements let foundSelectors = 0; for (const selector of pageConfig.selectors) { const element = await page.locator(selector).first(); const visible = await element.isVisible().catch(() => false); if (visible) { foundSelectors++; console.log(` ✅ Found: ${selector}`); } else { console.log(` ❌ Missing: ${selector}`); } } // Screenshot const screenshotPath = path.join(OUTPUT_DIR, `${pageConfig.name}.png`); await page.screenshot({ path: screenshotPath, fullPage: true }); console.log(` 📸 Screenshot: ${screenshotPath}`); // Save HTML const htmlPath = path.join(OUTPUT_DIR, `${pageConfig.name}.html`); const html = await page.content(); fs.writeFileSync(htmlPath, html); console.log(` 🔍 DOM: ${htmlPath}`); const success = errors.length === 0 && foundSelectors >= pageConfig.selectors.length * 0.8; console.log(` Result: ${success ? '✅ PASS' : '❌ FAIL'}`); if (errors.length > 0) { console.log(` Errors: ${errors.join(', ')}`); } await page.close(); return { success, name: pageConfig.name, errors, selectors: foundSelectors }; } catch (err) { console.log(` ❌ Error: ${err.message}`); await page.close(); return { success: false, name: pageConfig.name, errors: [err.message], selectors: 0 }; } } async function main() { console.log('🚀 Playwright Page Tests\n'); const browser = await chromium.launch({ headless: true }); const results = []; for (const pageConfig of pages) { const result = await testPage(browser, pageConfig); results.push(result); } await browser.close(); // Summary console.log('\n' + '='.repeat(50)); console.log('SUMMARY'); console.log('='.repeat(50)); for (const r of results) { console.log(`${r.success ? '✅' : '❌'} ${r.name}`); } const allPassed = results.every(r => r.success); console.log('\n' + (allPassed ? '✅ ALL TESTS PASSED' : '❌ SOME TESTS FAILED')); process.exit(allPassed ? 0 : 1); } main().catch(err => { console.error(err); process.exit(1); });