import { describe, it, expect, beforeEach, afterEach, vi } from 'vitest' import { __resetSharedResizeObserver, observeResize, } from './shared-resize-observer' // Track every ResizeObserver instance created in the test run so we can // assert on construction / disconnect lifecycle. The shared module is a // singleton — between tests we reset both its state and the mock. const instances: { observe: ReturnType unobserve: ReturnType disconnect: ReturnType }[] = [] class MockResizeObserver { observe = vi.fn() unobserve = vi.fn() disconnect = vi.fn() constructor() { instances.push(this) } } beforeEach(() => { __resetSharedResizeObserver() instances.length = 0 vi.stubGlobal('ResizeObserver', MockResizeObserver) }) afterEach(() => { __resetSharedResizeObserver() vi.unstubAllGlobals() }) describe('observeResize', () => { it('lazily creates a single observer for the first subscriber', () => { const el = document.createElement('div') observeResize(el, () => undefined) expect(instances).toHaveLength(1) expect(instances[0]?.observe).toHaveBeenCalledWith(el) }) it('reuses the singleton observer for additional subscribers', () => { const a = document.createElement('div') const b = document.createElement('div') observeResize(a, () => undefined) observeResize(b, () => undefined) expect(instances).toHaveLength(1) expect(instances[0]?.observe).toHaveBeenCalledTimes(2) }) it('unobserves on unsubscribe but keeps the observer while other subscribers remain', () => { const a = document.createElement('div') const b = document.createElement('div') const stopA = observeResize(a, () => undefined) observeResize(b, () => undefined) stopA() expect(instances[0]?.unobserve).toHaveBeenCalledWith(a) expect(instances[0]?.disconnect).not.toHaveBeenCalled() }) it('disconnects the observer once the last subscriber leaves', () => { const a = document.createElement('div') const stop = observeResize(a, () => undefined) stop() expect(instances[0]?.disconnect).toHaveBeenCalledTimes(1) }) it('returns a no-op cleanup when ResizeObserver is unavailable', () => { vi.stubGlobal('ResizeObserver', undefined) const el = document.createElement('div') const cb = vi.fn() const stop = observeResize(el, cb) // No constructor calls — no instances tracked. expect(instances).toHaveLength(0) // Cleanup is safe to call. expect(() => stop()).not.toThrow() }) it('re-instantiates the observer when a new subscriber arrives after disconnect', () => { const a = document.createElement('div') const b = document.createElement('div') observeResize(a, () => undefined)() expect(instances).toHaveLength(1) expect(instances[0]?.disconnect).toHaveBeenCalledTimes(1) observeResize(b, () => undefined) expect(instances).toHaveLength(2) expect(instances[1]?.observe).toHaveBeenCalledWith(b) }) })