chore(reports): docs/reports를 고객·단계별 폴더로 분류

- viewclinic/01_readiness_report (진단 덱 v1.0·v2_표준캔버스·v1.1 + 빌더) / 02_poc_proposal (POC 정본·v3 + 빌더) / 03_question_bank (QB 120문항·실측·엑셀) / 04_supporters (GEO 계획·콘텐츠 기획·감사 엑셀)
- taeha/ (태하 리포트 + 빌더), ibk/ (기업은행 블로그 감사), landing/ (랜딩 시안·스크린샷·HTML 내보내기)
- README.md에 구조·정본/파생본·빌드 명령 안내
- 경로 참조 갱신: 핸드오버 문서 4개, QB 스크립트 3개, 빌더 docstring, discovery 페이지 주석
- 이전에 삭제된 POC v2_표준캔버스 2파일 삭제 반영

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
This commit is contained in:
Haewon Kam 2026-09-07 13:03:53 +09:00
parent 90ad27ee73
commit 13a8fca775
48 changed files with 153 additions and 25 deletions

View File

@ -92,7 +92,7 @@
## v1.1 개선 과제 (2026-09-01 · Question Bank 120문항 실측 검증에서 도출) ## v1.1 개선 과제 (2026-09-01 · Question Bank 120문항 실측 검증에서 도출)
뷰성형외과 잠재 환자 질문 120개를 OpenAI 웹검색 API(gpt-4o + web_search, 서울 고정)와 Perplexity API(sonar)로 실측해 기준표 기반 사전판정을 채점했다. 데이터: `docs/reports/Viewclinic_QB_Results_Combined.md`, raw `scripts/out/qb_{openai,perplexity}_results.jsonl`, 러너 `scripts/run_question_bank_openai.py`. 뷰성형외과 잠재 환자 질문 120개를 OpenAI 웹검색 API(gpt-4o + web_search, 서울 고정)와 Perplexity API(sonar)로 실측해 기준표 기반 사전판정을 채점했다. 데이터: `docs/reports/viewclinic/03_question_bank/Viewclinic_QB_Results_Combined.md`, raw `scripts/out/qb_{openai,perplexity}_results.jsonl`, 러너 `scripts/run_question_bank_openai.py`.
**검증 요약** **검증 요약**

View File

@ -28,7 +28,7 @@ docs/AI_DISCOVERY_BUILD2_HANDOVER.md 를 읽고 AI Discovery 자동 채점기를
| 리포트 `/discovery/:id` | viewclinic 48점/C, taeha 68점/B | | 리포트 `/discovery/:id` | viewclinic 48점/C, taeha 68점/B |
| 데이터 파생 | 랜딩·리포트의 모든 수치는 `scoreDiscovery` 계산값. `nextGradeTarget`·`scorePctColor` 헬퍼 포함 | | 데이터 파생 | 랜딩·리포트의 모든 수치는 `scoreDiscovery` 계산값. `nextGradeTarget`·`scorePctColor` 헬퍼 포함 |
| lint | `npm run lint`(tsc) 0 에러. 단, 실제 검사는 AEO-GEO-Audit 워크트리에서만 가능 (main 워크트리는 node_modules에 tsc 없음) | | lint | `npm run lint`(tsc) 0 에러. 단, 실제 검사는 AEO-GEO-Audit 워크트리에서만 가능 (main 워크트리는 node_modules에 tsc 없음) |
| 영업 자료 | POC 제안서 `docs/reports/Viewclinic_POC_Proposal.pptx/.pdf` (10장) | | 영업 자료 | POC 제안서 `docs/reports/viewclinic/02_poc_proposal/Viewclinic_POC_Proposal.pptx/.pdf` (10장) |
## 2. 확정 결정 (2026-08-31 haewon) ## 2. 확정 결정 (2026-08-31 haewon)
@ -126,7 +126,7 @@ auto 22항목 중 **18항목 기존 실측(2026-08-28)과 일치**. 불일치 4
## 추가 (2026-09-01) · Question Bank 120문항 2엔진 실측 ## 추가 (2026-09-01) · Question Bank 120문항 2엔진 실측
- 산출물: `docs/reports/Viewclinic_AI_Discovery_Question_Bank.md`(120문항+사전판정+검증), `Viewclinic_QB_Results_Combined.md`(질문별 상위 병원 통합표), `Viewclinic_QB_Results_TOP50.xlsx`(5시트), raw `scripts/out/qb_{openai,perplexity}_results.jsonl` - 산출물: `docs/reports/viewclinic/03_question_bank/Viewclinic_AI_Discovery_Question_Bank.md`(120문항+사전판정+검증), `Viewclinic_QB_Results_Combined.md`(질문별 상위 병원 통합표), `Viewclinic_QB_Results_TOP50.xlsx`(5시트), raw `scripts/out/qb_{openai,perplexity}_results.jsonl`
- 러너: `scripts/run_question_bank_openai.py` (OpenAI Responses API + web_search 서울 고정 / Perplexity sonar, JSONL 재개 가능, UI 자동조회 금지 원칙 준수). 통합표 `scripts/merge_qb_results.py`, 엑셀 `scripts/export_qb_excel.py`. POC 후 재측정 시 JSONL 삭제 후 동일 명령 재실행. - 러너: `scripts/run_question_bank_openai.py` (OpenAI Responses API + web_search 서울 고정 / Perplexity sonar, JSONL 재개 가능, UI 자동조회 금지 원칙 준수). 통합표 `scripts/merge_qb_results.py`, 엑셀 `scripts/export_qb_excel.py`. POC 후 재측정 시 JSONL 삭제 후 동일 명령 재실행.
- 결과: 브랜드 질문 뷰 언급 GPT 97% · PPLX 100%, 논브랜드 GPT 11%(10/84) · PPLX 3%(3/84). 시술 정보 52문항은 두 엔진 모두 0건. - 결과: 브랜드 질문 뷰 언급 GPT 97% · PPLX 100%, 논브랜드 GPT 11%(10/84) · PPLX 3%(3/84). 시술 정보 52문항은 두 엔진 모두 0건.
- 점수 정합성 교정: scoreDiscovery 계산값 50/C(44.1/89, 검증 32/36)로 덱 2종(진단 리포트·POC 제안서)과 문서를 일괄 교정. 재채점 커밋 메시지의 49는 반올림 착오였음. 랜딩 스크린샷(shots/land_hero·land_report)도 프로덕션 50점 화면으로 재캡처(구판은 *_48pt_backup.png). - 점수 정합성 교정: scoreDiscovery 계산값 50/C(44.1/89, 검증 32/36)로 덱 2종(진단 리포트·POC 제안서)과 문서를 일괄 교정. 재채점 커밋 메시지의 49는 반올림 착오였음. 랜딩 스크린샷(shots/land_hero·land_report)도 프로덕션 50점 화면으로 재캡처(구판은 *_48pt_backup.png).

