Spaces:
Sleeping
Sleeping
File size: 5,284 Bytes
cd99321 | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 | import { describe, it, expect, beforeEach } from 'vitest';
import { render, screen, waitFor } from '../../tests/helpers/render';
import userEvent from '@testing-library/user-event';
import { resetAllStores, seedStore } from '../../tests/helpers/store';
import { buildUser } from '../../tests/helpers/factories';
import { useAuthStore } from '../store/authStore';
import SettingsPage from './SettingsPage';
// Mock heavy settings sub-tabs to focus on page-level concerns
vi.mock('../components/Settings/DisplaySettingsTab', () => ({
default: () => <div data-testid="display-settings-tab">Display Settings</div>,
}));
vi.mock('../components/Settings/MapSettingsTab', () => ({
default: () => <div data-testid="map-settings-tab">Map Settings</div>,
}));
vi.mock('../components/Settings/NotificationsTab', () => ({
default: () => <div data-testid="notifications-tab">Notifications Settings</div>,
}));
vi.mock('../components/Settings/IntegrationsTab', () => ({
default: () => <div data-testid="integrations-tab">Integrations Settings</div>,
}));
vi.mock('../components/Settings/AccountTab', () => ({
default: () => <div data-testid="account-tab">Account Settings</div>,
}));
vi.mock('../components/Settings/AboutTab', () => ({
default: ({ appVersion }: { appVersion: string }) => (
<div data-testid="about-tab">About v{appVersion}</div>
),
}));
beforeEach(() => {
resetAllStores();
seedStore(useAuthStore, { isAuthenticated: true, user: buildUser() });
});
describe('SettingsPage', () => {
describe('FE-PAGE-SETTINGS-001: Settings page renders', () => {
it('shows the Settings heading', () => {
render(<SettingsPage />);
expect(screen.getByRole('heading', { name: /settings/i })).toBeInTheDocument();
});
});
describe('FE-PAGE-SETTINGS-002: Default tab (Display) is active', () => {
it('shows Display tab content by default', async () => {
render(<SettingsPage />);
await waitFor(() => {
expect(screen.getByTestId('display-settings-tab')).toBeInTheDocument();
});
});
});
describe('FE-PAGE-SETTINGS-003: Tab navigation', () => {
it('switching to Map tab shows map settings content', async () => {
const user = userEvent.setup();
render(<SettingsPage />);
await waitFor(() => {
expect(screen.getByRole('button', { name: /map/i })).toBeInTheDocument();
});
await user.click(screen.getByRole('button', { name: /^map$/i }));
await waitFor(() => {
expect(screen.getByTestId('map-settings-tab')).toBeInTheDocument();
});
});
it('switching to Account tab shows account settings', async () => {
const user = userEvent.setup();
render(<SettingsPage />);
await waitFor(() => {
expect(screen.getByRole('button', { name: /account/i })).toBeInTheDocument();
});
await user.click(screen.getByRole('button', { name: /account/i }));
await waitFor(() => {
expect(screen.getByTestId('account-tab')).toBeInTheDocument();
});
});
it('switching to Notifications tab shows notifications content', async () => {
const user = userEvent.setup();
render(<SettingsPage />);
await waitFor(() => {
expect(screen.getByRole('button', { name: /notifications/i })).toBeInTheDocument();
});
await user.click(screen.getByRole('button', { name: /notifications/i }));
await waitFor(() => {
expect(screen.getByTestId('notifications-tab')).toBeInTheDocument();
});
});
});
describe('FE-PAGE-SETTINGS-004: All standard tabs are present', () => {
it('renders Display, Map, Notifications, Account tabs', async () => {
render(<SettingsPage />);
await waitFor(() => {
expect(screen.getByRole('button', { name: /display/i })).toBeInTheDocument();
});
expect(screen.getByRole('button', { name: /^map$/i })).toBeInTheDocument();
expect(screen.getByRole('button', { name: /notifications/i })).toBeInTheDocument();
expect(screen.getByRole('button', { name: /account/i })).toBeInTheDocument();
});
});
describe('FE-PAGE-SETTINGS-005: MFA redirect switches to Account tab', () => {
it('auto-switches to account tab when ?mfa=required is in URL', async () => {
render(<SettingsPage />, { initialEntries: ['/settings?mfa=required'] });
await waitFor(() => {
expect(screen.getByTestId('account-tab')).toBeInTheDocument();
});
});
});
describe('FE-PAGE-SETTINGS-006: About tab shown when version loads', () => {
it('About tab appears when app version is returned by API', async () => {
const { http, HttpResponse } = await import('msw');
const { server } = await import('../../tests/helpers/msw/server');
server.use(
http.get('/api/auth/app-config', () => {
return HttpResponse.json({
has_users: true,
allow_registration: true,
demo_mode: false,
oidc_configured: false,
oidc_only_mode: false,
version: '2.9.10',
});
}),
);
render(<SettingsPage />);
await waitFor(() => {
expect(screen.getByRole('button', { name: /about/i })).toBeInTheDocument();
});
});
});
});
|