// @vitest-environment jsdom import { act } from 'react'; import { createRoot } from 'react-dom/client'; import { afterEach, expect, it, vi } from 'vitest'; import { DashboardOverallRing, DashboardPostureConnectors } from '../../src/features/dashboard/DashboardPanel'; afterEach(() => { vi.restoreAllMocks(); vi.unstubAllGlobals(); }); it('retains the ring-to-domain fan after resize, domain changes and unmount', () => { vi.stubGlobal('IS_REACT_ACT_ENVIRONMENT', true); let width = 1000; let resized: () => void = () => {}; const disconnect = vi.fn(); vi.stubGlobal('ResizeObserver', class { constructor(callback: () => void) { resized = callback; } observe = vi.fn(); disconnect = disconnect; }); const rect = (x: number, y: number, w: number, h: number) => ({ x, y, left: x, top: y, right: x + w, bottom: y + h, width: w, height: h, toJSON() {} }); vi.spyOn(Element.prototype, 'getBoundingClientRect').mockImplementation(function (this: Element) { if (this.matches('.client-posture')) return rect(20, 30, width, 600); if (this.matches('.client-overall-ring')) return rect(60, 80, 280, 280); if (this.matches('.client-domain-score')) return rect(width - 200, 70 + Number(this.getAttribute('data-index')) * 70, 46, 46); return rect(0, 0, 0, 0); }); const container = document.createElement('div'); const root = createRoot(container); const render = (count: number) => act(() => root.render(
{Array.from({ length: count }, (_, index) => {index})}
)); try { render(8); const paths = () => [...container.querySelectorAll('.client-posture-connectors path')].map(path => path.getAttribute('d')); expect(paths()).toHaveLength(8); expect(paths()[0]).toBe('M320.0 169.0 C527.0 169.0, 573.0 63.0, 780.0 63.0'); expect(paths()[7]).toMatch(/780\.0 553\.0$/); width = 1200; act(() => window.dispatchEvent(new Event('resize'))); expect(paths()[0]).toMatch(/980\.0 63\.0$/); width = 950; act(() => resized()); expect(paths()[0]).toMatch(/730\.0 63\.0$/); render(3); expect(paths()).toHaveLength(3); expect(paths()[0]).toMatch(/^M320\.0 184\.0/); expect(container.querySelector('.client-overall-ring')?.getAttribute('aria-label')).toBe('Overall Score: 37'); } finally { act(() => root.unmount()); } expect(disconnect).toHaveBeenCalled(); }); it('makes the Overall Score an accessible Work remediation entry point', () => { vi.stubGlobal('IS_REACT_ACT_ENVIRONMENT', true); const onClick = vi.fn(); const container = document.createElement('div'); const root = createRoot(container); try { act(() => root.render()); const ring = container.querySelector('button.client-overall-ring')!; expect(ring.getAttribute('aria-label')).toBe('Open remediation overview in Work. Overall Score: 37'); expect(ring.textContent).toBe('37/100ASSESSOR'); expect(ring.querySelector('.client-overall-ring-title')).toBeNull(); act(() => ring.click()); expect(onClick).toHaveBeenCalledOnce(); } finally { act(() => root.unmount()); } });