View File

@ -10,7 +10,7 @@
``` ```
docs/AI_DISCOVERY_FRONTEND_HANDOVER.md 를 읽고 AI Discovery 랜딩 페이지를 프로덕트에 구현해줘. docs/AI_DISCOVERY_FRONTEND_HANDOVER.md 를 읽고 AI Discovery 랜딩 페이지를 프로덕트에 구현해줘.
- 시안: docs/reports/ai_discovery_landing.html (픽셀 기준, 이 파일이 정답) - 시안: docs/reports/landing/ai_discovery_landing.html (픽셀 기준, 이 파일이 정답)
- 라우트: /discovery (index) 신규, 기존 /discovery/:id 리포트 페이지와 공존 - 라우트: /discovery (index) 신규, 기존 /discovery/:id 리포트 페이지와 공존
- 재사용: Navbar/Footer(BI 워드마크), ScoreRing, Solution.tsx의 루프 다이어그램 구조(AGDP → ABMR 워딩) - 재사용: Navbar/Footer(BI 워드마크), ScoreRing, Solution.tsx의 루프 다이어그램 구조(AGDP → ABMR 워딩)
- 데이터: src/data/discovery_viewclinic.ts + src/lib/discoveryScore.ts 실측값만 사용, 수치 하드코딩 금지 - 데이터: src/data/discovery_viewclinic.ts + src/lib/discoveryScore.ts 실측값만 사용, 수치 하드코딩 금지
@ -25,10 +25,10 @@ docs/AI_DISCOVERY_FRONTEND_HANDOVER.md 를 읽고 AI Discovery 랜딩 페이지
| 산출물 | 경로 | 상태 | | 산출물 | 경로 | 상태 |
|---|---|---| |---|---|---|
| 랜딩 시안 (단일 HTML, 픽셀 정답) | `docs/reports/ai_discovery_landing.html` | 확정 | | 랜딩 시안 (단일 HTML, 픽셀 정답) | `docs/reports/landing/ai_discovery_landing.html` | 확정 |
| 랜딩 스크린샷 (덱 삽입용) | `docs/reports/shots/land_hero.png`, `land_report.png` | 확정 | | 랜딩 스크린샷 (덱 삽입용) | `docs/reports/landing/shots/land_hero.png`, `land_report.png` | 확정 |
| POC 제안서 덱 (10장) | `docs/reports/Viewclinic_POC_Proposal.pptx` / `.pdf` | 확정 | | POC 제안서 덱 (10장) | `docs/reports/viewclinic/02_poc_proposal/Viewclinic_POC_Proposal.pptx` / `.pdf` | 확정 |
| 덱 빌드 스크립트 | `docs/reports/build_viewclinic_poc_deck.py` | 재실행 가능 | | 덱 빌드 스크립트 | `docs/reports/viewclinic/02_poc_proposal/build_viewclinic_poc_deck.py` | 재실행 가능 |
시안 HTML은 외부 의존성이 Google Fonts(Playfair Display, Noto Sans KR) 하나뿐인 시안 HTML은 외부 의존성이 Google Fonts(Playfair Display, Noto Sans KR) 하나뿐인
단일 파일이다. 랜딩을 수정하면 스크린샷 재캡처 → 덱 리빌드 순서로 갱신한다 단일 파일이다. 랜딩을 수정하면 스크린샷 재캡처 → 덱 리빌드 순서로 갱신한다
@ -83,7 +83,7 @@ docs/AI_DISCOVERY_FRONTEND_HANDOVER.md 를 읽고 AI Discovery 랜딩 페이지
## 7. 완료 기준·배포 ## 7. 완료 기준·배포
- `npm run lint` (tsc --noEmit) 통과. - `npm run lint` (tsc --noEmit) 통과.
- 1440px에서 `/discovery``docs/reports/ai_discovery_landing.html`과 시각적으로 일치. - 1440px에서 `/discovery``docs/reports/landing/ai_discovery_landing.html`과 시각적으로 일치.
- 390px에서 2열 그리드가 1열로 접히고 헤드라인이 줄바꿈 깨짐 없이 표시. - 390px에서 2열 그리드가 1열로 접히고 헤드라인이 줄바꿈 깨짐 없이 표시.
- 배포: `git push``vercel --prod` 수동 실행 (Gitea 자동 트리거 없음). - 배포: `git push``vercel --prod` 수동 실행 (Gitea 자동 트리거 없음).

