I've created a widget component that can be embedded on a webapp as a script. It is not embedded in an IFrame therefore lives inside the webapp's window object. This embedded component is responsive and applies different margin classes(tailwind) based on its own resizing, but not on the resizing of the webapp's window itself, hence why I use a hook to make this component responsive and not media queries. The component and hook work how I intend them to work just wondering what the best way of testing this is? Any help appreciated!
import { useContainerWidth } from 'custom-hooks'
function EmbeddedComponent() {
const { targetRef, containerWidth } = useContainerWidth()
return (
<div
data-testid="test-embeddedComponent"
className={clsx(
containerWidth < 640 && 'my-0',
containerWidth >= 640 && containerWidth < 768 && 'my-8',
conatinerWidth >= 768 && containerWidth < 1024 && 'my-16',
containerWidth >= 1024 && 'my-20'
)}
>
<LayoutComponent containerWidth={containerWidth} />
</div>
)
}
function LayoutComponent({ containerWidth }: { containerWidth: number }) {
return (
<div>
<div
className={clsx(
containerWidth < 640 && 'mb-2',
containerWidth >= 640 && containerWidth < 768 && 'mb-7',
conatinerWidth >= 768 && containerWidth < 1024 && 'mb-12',
containerWidth >= 1024 && 'mb-14'
)}
>
<TopComponent/>
</div>
<div>
<BottomComponent/>
</div>
</div>
}
export function useContainerWidth() {
const [containerWidth, setContainerWidth] = React.useState(400)
const targetRef = React.useRef<HTMLDivElement>(null)
React.useEffect(() => {
if (window === undefined) return
getContainerWidth()
window.addEventListener('resize', getContainerWidth)
function getContainerWidth() {
if (targetRef.current) {
setContainerWidth(targetRef.current.offsetWidth)
}
}
return () => {
window.removeEventListener('resize', getContainerWidth)
}
}, [containerWidth])
return {
containerWidth,
targetRef
}
}
This is how far I got with the testing but pretty clueless
it('should apply the right margin classes on resize', () => {
??? How do I test this ???
??? what do I do with targetRef ???
const { result } = renderHook(() => useContainerWidth())
jest.spyOn(window, ???).mockReturnValue(650)
render(<EmbeddedComponent />)
expect(screen.getByTestId('test-embeddedComponent')).toHaveClass('my-8')
??? Can I then set window size to something else like 800 ???
expect(screen.getByTestId('test-embeddedComponent')).toHaveClass('my-16')
}
)
// I've also tried this one
it('should apply the right margins for a window size', async () => {
const { result } = renderHook(() => useContainerWidth())
act(() => {
window.resizeTo(650, 650)
})
await mockDelay(300)
expect(result.current.containerWidth).toBe(650)
expect(screen.getByTestId('test-embeddedComponent')).toHaveClass('my-8')
})