Files
SkinbaseNova/tests/cpad/dashboard.spec.ts
2026-03-12 07:22:38 +01:00

123 lines
3.9 KiB
TypeScript

/**
* Dashboard tests for the cPad Control Panel.
*
* Uses the pre-saved authenticated session (tests/.auth/admin.json) so no
* explicit login is required in each test.
*
* Coverage:
* • Dashboard page loads (HTTP 200, not a Laravel error page)
* • Page title is not empty
* • No JavaScript console errors
* • No HTTP 5xx responses
* • Key dashboard elements are visible (sidebar, main content area)
* • Dashboard setup page loads
*
* Run:
* npx playwright test tests/cpad/dashboard.spec.ts --project=cpad
*/
import { test, expect } from '@playwright/test';
import { DASHBOARD_PATH, CP_PATH, attachErrorListeners } from '../helpers/auth';
test.describe('cPad Dashboard', () => {
test('dashboard page loads without errors', async ({ page }) => {
const { consoleErrors, networkErrors } = attachErrorListeners(page);
await page.goto(DASHBOARD_PATH);
await page.waitForLoadState('networkidle');
// Must not be redirected to login
expect(page.url(), 'Should not redirect to login').not.toContain('/login');
// Title check
const title = await page.title();
expect(title.length, 'Page must have a non-empty title').toBeGreaterThan(0);
// Body must be visible
await expect(page.locator('body')).toBeVisible();
// No server error page
const bodyText = await page.locator('body').textContent() ?? '';
expect(/Whoops|Server Error|5[0-9]{2}/.test(bodyText), 'Server error detected in body').toBe(false);
// No JS exceptions
expect(consoleErrors.length, `Console errors: ${consoleErrors.join(' | ')}`).toBe(0);
expect(networkErrors.length, `HTTP 5xx: ${networkErrors.join(' | ')}`).toBe(0);
});
test('dashboard root redirect works', async ({ page }) => {
const { networkErrors } = attachErrorListeners(page);
// /cp redirects to /cp/dashboard
await page.goto(CP_PATH);
await page.waitForLoadState('networkidle');
expect(page.url(), 'Should not be on login page').not.toContain('/login');
expect(networkErrors.length, `HTTP 5xx: ${networkErrors.join(' | ')}`).toBe(0);
});
test('dashboard has visible sidebar or navigation', async ({ page }) => {
await page.goto(DASHBOARD_PATH);
await page.waitForLoadState('networkidle');
// Check for a nav/sidebar element — any of these common AdminLTE/Bootstrap selectors
const navSelectors = [
'nav',
'.sidebar',
'#sidebar',
'.main-sidebar',
'#main-sidebar',
'[data-testid="sidebar"]',
'.navbar',
];
let foundNav = false;
for (const sel of navSelectors) {
const count = await page.locator(sel).count();
if (count > 0) {
foundNav = true;
break;
}
}
expect(foundNav, 'Dashboard should contain a sidebar or navigation element').toBe(true);
});
test('dashboard main content area is visible', async ({ page }) => {
await page.goto(DASHBOARD_PATH);
await page.waitForLoadState('networkidle');
// Any of these indicate a main content wrapper is rendered
const contentSelectors = [
'main',
'#content',
'.content-wrapper',
'.main-content',
'[data-testid="main-content"]',
'.wrapper',
];
let foundContent = false;
for (const sel of contentSelectors) {
const count = await page.locator(sel).count();
if (count > 0) {
foundContent = true;
break;
}
}
expect(foundContent, 'Dashboard main content area should be present').toBe(true);
});
test('dashboard setup page loads', async ({ page }) => {
const { consoleErrors, networkErrors } = attachErrorListeners(page);
await page.goto(CP_PATH + '/dashboard/setup');
await page.waitForLoadState('networkidle');
expect(page.url()).not.toContain('/login');
expect(consoleErrors.length, `Console errors: ${consoleErrors.join(' | ')}`).toBe(0);
expect(networkErrors.length, `Network errors: ${networkErrors.join(' | ')}`).toBe(0);
});
});