View File

@ -21,17 +21,17 @@ INFINITH 저장소(브랜치 feature/discovery-url-cta)에서 "AI Discovery 자
| 자산 | 위치 | 상태 | | 자산 | 위치 | 상태 |
|---|---|---| |---|---|---|
| AI Discovery 랜딩 (뷰성형외과 제안용) | `src/pages/DiscoveryLandingPage.tsx` + `src/components/discovery/` 9종 (Hero·WhyNow·AbmrLoop·HowItWorks·SampleReport·HonestyStrip·Roadmap·DiscoveryCta·DiscoveryLeadModal) | 프로덕션 https://infinith-demo.vercel.app/discovery (main). 단일 HTML 시안 `docs/reports/ai_discovery_landing.html` | | AI Discovery 랜딩 (뷰성형외과 제안용) | `src/pages/DiscoveryLandingPage.tsx` + `src/components/discovery/` 9종 (Hero·WhyNow·AbmrLoop·HowItWorks·SampleReport·HonestyStrip·Roadmap·DiscoveryCta·DiscoveryLeadModal) | 프로덕션 https://infinith-demo.vercel.app/discovery (main). 단일 HTML 시안 `docs/reports/landing/ai_discovery_landing.html` |
| URL 입력 CTA | `DiscoveryLeadModal.tsx` → Supabase `discovery_leads` insert (URL·연락처 필수, 상호 선택). 실패 시 o2oteam@o2o.kr mailto 폴백 | 브랜치 `feature/discovery-url-cta`, 프로덕션 미배포. 마이그레이션 `supabase/migrations/20260831_discovery_leads.sql` **미적용** (supabase login 후 db push 필요) | | URL 입력 CTA | `DiscoveryLeadModal.tsx` → Supabase `discovery_leads` insert (URL·연락처 필수, 상호 선택). 실패 시 o2oteam@o2o.kr mailto 폴백 | 브랜치 `feature/discovery-url-cta`, 프로덕션 미배포. 마이그레이션 `supabase/migrations/20260831_discovery_leads.sql` **미적용** (supabase login 후 db push 필요) |
| 진단 리포트 페이지 | `src/pages/DiscoveryReportPage.tsx`, 결과 레지스트리 `src/data/discoveryResults.ts`, 뷰성형외과 결과 `src/data/discovery_viewclinic.ts` (50/C) | 새 병원 = 결과 파일 + 레지스트리 1줄 | | 진단 리포트 페이지 | `src/pages/DiscoveryReportPage.tsx`, 결과 레지스트리 `src/data/discoveryResults.ts`, 뷰성형외과 결과 `src/data/discovery_viewclinic.ts` (50/C) | 새 병원 = 결과 파일 + 레지스트리 1줄 |
| 기준표 | `src/data/aeoGeoRubric.ts` (36항목, A20/B20/C25/D20/E10/F5), 문서 `docs/AEO_GEO_RUBRIC.md`, 채점 `src/lib/discoveryScore.ts` | v1.0. 미검증은 분모 제외 | | 기준표 | `src/data/aeoGeoRubric.ts` (36항목, A20/B20/C25/D20/E10/F5), 문서 `docs/AEO_GEO_RUBRIC.md`, 채점 `src/lib/discoveryScore.ts` | v1.0. 미검증은 분모 제외 |
| 자동 채점기 | `scripts/audit_aeo_geo.py <main_url> <service_url> --id --name --skip-ts --json` (auto 21~22항목) | stdlib+curl. 노드 순회가 역순(stack.pop)이라 sameAs는 Organization 타입 노드가 먼저 잡힘 → 서포터즈 스키마는 `@type: ['MedicalClinic','Organization']` | | 자동 채점기 | `scripts/audit_aeo_geo.py <main_url> <service_url> --id --name --skip-ts --json` (auto 21~22항목) | stdlib+curl. 노드 순회가 역순(stack.pop)이라 sameAs는 Organization 타입 노드가 먼저 잡힘 → 서포터즈 스키마는 `@type: ['MedicalClinic','Organization']` |
| 기존 백엔드 파이프라인 | `supabase/functions/` discover-channels → collect-channel-data → generate-report → generate-content-plan, scrape-website, enrich-channels, `_shared/` (extractSocialLinks·verifyHandles·dataQuality·retry) | 실제 연동: YouTube Data API, Apify, Naver Search API, Firecrawl, Perplexity. 문서 `docs/AI_DISCOVERY_BUILD2_HANDOVER.md`, `docs/PIPELINE_IMPROVEMENT_PLAN.md` | | 기존 백엔드 파이프라인 | `supabase/functions/` discover-channels → collect-channel-data → generate-report → generate-content-plan, scrape-website, enrich-channels, `_shared/` (extractSocialLinks·verifyHandles·dataQuality·retry) | 실제 연동: YouTube Data API, Apify, Naver Search API, Firecrawl, Perplexity. 문서 `docs/AI_DISCOVERY_BUILD2_HANDOVER.md`, `docs/PIPELINE_IMPROVEMENT_PLAN.md` |
| 질문 뱅크 | `docs/reports/Viewclinic_AI_Discovery_Question_Bank.md` (120문항, 7카테고리), 러너 `scripts/run_question_bank_openai.py`, 통합 `scripts/merge_qb_results.py`, 엑셀 `scripts/export_qb_excel.py` | 뷰성형외과 2엔진 실측 완료 | | 질문 뱅크 | `docs/reports/viewclinic/03_question_bank/Viewclinic_AI_Discovery_Question_Bank.md` (120문항, 7카테고리), 러너 `scripts/run_question_bank_openai.py`, 통합 `scripts/merge_qb_results.py`, 엑셀 `scripts/export_qb_excel.py` | 뷰성형외과 2엔진 실측 완료 |
| **서포터즈 샘플 사이트 (수작업 v3)** | `supporters/` (Astro 7 정적, 별도 Vercel 프로젝트 `view-supporters-sample`, https://view-supporters-sample.vercel.app, noindex) | 이 세션의 산출물. 자동화의 정답지(golden sample) | | **서포터즈 샘플 사이트 (수작업 v3)** | `supporters/` (Astro 7 정적, 별도 Vercel 프로젝트 `view-supporters-sample`, https://view-supporters-sample.vercel.app, noindex) | 이 세션의 산출물. 자동화의 정답지(golden sample) |
| 감사 비교 엑셀 | `docs/reports/Viewclinic_Supporters_vs_Official_AEO_Audit.xlsx`, 빌더 `scripts/build_supporters_audit_xlsx.py` | 공식 50/C · 샘플 78/B · 색인 허용 86/A. 시트 4 "E 측정 인프라 연결 가이드" | | 감사 비교 엑셀 | `docs/reports/viewclinic/04_supporters/Viewclinic_Supporters_vs_Official_AEO_Audit.xlsx`, 빌더 `scripts/build_supporters_audit_xlsx.py` | 공식 50/C · 샘플 78/B · 색인 허용 86/A. 시트 4 "E 측정 인프라 연결 가이드" |
| 설계 문서 | `docs/INFINITH_Viewclinic_Supporters_Site_Design_v0.1.md` | 중복 회피 6규칙, 법무 게이트, 네이버 2트랙 | | 설계 문서 | `docs/INFINITH_Viewclinic_Supporters_Site_Design_v0.1.md` | 중복 회피 6규칙, 법무 게이트, 네이버 2트랙 |
| 기업은행 블로그 감사 | `docs/reports/IBK_Blog_AEO_GEO_Audit_2026-09-04.md` | 54/C, Perplexity 3/3 인용. 글 구조(세 줄 요약·질문형 H3·표·FAQ)의 근거 | | 기업은행 블로그 감사 | `docs/reports/ibk/IBK_Blog_AEO_GEO_Audit_2026-09-04.md` | 54/C, Perplexity 3/3 인용. 글 구조(세 줄 요약·질문형 H3·표·FAQ)의 근거 |
### supporters/ 구조 (자동 생성기가 만들어야 할 결과물) ### supporters/ 구조 (자동 생성기가 만들어야 할 결과물)
``` ```

39
docs/reports/README.md Normal file
View File

@ -0,0 +1,39 @@
# docs/reports 폴더 안내
2026-09-07 분류. 산출물은 고객(병원)별 폴더 아래 산출 단계 순서로 둔다. 빌드 스크립트는 산출물과 같은 폴더에 둔다.
```
docs/reports/
├── viewclinic/ 뷰성형외과
│ ├── 01_readiness_report/ AI Answer Readiness 진단 덱 (v1.0 정본 · v2_표준캔버스 · v1.1 정정판) + 빌더
│ ├── 02_poc_proposal/ POC 제안서 덱 (정본 · v3 · v3_표준캔버스) + 빌더
│ ├── 03_question_bank/ 질문 뱅크 120문항 · ChatGPT/Perplexity 실측 결과 · TOP50 엑셀
│ └── 04_supporters/ 서포터즈 GEO 개선 계획 · 2단계 콘텐츠 기획 · 서포터즈 vs 공식 AEO 감사 엑셀
├── taeha/ 태하 AI Answer Readiness 리포트 (html · pdf · pptx) + 빌더
├── ibk/ 기업은행 블로그 AEO/GEO 감사
└── landing/ AI Discovery 랜딩 시안 (픽셀 정답 HTML) · 스크린샷 · 리포트 페이지 HTML 내보내기 스크립트
```
## 정본과 파생본
- `Viewclinic_AI_Answer_Readiness_Report.pptx`: v1.0 정본. haewon이 폰트를 직접 손본 파일이라 재생성하지 않는다.
- `Viewclinic_AI_Answer_Readiness_Report_v1.1.pptx`: 2026-09-07 재검증 정정판. 블로그·FAQ·수치 판정 3건 정정, 병원 요청 슬라이드 추가. 빌더 `build_viewclinic_deck_v1_1.py`.
- `Viewclinic_POC_Proposal.pptx`: POC 제안서 정본(haewon 수정본). v3 계열은 폰트 기준 적용 파생본.
- `*_표준캔버스.pptx`: 20in 캔버스를 2/3로 균등 축소한 13.33in 편집용. `scripts/rescale_deck.py`로 만든다.
## 빌드
```bash
# 진단 덱 v1.1
python3 docs/reports/viewclinic/01_readiness_report/build_viewclinic_deck_v1_1.py docs/reports/viewclinic/01_readiness_report/Viewclinic_AI_Answer_Readiness_Report_v1.1.pptx
# 표준캔버스 축소본
python3 scripts/rescale_deck.py <in.pptx> <out_표준캔버스.pptx>
# PDF
soffice --headless --convert-to pdf <file.pptx>
# 질문 뱅크 실측 → 통합 → 엑셀 (출력 경로는 스크립트 안에 03_question_bank로 고정)
python3 scripts/run_question_bank_openai.py && python3 scripts/merge_qb_results.py && python3 scripts/export_qb_excel.py
```
## 다른 문서에서의 참조
`docs/AI_DISCOVERY_FRONTEND_HANDOVER.md`, `docs/AI_DISCOVERY_BUILD2_HANDOVER.md`, `docs/AEO_GEO_RUBRIC.md`, `docs/NEXT_SESSION_SUPPORTERS_AUTOBUILD.md``src/pages/DiscoveryLandingPage.tsx` 주석이 이 폴더를 가리킨다. 파일을 옮기면 그 참조도 같이 고친다.

View File

@ -0,0 +1,89 @@
# IBK기업은행 블로그(blog.ibk.co.kr) AEO/GEO 감사
**실측일:** 2026-09-04 · **도구:** `scripts/audit_aeo_geo.py`(자동 22항목) + 수동 판정 5항목 + Perplexity sonar 실측 3문항
**대상 URL:** 메인 https://blog.ibk.co.kr/ + 최신 글 https://blog.ibk.co.kr/569694 (2026-09-02 발행, "IBK나라사랑카드 PX 환급")
**목적:** 뷰성형외과 서포터즈 사이트의 레퍼런스 모델로 삼기 전, 이 모델이 AI 답변엔진에 실제로 인용되는 구조인지 확인
---
## 1. 결론
**54점 / C (38.7 / 71, 검증 26/36).** 뷰성형외과(50점/C)와 총점은 비슷하지만 내용이 정반대입니다.
| | IBK 블로그 | 뷰성형외과 |
|---|---|---|
| 총점 | 54 / C | 50 / C |
| A 접근성 | 84% | 98% |
| B 엔티티 | **20%** | 25% |
| C 콘텐츠 | **64%** | 28% |
| D 표면 | 53% (검증 2/6) | 68% |
| E 측정 | 미검증 | 0% |
| F 위생 | 42% | 33% |
IBK 블로그는 **글 한 편의 구조(C)가 강하고, "누가 쓴 사이트인가"를 알리는 엔티티(B)가 약합니다.** 뷰성형외과는 반대로 접근성은 좋은데 인용할 문장이 없었습니다. 서포터즈 사이트는 IBK의 글 구조를 가져오되, IBK가 놓친 엔티티 연결을 처음부터 넣으면 됩니다.
**Perplexity 실측 3문항 중 3문항에서 blog.ibk.co.kr이 인용되었습니다.** 특히 "나라사랑카드 PX 환급 언제 입금돼?"라는 질문에 발행 2일 된 글이 1순위 출처로 나왔습니다. 이 모델은 실제로 작동합니다.
주의: 3문항 × 1회는 정식 기준선(10문항 × 5회)이 아닙니다. 방향 확인용 증거이며 언급률로 보고하지 않습니다.
---
## 2. 왜 인용되는가 (글 구조 실측)
최신 글 569694의 구조입니다. 서포터즈 페이지 템플릿이 그대로 가져갈 부분입니다.
| 요소 | 실측 | 판정 |
|---|---|---|
| 첫 단락 | "💡세 줄 요약" 블록. 질문의 답(신청 불필요·입금 시점·월 한도 11만 원)을 3문장으로 먼저 제시 | 직접 답변 블록의 교과서 형태 |
| H1 | 1개, 서술형 제목("IBK나라사랑카드 PX 환급, 신청 조건부터 입금 시점·할인 한도까지") | 양호. 단 빈 H1이 하나 더 있음(테마 결함) |
| H3 | "1. 나라사랑카드 PX 환급, 별도 신청이 필요한가요?" 등 질문형 3개 + "FAQ. 자주 하는 질문" | 질문형 소제목 |
| 표 | HTML table 2개 | 이미지가 아닌 표 |
| 수치 | 월 최대 11만 원, 20만 원 이상 50%, 3만 원 미만 15% 등 조건이 붙은 수치 | C4 만점 |
| FAQ | 텍스트 FAQ 섹션 존재. FAQPage 스키마는 없음 | 절반 |
| 갱신 | datePublished·dateModified·article:modified_time 모두 존재. sitemap lastmod 2,244개 글 전부 표기 | 만점 |
| 본문 길이 | 텍스트 약 13,500자, HTML 71KB | 가볍고 길다 |
---
## 3. 무엇이 약한가
| 항목 | 실측 | 서포터즈 설계 반영 |
|---|---|---|
| B2 조직 스키마 | Organization·BankOrCreditUnion 없음. JSON-LD의 publisher가 **"TISTORY"** | 티스토리 기본 스키마의 한계. 자체 빌드에서는 publisher와 about을 병원 엔티티로 |
| B5 sameAs | 빈 배열. 푸터에 페이스북·인스타·유튜브 링크가 있어도 스키마에 미연결 | sameAs에 홈페이지·유튜브·강남언니·GBP 연결 |
| 저자 | author가 "IBK.Bank.Official"이라는 Person. 실명·자격 없음 | 실명 서포터즈 Person + reviewedBy 원장 |
| B3·B4 | 전문가 스키마 없음. 주소·전화가 텍스트에 없음 | 팩트 시트에서 병원 정보 블록 자동 삽입 |
| C3 메인 H1 | 메인 페이지 H1 0개 | 메인에도 서술형 H1 1개 |
| A5 sitemap | /sitemap.xml은 있으나 robots.txt에 Sitemap 미선언 | robots에 선언 |
| A4 리다이렉트 | http → https 일부 302 | 301 |
| F1 alt | 메인 이미지 23개 중 19개(83%) alt 없음. 글 이미지 28개 중 20개 alt 없음 | 캡처 이미지 alt 필수 게이트 |
| C2 FAQPage | 텍스트 FAQ는 있으나 스키마 없음 | FAQPage 스키마 |
| 플랫폼 통제 | robots.txt는 카카오 공통, 서버 로그 접근 불가 | 자체 빌드로 해결 |
---
## 4. 중복 처리 방식 (참고 사례)
티스토리 기본 주소 **smartibk.tistory.com** 이 blog.ibk.co.kr과 같은 글을 그대로 200으로 서빙합니다. 즉 같은 글이 두 주소에 존재합니다. 티스토리는 이를 `rel=canonical → https://blog.ibk.co.kr/569694` 로 처리해 검색엔진이 한 주소만 원본으로 인식하게 합니다. 실측 결과 Perplexity 인용도 전부 blog.ibk.co.kr이었습니다.
시사점: 중복이 생겨도 canonical이 일관되면 원본이 살아남습니다. 서포터즈 허브와 네이버 재작성본 사이에도 같은 원리를 적용합니다(허브 선발행 + 허브 링크).
---
## 5. Perplexity 실측 상세
| 질문 | blog.ibk.co.kr 인용 | 인용 순위 | 비고 |
|---|---|---|---|
| 나라사랑카드 PX 할인 환급은 언제 어디로 입금돼? | ○ | 1위 (569694) | 발행 2일 된 글. 답변 첫 문장이 글의 세 줄 요약과 일치 |
| IBK기업은행 공식 블로그 있어? 무슨 내용 다뤄? | ○ | 1위 (메인) | 카테고리·태그 페이지까지 인용 |
| 기업은행 중소기업 대출 상품 종류 알려줘 | ○ | 하위 | 개인 티스토리·언론이 상위. 공식 블로그가 밀림 |
raw: 스크래치패드 `ibk_pplx/q1~3.json`, 자동 채점 `ibk_audit.json`
---
## 6. 판정 근거 메모
- 자동 판정 21항목은 스크립트 출력 그대로. 수동 판정 5항목(C1=2, C4=3, C7=1, C8=2, D3=2)은 글 569694 실측으로 haewon이 재확인 가능
- 기준표는 로컬 비즈니스용이라 D1(버티컬)·D2(GBP)·D5(플레이스)·B3(전문가)는 기업 블로그에 잘 맞지 않음. 미검증 처리해 분모에서 제외했고, B3은 스키마 부재 사실 그대로 0점
- E(측정) 4항목은 오너 접근 필요. 3문항 스팟체크는 E4 정식 기준선이 아니므로 미검증 유지

View File

@ -2,7 +2,7 @@
/discovery/:id 리포트 페이지를 단일 HTML 파일로 내보낸다. /discovery/:id 리포트 페이지를 단일 HTML 파일로 내보낸다.
npm run build && npx vite preview --port 3012 npm run build && npx vite preview --port 3012
python3 docs/reports/export_html.py taeha docs/reports/Taeha_AI_Answer_Readiness_Report.html python3 docs/reports/landing/export_html.py taeha docs/reports/taeha/Taeha_AI_Answer_Readiness_Report.html
- 헤드리스 Chrome으로 렌더된 DOM을 덤프하고 빌드 CSS를 인라인한다 - 헤드리스 Chrome으로 렌더된 DOM을 덤프하고 빌드 CSS를 인라인한다
- Navbar·Footer·스크립트 제거, motion 애니메이션 고정 - Navbar·Footer·스크립트 제거, motion 애니메이션 고정

View File

Before

Width:  |  Height:  |  Size: 678 KiB

After

Width:  |  Height:  |  Size: 678 KiB

View File

Before

Width:  |  Height:  |  Size: 109 KiB

After

Width:  |  Height:  |  Size: 109 KiB

View File

@ -1,7 +1,7 @@
""" """
법무법인 태하 AI Answer Readiness Report 빌드 (INFINITH Deck 규격) 법무법인 태하 AI Answer Readiness Report 빌드 (INFINITH Deck 규격)
python3 docs/reports/build_taeha_deck.py docs/reports/Taeha_AI_Answer_Readiness_Report.pptx python3 docs/reports/taeha/build_taeha_deck.py docs/reports/taeha/Taeha_AI_Answer_Readiness_Report.pptx
""" """
import sys import sys
sys.path.insert(0, "/Users/haewonkam/.claude/skills/infinith-deck/scripts") sys.path.insert(0, "/Users/haewonkam/.claude/skills/infinith-deck/scripts")

View File

@ -1,7 +1,7 @@
""" """
Viewclinic AI Answer Readiness Report 빌드 (INFINITH Deck 규격) Viewclinic AI Answer Readiness Report 빌드 (INFINITH Deck 규격)
python3 docs/reports/build_viewclinic_deck.py docs/reports/Viewclinic_AI_Answer_Readiness_Report.pptx python3 docs/reports/viewclinic/01_readiness_report/build_viewclinic_deck.py docs/reports/viewclinic/01_readiness_report/Viewclinic_AI_Answer_Readiness_Report.pptx
""" """
import sys import sys
sys.path.insert(0, "/Users/haewonkam/.claude/skills/infinith-deck/scripts") sys.path.insert(0, "/Users/haewonkam/.claude/skills/infinith-deck/scripts")

View File

@ -10,7 +10,7 @@ v1.0(2026-09-01)을 2026-09-07 재검증으로 정정한 판. 원본 v1.0 파일
폰트: haewon 확정 기준(본문 20 / 리드 24 / 카드 제목 28). ifd 분량 검사(폰트 축소 금지) 안에서 카피를 줄였다. 폰트: haewon 확정 기준(본문 20 / 리드 24 / 카드 제목 28). ifd 분량 검사(폰트 축소 금지) 안에서 카피를 줄였다.
python3 docs/reports/build_viewclinic_deck_v1_1.py docs/reports/Viewclinic_AI_Answer_Readiness_Report_v1.1.pptx python3 docs/reports/viewclinic/01_readiness_report/build_viewclinic_deck_v1_1.py docs/reports/viewclinic/01_readiness_report/Viewclinic_AI_Answer_Readiness_Report_v1.1.pptx
""" """
import sys import sys
sys.path.insert(0, "/Users/haewonkam/.claude/skills/infinith-deck/scripts") sys.path.insert(0, "/Users/haewonkam/.claude/skills/infinith-deck/scripts")

View File

@ -7,10 +7,10 @@ Viewclinic AI Discovery POC Proposal 덱 빌드 (INFINITH Deck 규격, 15페이
리드문(ifd 내부 20pt) 카드 제목(24pt) ifd 기본값이라, 재생성 후처리로 24/28 승격이 필요하다. 리드문(ifd 내부 20pt) 카드 제목(24pt) ifd 기본값이라, 재생성 후처리로 24/28 승격이 필요하다.
제안 4 + 진단 리포트 요약 5 + 부록 5( 점수 읽는 + User Question Bank 120문항 실측) + 클로징 1. 제안 4 + 진단 리포트 요약 5 + 부록 5( 점수 읽는 + User Question Bank 120문항 실측) + 클로징 1.
부록 실측 데이터: docs/reports/Viewclinic_QB_Results_Combined.md (2026-09-01, OpenAI·Perplexity API) 부록 실측 데이터: docs/reports/viewclinic/03_question_bank/Viewclinic_QB_Results_Combined.md (2026-09-01, OpenAI·Perplexity API)
본문 텍스트는 기본값 대비 +2pt (rows/bullets 18, grid 16.25, quote 19.25). 본문 텍스트는 기본값 대비 +2pt (rows/bullets 18, grid 16.25, quote 19.25).
python3 docs/reports/build_viewclinic_poc_deck.py docs/reports/Viewclinic_POC_Proposal.pptx python3 docs/reports/viewclinic/02_poc_proposal/build_viewclinic_poc_deck.py docs/reports/viewclinic/02_poc_proposal/Viewclinic_POC_Proposal.pptx
""" """
import os import os
import sys import sys

View File

@ -8,7 +8,7 @@
| 근거 | 무엇을 말해 주나 | 출처 | | 근거 | 무엇을 말해 주나 | 출처 |
|---|---|---| |---|---|---|
| 질문 뱅크 120문항 실측 (2026-09-01) | 논브랜드 질문에서 뷰 언급률 ChatGPT 11%, Perplexity 3%. C 추천·비교 15문항 전부 ✕, F 가격 8문항 전부 ✕, D2 눈·D3 코·D4 윤곽 27문항 중 25문항 ✕ | docs/reports/Viewclinic_QB_Results_Combined.md | | 질문 뱅크 120문항 실측 (2026-09-01) | 논브랜드 질문에서 뷰 언급률 ChatGPT 11%, Perplexity 3%. C 추천·비교 15문항 전부 ✕, F 가격 8문항 전부 ✕, D2 눈·D3 코·D4 윤곽 27문항 중 25문항 ✕ | docs/reports/viewclinic/03_question_bank/Viewclinic_QB_Results_Combined.md |
| 유튜브 조회수 (2026-09-04) | 사람들이 실제로 보는 주제. 롱폼 1~5위: 보형물 촉감 21만, 기능코성형 15만, 코 모양 13만, 눈성형 9만, 안면거상 6만. 정보형 쇼츠 1위 뒤트임·밑트임 차이 17만 | supporters/src/data/videos.json | | 유튜브 조회수 (2026-09-04) | 사람들이 실제로 보는 주제. 롱폼 1~5위: 보형물 촉감 21만, 기능코성형 15만, 코 모양 13만, 눈성형 9만, 안면거상 6만. 정보형 쇼츠 1위 뒤트임·밑트임 차이 17만 | supporters/src/data/videos.json |
| 뉴스 1,137건 주제 분포 | 가슴 226 · 윤곽·양악 148 · 리프팅·피부 148 · 눈·코 115. 최근 3개월: 고압산소치료기 도입(회복관리), 프리저베 도입, 코성형 협진 인터뷰, 중년 눈성형, 안면거상 | supporters/src/data/news.json | | 뉴스 1,137건 주제 분포 | 가슴 226 · 윤곽·양악 148 · 리프팅·피부 148 · 눈·코 115. 최근 3개월: 고압산소치료기 도입(회복관리), 프리저베 도입, 코성형 협진 인터뷰, 중년 눈성형, 안면거상 | supporters/src/data/news.json |
| 공식 홈페이지 커버리지 (Codex 평가) | 홈페이지가 강한 것: 회복·주의사항 상세, 의료진 이력. 홈페이지에 없는 것: 상담 질문 체크리스트, 회복 일정 표, 비용 구성 항목, 마취 선택 기준, 검진 일정 | 비교평가 §11, Astra 개선안 §12 | | 공식 홈페이지 커버리지 (Codex 평가) | 홈페이지가 강한 것: 회복·주의사항 상세, 의료진 이력. 홈페이지에 없는 것: 상담 질문 체크리스트, 회복 일정 표, 비용 구성 항목, 마취 선택 기준, 검진 일정 | 비교평가 §11, Astra 개선안 §12 |

View File

@ -13,7 +13,7 @@ from openpyxl.utils import get_column_letter
ROOT = os.path.dirname(os.path.dirname(os.path.abspath(__file__))) ROOT = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))
QUESTIONS = os.path.join(ROOT, "scripts", "question_bank_viewclinic.json") QUESTIONS = os.path.join(ROOT, "scripts", "question_bank_viewclinic.json")
OUT = os.path.join(ROOT, "docs", "reports", "Viewclinic_QB_Results_TOP50.xlsx") OUT = os.path.join(ROOT, "docs", "reports", "viewclinic", "03_question_bank", "Viewclinic_QB_Results_TOP50.xlsx")
INK = "0A1128" INK = "0A1128"
VIOLET = "4F1DA1" VIOLET = "4F1DA1"

