import { h, render, mount, nextTick, type WDom } from 'lithent';
import { unwrapChildren } from '@/utils/children';
// Render props 패턴 - DataProvider
const DataProvider = mount((renew, _props, children: WDom[]) => {
let count = 0;
return () => {
const candidate = unwrapChildren(children) as unknown;
// 함수인지 확인하고 호출
if (typeof candidate === 'function') {
const renderChild = candidate as (data: {
count: number;
increment: () => void;
}) => WDom;
const data = {
count,
increment: () => {
count++;
renew();
},
};
return renderChild(data);
}
return
{candidate ?? children}
;
};
});
// 테스트 컴포넌트
const TestRenderProps = mount(() => {
return () => (
{(data: any) => (
Count: {data.count}
)}
);
});
const testWrap = document.getElementById('root');
if (testWrap) {
render(, testWrap);
}
if (import.meta.vitest) {
const { it, expect, describe } = import.meta.vitest;
describe('Render props pattern', () => {
it('Should support function as children (render props)', async () => {
const container = document.createElement('div');
render(, container);
await nextTick();
const countSpan = container.querySelector('.count');
const incrementBtn = container.querySelector(
'.increment-btn'
) as HTMLButtonElement;
expect(countSpan?.textContent).toContain('Count: 0');
incrementBtn?.click();
await nextTick();
expect(countSpan?.textContent).toContain('Count: 1');
incrementBtn?.click();
await nextTick();
expect(countSpan?.textContent).toContain('Count: 2');
});
});
}