import { describe, it, afterEach } from "vitest"; import { render, screen, cleanup } from "@testing-library/react"; import { PublicPageRenderer } from "@/features/editor/components/PublicPageRenderer"; import { createHeroTemplateBlocks } from "@/app/editor/templates/heroTemplate"; import { createFeaturesTemplateBlocks } from "@/app/editor/templates/featuresTemplate"; import { createCtaTemplateBlocks } from "@/app/editor/templates/ctaTemplate"; import type { Block } from "@/features/editor/state/editorStore"; // PublicPageRenderer 템플릿 TDD // - Hero / Features / CTA 템플릿이 섹션 + 텍스트/버튼 구조로 올바르게 렌더되는지 검증한다. function createIdFactory() { let i = 0; return () => `tpl_${++i}`; } describe("PublicPageRenderer - 섹션 템플릿", () => { afterEach(() => { cleanup(); }); it("Hero 템플릿 섹션은 섹션과 헤드라인/서브텍스트/버튼을 렌더해야 한다", () => { const sectionId = "hero_section_1"; const { blocks } = createHeroTemplateBlocks({ sectionId, createId: createIdFactory() }); render(); // 헤드라인/서브텍스트 텍스트가 존재해야 한다. screen.getByText("Hero 제목을 여기에 입력하세요"); screen.getByText("제품이나 서비스를 한 문장으로 설명하는 서브텍스트입니다."); // CTA 버튼 라벨 텍스트가 존재해야 한다. screen.getByText("지금 시작하기"); }); it("Features 템플릿 섹션은 3컬럼 Feature 제목/설명 텍스트를 렌더해야 한다", () => { const sectionId = "features_section_1"; const { blocks } = createFeaturesTemplateBlocks({ sectionId, createId: createIdFactory() }); render(); // 각 컬럼의 Feature 제목과 설명 텍스트가 모두 존재해야 한다. screen.getByText("Feature 1 제목"); screen.getByText("Feature 2 제목"); screen.getByText("Feature 3 제목"); const descText = "해당 기능을 간단히 설명하는 텍스트입니다."; // 설명 텍스트는 3번 등장해야 한다. const allDesc = screen.getAllByText(descText); if (allDesc.length !== 3) { throw new Error(`기대하는 설명 텍스트 개수(3)가 아니고 ${allDesc.length}개가 렌더되었습니다.`); } }); it("CTA 템플릿 섹션은 텍스트와 CTA 버튼을 렌더해야 한다", () => { const sectionId = "cta_section_1"; const { blocks } = createCtaTemplateBlocks({ sectionId, createId: createIdFactory() }); render(); // CTA 본문 텍스트와 버튼 라벨이 존재해야 한다. screen.getByText("지금 바로 행동을 유도하는 CTA 텍스트를 입력하세요."); screen.getByText("CTA 버튼"); }); });