View File

@ -6,7 +6,7 @@ import time
ROOT = os.path.dirname(os.path.dirname(os.path.abspath(__file__))) ROOT = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))
QUESTIONS = os.path.join(ROOT, "scripts", "question_bank_viewclinic.json") QUESTIONS = os.path.join(ROOT, "scripts", "question_bank_viewclinic.json")
OUT_MD = os.path.join(ROOT, "docs", "reports", "Viewclinic_QB_Results_Combined.md") OUT_MD = os.path.join(ROOT, "docs", "reports", "viewclinic", "03_question_bank", "Viewclinic_QB_Results_Combined.md")
CAT_LABEL = { CAT_LABEL = {
"A": "A. 브랜드 직접", "B": "B. 위치·운영", "C": "C. 지역 추천·비교", "A": "A. 브랜드 직접", "B": "B. 위치·운영", "C": "C. 지역 추천·비교",

View File

@ -229,7 +229,7 @@ def summarize(engine):
"| 병원 | 언급 질문 수 | 1순위 등장 수 |", "|---|---|---|"] "| 병원 | 언급 질문 수 | 1순위 등장 수 |", "|---|---|---|"]
for name, (cnt, first) in sorted(freq.items(), key=lambda x: -x[1][0])[:15]: for name, (cnt, first) in sorted(freq.items(), key=lambda x: -x[1][0])[:15]:
lines.append(f"| {name} | {cnt} | {first} |") lines.append(f"| {name} | {cnt} | {first} |")
out_md = os.path.join(ROOT, "docs", "reports", f"Viewclinic_QB_{engine}_results.md") out_md = os.path.join(ROOT, "docs", "reports", "viewclinic", "03_question_bank", f"Viewclinic_QB_{engine}_results.md")
open(out_md, "w").write("\n".join(lines) + "\n") open(out_md, "w").write("\n".join(lines) + "\n")
print(f"저장: {out_md}") print(f"저장: {out_md}")

View File

@ -1,7 +1,7 @@
/** /**
* AI Discovery . * AI Discovery .
* Hero.tsx의 ·· , ABMR + AI 2 . * Hero.tsx의 ·· , ABMR + AI 2 .
* 시안: docs/reports/ai_discovery_landing.html ( ) * 시안: docs/reports/landing/ai_discovery_landing.html ( )
*/ */
import { Link } from 'react-router'; import { Link } from 'react-router';
import { motion } from 'motion/react'; import { motion } from 'motion/react';

View File

@ -1,6 +1,6 @@
/** /**
* /discovery AI Discovery(AEO/GEO) . * /discovery AI Discovery(AEO/GEO) .
* 시안: docs/reports/ai_discovery_landing.html (2026-08-31 ) * 시안: docs/reports/landing/ai_discovery_landing.html (2026-08-31 )
* *
* 원칙: 점수·· %· * 원칙: 점수·· %·
* scoreDiscovery(AEO_GEO_RUBRIC, DISCOVERY_VIEWCLINIC) . * scoreDiscovery(AEO_GEO_RUBRIC, DISCOVERY_VIEWCLINIC) .