feat: 법무법인 태하 AI Discovery 케이스 (68점/B) + 기준표 업종 중립화 + 결과 레지스트리 분리

- 선정: 네이버 '마약 변호사' 파워링크 1위 광고주. 랜딩 taehadrug.com + 메인 taehalaw.com 실측
- 핵심 발견: 메인 도메인 가비아 WAF가 GPTBot·OAI-SearchBot 403 차단, 도메인 6개·전화번호 4종 엔티티 분산, canonical http://
- 기준표 D1/B2/B3/C7 라벨을 병의원·법률 공용으로 (강남언니/로톡, MedicalClinic/LegalService, Physician/Attorney)
- src/data/discoveryResults.ts 레지스트리 신설, /discovery/taeha
- INFINITH 덱 13장 + PDF

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
Haewon Kam 2026-08-28 11:40:01 +09:00
parent 65e6a19ec1
commit 6a38b19ddd
9 changed files with 396 additions and 24 deletions

View File

@ -46,8 +46,8 @@
| A6 | Bing 색인 (ChatGPT 경로) | 3 | 벤더 | 직접 | 수동 | 색인 + IndexNow |
| A7 | 응답 속도·크롤 예산 | 1 | 추정 | 직접 | 자동 | TTFB < 0.5s, HTML < 300KB |
| B1 | JSON-LD 문법 유효성 | 3 | 실측 | 직접 | 자동 | 전부 유효 + @graph 연결 |
| B2 | MedicalClinic / LocalBusiness | 5 | 학술 | 직접 | 자동 | + openingHours·medicalSpecialty·geo |
| B3 | Physician 스키마 | 3 | 학술 | 직접 | 자동 | 자격·소속·sameAs 포함 |
| B2 | 업종 엔티티 스키마 (MedicalClinic / LegalService) | 5 | 학술 | 직접 | 자동 | + openingHours·medicalSpecialty·geo |
| B3 | 전문가 스키마 (Physician / Attorney) | 3 | 학술 | 직접 | 자동 | 자격·소속·sameAs 포함 |
| B4 | NAP 사이트 내 일관성 | 3 | 실측 | 직접 | 자동 | 단일 표기 |
| B5 | sameAs 연결 | 2 | 학술 | 직접 | 자동 | 5개 이상 (SNS+버티컬+지도) |
| B6 | canonical·중복 제거 | 2 | 실측 | 직접 | 자동 | 있음 + 파라미터 정리 |
@ -58,9 +58,9 @@
| C4 | 구체 수치 (가격·시간·회복) | 4 | 학술 | 직접 | 반자동 | 시술별 가격대·시간·회복 표기 |
| C5 | 표·비교 구조 | 2 | 벤더 | 직접 | 자동 | HTML 표 다수 |
| C6 | 신선도 신호 | 3 | 학술 | 직접 | 자동 | 3개월 이내 + dateModified |
| C7 | 의료진 E-E-A-T | 3 | 학술 | 직접 | 반자동 | + 논문·학회·수상 + Physician 스키마 |
| C7 | 전문가 E-E-A-T (의료진 / 변호사) | 3 | 학술 | 직접 | 반자동 | + 논문·학회·수상 + Physician 스키마 |
| C8 | 패시지 자기완결성 | 2 | 학술 | 직접 | 수동 | 80% 이상 |
| D1 | 강남언니 프로필 | 6 | 실측 | 직접 | 수동 | + 의료진·가격 갱신 3개월 이내 |
| D1 | 업종 버티컬 프로필 (강남언니 / 로톡) | 6 | 실측 | 직접 | 수동 | + 의료진·가격 갱신 3개월 이내 |
| D2 | Google 비즈니스 프로필 | 4 | 실측 | 직접 | 수동 | 소유·리뷰 응답·게시물 활성 |
| D3 | 오픈웹 언급 | 4 | 학술 | 영향 | 반자동 | 다수 오픈 도메인 일관 언급 |
| D4 | 표면 간 NAP 완전 일치 | 3 | 실측 | 직접 | 수동 | 완전 일치 |

Binary file not shown.

Binary file not shown.

View File

@ -0,0 +1,213 @@
"""
법무법인 태하 AI Answer Readiness Report 덱 빌드 (INFINITH Deck 규격)
python3 docs/reports/build_taeha_deck.py docs/reports/Taeha_AI_Answer_Readiness_Report.pptx
"""
import sys
sys.path.insert(0, "/Users/haewonkam/.claude/skills/infinith-deck/scripts")
from ifd import Deck
OUT = sys.argv[1] if len(sys.argv) > 1 else "Taeha_AI_Answer_Readiness_Report.pptx"
d = Deck()
# 01 Cover
d.cover(
eyebrow="AI DISCOVERY · AEO / GEO AUDIT v1.0 · LEGAL",
title_lines=["AI Answer", "Readiness Report."],
subtitle="법무법인 태하 · taehadrug.com · 네이버 \"마약 변호사\" 파워링크 1위 · 2026. 08. 28",
meta_right="AI Discovery Report · 2026",
)
# 02 Executive summary
s = d.slide(eyebrow="Executive Summary",
title="잘 만든 사이트를 ", title_accent="ChatGPT가 못 읽는다",
lede=["36개 항목 중 31개를 실측했고, 오너 계정이 필요한 5개는 점수 분모에서 제외했습니다.",
"구조화·콘텐츠·위생은 상위권. 메인 도메인의 WAF 차단과 도메인 6개 분산이 총점을 끌어내립니다."],
section="Summary")
k1, k2, k3, k4 = s.cards4(y=s.band_y, h=3.4)
k1.kpi("68 / 100", "AI ANSWER READINESS", "등급 B · 60 / 88점")
k2.kpi("87%", "F · 기술 위생", "alt 누락 0 · HTML 274KB")
k3.kpi("65%", "C · 인용 가능 콘텐츠", "FAQ 14문항 · 전관 경력 텍스트")
k4.kpi("403", "메인 도메인 → GPTBot", "taehalaw.com WAF가 AI 검색봇 차단")
# 03 What AI sees (dark)
s = d.slide(eyebrow="What AI Sees · 진단의 결론",
title="엔티티가 6개로 ", title_accent="쪼개져 있다", dark=True, section="Findings")
L, R = s.cards2(y=s.band_y)
L.chip("정상", "good").rows([
("마약 사이트 구조화 우수", "JSON-LD 3블록 전부 유효. LegalService·Attorney·FAQPage·Breadcrumb가 @graph로 연결."),
("전관 경력이 텍스트로 있다", "지청장·판사·부장검사 역임이 H3로 노출. AI가 읽을 수 있는 권위 신호."),
("FAQ 14문항, 실제 질문형", "\"초범인데도 실형이 나올 수 있나요?\" 같은 의뢰인 언어 그대로. FAQPage 스키마 병행."),
])
R.chip("치명", "critical").rows([
("메인 도메인이 ChatGPT를 차단", "taehalaw.com 가비아 WAF가 GPTBot·OAI-SearchBot을 403으로. 브라우저·Perplexity는 200."),
("도메인 6개, 전화번호 4종", "마약·형사·이혼·군형법·학폭 사이트가 따로. 콜트래킹 번호와 안심번호가 전부 다름."),
("canonical이 http://, 경로 불일치", "메인 canonical http://taehadrug.com/. 성공사례 canonical이 실제 URL과 다름."),
])
# 04 Scorecard
s = d.slide(eyebrow="Scorecard · 6 Categories",
title="카테고리별 점수와 ", title_accent="검증 범위",
lede="점수는 검증된 항목만으로 정규화했습니다. 미검증 항목을 확인하면 총점이 바뀔 수 있습니다.",
section="Scorecard")
W, Rail = s.cards2(y=s.band_y, split=0.66)
W.grid(
headers=["카테고리", "배점", "획득", "검증", "판정"],
col_w=[4.6, 1.3, 2.0, 1.4, 1.6],
rows=[
["A · AI 크롤러 접근성", "20", "15.0 / 17", "6 / 7", "양호"],
["B · 엔티티 식별·구조화", "20", "13.7 / 20", "7 / 7", "양호"],
["C · 답변 인용 가능 콘텐츠", "25", "16.3 / 25", "8 / 8", "양호"],
["D · AI 인용 표면 확보", "20", "10.7 / 19", "5 / 6", "보완"],
["E · AI 가시성 측정 인프라", "10", "0 / 2", "1 / 4", "미설치"],
["F · 기술 위생", "5", "4.3 / 5", "4 / 4", "우수"],
],
tones=[[None, None, None, None, "good"], [None, None, None, None, "good"],
[None, None, None, None, "good"], [None, None, None, None, "warning"],
[None, None, None, None, "critical"], [None, None, None, None, "info"]],
row_h=0.62,
)
Rail.title("읽는 법").bullets([
"획득 분모는 검증 항목의 배점 합. E는 미검증 3개라 분모가 2점뿐.",
"총점 60 / 88 = 68점, 등급 B. 뷰성형외과 48점과 20점 차이.",
"A가 88%인 이유: 마약 사이트는 열려 있지만 메인 도메인 WAF 차단으로 A2 감점.",
])
# 05 A 접근성 (dark)
s = d.slide(eyebrow="A · Access & Crawlability · 88%",
title="마약 사이트는 열려 있고, ", title_accent="메인은 막혀 있다", dark=True, section="A · Access")
L, R = s.cards2(y=s.band_y)
L.chip("taehadrug.com · 정상", "good").rows([
("A1 검색용 AI 봇 허용", "robots.txt User-agent * Allow /. 12종 UA로 실제 GET, 전부 200."),
("A4 · A5 정합·sitemap", "http·www 변형 전부 301 수렴. sitemap 326개 URL, lastmod 2026-08-06."),
("A7 속도·무게", "TTFB 0.31s, 초기 HTML 274KB. 기준 300KB 이내."),
])
R.chip("taehalaw.com · 차단", "critical").rows([
("A2 WAF가 AI 검색봇 차단", "GPTBot → errdoc.gabia.io/403.html, OAI-SearchBot → modsecurity.html로 302."),
("결과", "ChatGPT 검색은 \"법무법인 태하\" 메인 사이트를 읽지 못한다. Perplexity는 읽는다."),
("A6 Bing 색인 (미검증)", "ChatGPT 검색은 Bing 인덱스에 의존. Webmaster 등록 여부는 계정 확인 필요."),
])
# 06 B 엔티티
s = d.slide(eyebrow="B · Entity & Structured Data · 68%",
title="스키마는 좋은데 ", title_accent="도메인끼리 서로 모른다", section="B · Entity")
L, R = s.cards2(y=s.band_y)
L.chip("우수", "info").rows([
("B1 JSON-LD 전부 유효", "Organization·WebSite·LegalService×4·WebPage·Breadcrumb·FAQPage가 @graph로 연결."),
("B5 sameAs 6개", "네이버 블로그·Instagram·YouTube·카카오채널·네이버 지도·Google 지도."),
("B2 · B3 LegalService·Attorney", "address·geo·areaServed 있음. Attorney 2명 name·jobTitle·knowsAbout."),
])
R.chip("보완", "warning").rows([
("B6 canonical 오류", "http:// 지정. 성공사례 canonical /success-story/ vs 실제 /success/success_story/."),
("B3 변호사 6명 중 2명만 구조화", "전관 경력(지청장·판사·부장검사)이 스키마에 없음. openingHours 없음."),
("B4 전화 2종, B7 단일 언어", "taehadrug 1533-2403 / taehalaw 1533-1403. hreflang 없음."),
])
# 07 C 콘텐츠 (dark)
s = d.slide(eyebrow="C · Answer-Ready Content · 65%",
title="FAQ와 사례는 있고, ", title_accent="정의문과 표가 없다", dark=True, section="C · Content")
L, R = s.cards2(y=s.band_y)
L.chip("우수", "good").rows([
("C2 FAQ 14문항 + FAQPage", "\"마약 양이 적어도 구속될 수 있어요?\" 등 의뢰인 질문 그대로 H3."),
("C7 전관 경력 텍스트", "지청장·판사·부장검사 역임이 H3로 노출. Attorney 스키마 병행."),
("C8 · C6 사례 자기완결·갱신", "성공사례 H2가 [결과] 사건 유형 형태. sitemap 3주 전 갱신."),
])
R.chip("보완", "warning").rows([
("C1 정의문 없음", "H1 \"마약 사건엔 태하가 답입니다\"는 슬로건. 누구·어디·무엇 정의문 없음."),
("C5 HTML 표 없음", "\"마약사건 처벌현황\"이 표가 아닌 이미지·블록. 형량 비교표가 있어야 인용된다."),
("C4 · C3 수치·제목", "수임료 범위·처리 기간 수치 없음. 첫 H2가 \"#필로폰 #MDMA\" 해시태그."),
])
# 08 D 표면 / E 측정
s = d.slide(eyebrow="D · Surfaces / E · Measurement",
title="광고는 1위, ", title_accent="브랜드 검색은 경쟁사 차지", section="D · Surfaces")
L, R = s.cards2(y=s.band_y)
L.chip("D · 표면 56%", "warning").rows([
("D4 전화번호 4종", "1533-2403 / 1533-1403 / 0507-1495-4404 / 050-71496-4404. NAP가 안 맞는다."),
("D2 GBP 본점 평점 미표시", "수원분사무소는 5.0. 브랜드 검색에 법무법인YK·로엘 스폰서가 상단 노출."),
("D1 · D5 로톡·플레이스", "로톡은 변호사 개인 프로필만 확인. 플레이스 리뷰 220건, 분사무소 5곳."),
])
R.chip("E · 측정 0%", "critical").rows([
("E1 크롤러 로그", "Apache 직접 호스팅. AI 봇 히트 추출과 IP 검증 파이프라인 없음."),
("E2 GA4 AI 유입 채널", "광고에 utm_source=naver는 쓰고 있음. AI 채널그룹은 미확인, 계정 접근 필요."),
("E4 기준선 스팟체크", "미실시. \"마약 변호사\", \"필로폰 초범 집행유예\" 질의 10개 × 5회가 전제."),
])
# 09 Action plan
s = d.slide(eyebrow="Action Plan",
title="1일 안에 고칠 것과 ", title_accent="4주 안에 만들 것", section="Action Plan")
a, b, c = s.cards3(y=s.band_y)
a.chip("P0 · 1일~1주", "critical").title("접근·엔티티·NAP").bullets([
"가비아 WAF에서 GPTBot·OAI-SearchBot·Claude-SearchBot 화이트리스트.",
"canonical https 교정, 6개 도메인 sameAs 상호 연결.",
"대표번호 1개로 홈페이지 6개·플레이스·Google 지도 통일.",
"메인 taehalaw.com에 LegalService + Attorney 전원 스키마.",
])
b.chip("P1 · 4주 내", "warning").title("콘텐츠 구조·측정").bullets([
"각 도메인 첫 단락에 정의문. 메인 H1을 서술형으로.",
"성공사례 결과 분포·처리 기간을 HTML 표로.",
"GA4 AI 채널그룹, 서버로그 IP 검증, GSC·Bing 등록, 기준선 측정.",
])
c.chip("P2 · 지속", "good").title("신선도·시딩").bullets([
"성공사례에 datePublished·dateModified 마크업.",
"YouTube @with_lawyer 영상을 사이트 글로 전사.",
"티스토리·언론 기고로 naver.com 외 언급 도메인 확보.",
"분기 1회 반복 측정. 언급률과 신뢰구간으로만 보고.",
])
# 10 Roadmap (dark)
s = d.slide(eyebrow="Roadmap · 8 Weeks",
title="8주 안에 ", title_accent="B에서 A로", dark=True, section="Roadmap")
s.stats3([
("W1–2", "WAF 해제·canonical·sameAs·NAP 통일.\n기준선 스팟체크 1회."),
("W3–6", "정의문·HTML 표·메인 H1 재설계.\n측정 인프라 설치."),
("W7–8", "재진단. 미검증 5개 반영해\n총점 재산정."),
], y=s.band_y + 0.6)
# 11 What we don't sell
s = d.slide(eyebrow="What We Don't Sell · 정직성 규약",
title="근거 없는 것은 ", title_accent="팔지 않는다", section="Integrity")
a, b, c = s.cards3(y=s.band_y)
a.icon_square().title("만들지 않는 것").bullets([
"llms.txt. Google 공식 효과 0, 채택률 0.13%, 서버 로그에 요청 자체가 없음.",
"도메인 통합 강요. 분야별 랜딩은 광고 전환에 유리하다. sameAs·NAP로 묶는 쪽이 싸다.",
])
b.icon_square().title("약속하지 않는 것").bullets([
"\"스키마 넣으면 인용됩니다\". 태하는 스키마가 좋은데도 ChatGPT가 메인을 못 읽는다.",
"순위·노출 보장. LLM 답변은 동일 질문에도 10~34% 흔들림.",
])
c.icon_square().title("측정 규율").bullets([
"단발 조회로 성과 보고 금지. 반복 측정과 신뢰구간만.",
"답변엔진 UI 자동 조회 금지. OpenAI·Perplexity 약관 위반.",
"AI 유입은 항상 하한값. 35~70%가 Direct로 유실.",
])
# 12 Method
s = d.slide(eyebrow="Method · AEO / GEO Rubric v1.0",
title="36개 항목, 100점, ", title_accent="근거 등급을 명시", section="Method")
a, b, c = s.cards3(y=s.band_y)
a.icon_square().title("채점 방식").bullets([
"항목별 0~3 레벨 × 배점. 미검증은 0점이 아니라 분모 제외.",
"A 20 · B 20 · C 25 · D 20 · E 10 · F 5.",
"등급 A 81+ · B 61~80 · C 41~60 · D 40 이하.",
])
b.icon_square().title("법률 업종 적용").bullets([
"업종 스키마: LegalService · 전문가 스키마: Attorney.",
"버티컬 표면: 로톡·로앤굿 (병의원의 강남언니 자리).",
"E-E-A-T: 전관 경력·전문분야 등록을 텍스트로.",
])
c.icon_square().title("항목마다 붙는 태그").bullets([
"근거 등급: 실측 / 학술 / 벤더 / 추정.",
"통제 가능성: 직접 / 영향 / 불가.",
"채점 방식: 자동 / 반자동 / 수동. 자동 항목은 Edge Function으로 이식.",
])
# 13 Closing
d.closing(eyebrow="Next Step",
title_lines=["WAF 한 줄이 ", "총점을 가르고 있습니다."],
lede="메인 도메인에서 AI 검색봇을 허용하는 데 1일. 그 다음 canonical·sameAs·전화번호 통일까지 1주.",
cta_primary="P0 착수하기 →", cta_secondary="리포트 페이지 보기",
contact="infinith.kr · hello@infinith.kr")
d.save(OUT)
print("saved", OUT)

View File

@ -180,25 +180,25 @@ export const AEO_GEO_RUBRIC: Rubric = {
{
id: 'B2',
category: 'entity',
name: 'MedicalClinic / LocalBusiness 스키마',
rationale: '엔티티 식별을 돕는 위생 조치. 인과 증거는 없으나 name·address·telephone·openingHours·medicalSpecialty를 기계가 읽게 한다.',
name: '업종 엔티티 스키마 (MedicalClinic / LegalService / LocalBusiness)',
rationale: '엔티티 식별을 돕는 위생 조치. 인과 증거는 없으나 name·address·telephone·openingHours·전문분야(medicalSpecialty / areaServed)를 기계가 읽게 한다.',
weight: 5,
evidenceGrade: 'academic',
control: 'direct',
method: 'auto',
howToCheck: '@type MedicalClinic|MedicalBusiness|LocalBusiness 존재 + 필수 속성 4개',
levels: L('없음', 'Organization만', 'MedicalClinic + 주소·전화', '+ openingHours·medicalSpecialty·geo'),
howToCheck: '@type MedicalClinic|LegalService|LocalBusiness 존재 + 필수 속성 4개',
levels: L('없음', 'Organization만', '업종 타입 + 주소·전화', '+ openingHours·전문분야·geo'),
},
{
id: 'B3',
category: 'entity',
name: 'Physician 스키마 (의료진)',
rationale: '"누가 수술하나"는 병의원 질의의 핵심. 의사 이름·전문의 자격을 구조화하면 E-E-A-T 엔티티가 된다.',
name: '전문가 스키마 (Physician / Attorney)',
rationale: '"누가 담당하나"는 병의원·로펌 질의의 핵심. 의사·변호사 이름과 자격·경력을 구조화하면 E-E-A-T 엔티티가 된다.',
weight: 3,
evidenceGrade: 'academic',
control: 'direct',
method: 'auto',
howToCheck: '@type Physician + name·medicalSpecialty·worksFor',
howToCheck: '@type Physician|Attorney + name·전문분야·worksFor',
levels: L('없음', '이름만', '전문분야 포함', '자격·소속·sameAs 포함'),
},
{
@ -326,14 +326,14 @@ export const AEO_GEO_RUBRIC: Rubric = {
{
id: 'C7',
category: 'content',
name: '의료진 E-E-A-T',
rationale: '전문의 자격·경력·학회·수상이 텍스트로 존재해야 AI가 "믿을 만한 출처"로 판단할 근거가 생긴다. 이미지 안의 글자는 안 읽힌다.',
name: '전문가 E-E-A-T (의료진 / 변호사)',
rationale: '전문의 자격·경력·학회·수상, 변호사의 전관 경력·전문분야 등록이 텍스트로 존재해야 AI가 "믿을 만한 출처"로 판단할 근거가 생긴다. 이미지 안의 글자는 안 읽힌다.',
weight: 3,
evidenceGrade: 'academic',
control: 'direct',
method: 'semi',
howToCheck: '의료진 페이지 텍스트에 전문의·경력·학회 명시 여부',
levels: L('의료진 정보 없음', '이름·사진만', '전문의·경력 텍스트', '+ 논문·학회·수상 + Physician 스키마'),
howToCheck: '전문가 페이지 텍스트에 자격·경력 명시 여부',
levels: L('전문가 정보 없음', '이름·사진만', '자격·경력 텍스트', '+ 논문·학회·수상 + 전문가 스키마'),
},
{
id: 'C8',
@ -352,14 +352,14 @@ export const AEO_GEO_RUBRIC: Rubric = {
{
id: 'D1',
category: 'surface',
name: '강남언니 프로필',
rationale: '2026-08 실측: 병의원 질의는 강남언니(ai-input=yes 명시)·닥터나우·마이닥터가 AI 인용을 100% 장악. 여기 없으면 AI에겐 없는 병원.',
name: '업종 버티컬 프로필 (병의원: 강남언니 / 법률: 로톡)',
rationale: '2026-08 실측: 병의원 질의는 강남언니(ai-input=yes 명시)·닥터나우가 AI 인용을 장악. 법률은 로톡·로앤굿 등 변호사 디렉터리가 같은 역할. 여기 없으면 AI에겐 없는 업체.',
weight: 6,
evidenceGrade: 'measured',
control: 'direct',
method: 'manual',
howToCheck: '강남언니 병원 페이지 존재·시술 등록 수·후기 수·최근 갱신',
levels: L('미등록', '등록, 시술 3개 미만', '시술 다수·후기 활성', '+ 의료진·가격 갱신 3개월 이내'),
howToCheck: '버티컬 프로필 존재·등록 항목 수·후기 수·최근 갱신 (병원 페이지 / 로펌·변호사 프로필)',
levels: L('미등록', '등록, 항목 3개 미만', '항목 다수·후기 활성', '+ 전문가·가격 갱신 3개월 이내'),
},
{
id: 'D2',

View File

@ -0,0 +1,12 @@
/**
* AI Discovery 결과 레지스트리. /discovery/:id 가 여기서 찾는다.
* 새 업체는 결과 파일을 만들고 여기에 한 줄 추가한다.
*/
import type { DiscoveryResult } from '../types/discovery';
import { DISCOVERY_VIEWCLINIC } from './discovery_viewclinic';
import { DISCOVERY_TAEHA } from './discovery_taeha';
export const DISCOVERY_RESULTS: Record<string, DiscoveryResult> = {
viewclinic: DISCOVERY_VIEWCLINIC,
taeha: DISCOVERY_TAEHA,
};

150
src/data/discovery_taeha.ts Normal file
View File

@ -0,0 +1,150 @@
/**
* 법무법인 태하 (taehadrug.com) AEO/GEO 진단 결과
* 선정 근거: 네이버 "마약 변호사" 검색 파워링크 1위 광고주 (2026-08-28)
* 실측 대상: 광고 랜딩 taehadrug.com(마약 전용) + 메인 www.taehalaw.com
* 미검증 항목은 'unverified'. 오너 계정(GA4·GSC·Bing·서버로그) 접근이 필요하다.
*/
import type { DiscoveryResult } from '../types/discovery';
export const DISCOVERY_TAEHA: DiscoveryResult = {
id: 'taeha',
clinicName: '법무법인 태하',
url: 'https://taehadrug.com',
industry: '로펌 · 마약 형사 (강남 테헤란로, 6개 분사무소)',
auditedAt: '2026-08-28',
rubricVersion: '1.0',
conditions: [
'선정: 네이버 "마약 변호사" 검색 파워링크 1위 광고주. 광고 랜딩은 마약 전용 도메인 taehadrug.com',
'실측 대상: taehadrug.com 메인 + /success/success_story/, www.taehalaw.com 메인 + /member/page. JS 미실행 HTML 기준',
'크롤러 접근성: robots.txt 파싱 + 12개 AI 봇 UA 실제 GET 요청 (두 도메인 모두)',
'외부 표면: Google 지도·네이버 플레이스·로톡은 공개 페이지 실측. GBP 소유권·GA4·GSC·Bing·서버로그는 오너 접근 필요 → 미검증, 분모 제외',
'태하는 도메인이 6개 이상(taehalaw · taehadrug · taehacri · taehadivorce · taehamil · taehaschool)으로 분산돼 있어 엔티티 판단은 메인 도메인과 교차 확인',
],
results: [
// A. 접근성
{ criterionId: 'A1', level: 3, evidence: 'taehadrug.com robots.txt: User-agent * Allow /. 12개 AI 봇 UA 전부 200', source: 'https://taehadrug.com/robots.txt' },
{ criterionId: 'A2', level: 1, evidence: '메인 도메인 www.taehalaw.com(가비아 호스팅)의 ModSecurity WAF가 GPTBot·OAI-SearchBot을 403으로 차단(errdoc.gabia.io/modsecurity.html로 302). ChatGPT 검색은 메인 사이트를 읽지 못함. taehadrug.com(Apache 별도 호스팅)은 정상', source: 'GPTBot → 302 http://errdoc.gabia.io/403.html / OAI-SearchBot → 302 https://errdoc.gabia.io/modsecurity.html' },
{ criterionId: 'A3', level: 3, evidence: '서버 렌더링. JS 미실행 HTML에서 본문 18,352자 추출 (메인), 성공사례 4,578자' },
{ criterionId: 'A4', level: 3, evidence: 'http://, http://www, https://www 전부 301로 https://taehadrug.com/ 수렴' },
{ criterionId: 'A5', level: 3, evidence: 'robots.txt에 sitemap 선언, 200 응답, URL 326개, lastmod 최신 2026-08-06' },
{ criterionId: 'A6', level: 'unverified', evidence: 'Bing Webmaster Tools 등록 여부는 오너 계정 접근 필요' },
{ criterionId: 'A7', level: 3, evidence: 'TTFB 0.31s, 초기 HTML 274KB (기준 300KB 이내)' },
// B. 엔티티
{ criterionId: 'B1', level: 3, evidence: 'JSON-LD 3블록 전부 유효. @graph로 Organization·WebSite·LegalService×4·WebPage·BreadcrumbList·FAQPage 연결' },
{ criterionId: 'B2', level: 2, evidence: 'LegalService에 name·telephone·address·geo·areaServed(서울·수원·인천 등) 존재. openingHoursSpecification 없음' },
{ criterionId: 'B3', level: 2, evidence: 'Organization.employee에 Attorney 2명(채의준 대표변호사, 최승현) name·jobTitle·knowsAbout. 페이지에 소개된 변호사 6명 중 2명만 구조화, 전관 경력(지청장·판사·부장검사 역임)은 스키마에 없음' },
{ criterionId: 'B4', level: 2, evidence: '주소는 "테헤란로 522 홍우빌딩 14층" 단일 표기. 전화는 사이트별 상이: taehadrug 1533-2403 / taehalaw 1533-1403 (콜트래킹 번호 2종)' },
{ criterionId: 'B5', level: 3, evidence: 'Organization.sameAs 6개: 네이버 블로그·Instagram·YouTube·카카오채널·네이버 지도·Google 지도' },
{ criterionId: 'B6', level: 1, evidence: 'canonical이 http://taehadrug.com/ (https 아님). 성공사례 페이지 canonical은 /success-story/인데 실제 URL은 /success/success_story/ → 불일치. 메인 taehalaw.com은 모든 하위 페이지 canonical이 루트를 가리킴' },
{ criterionId: 'B7', level: 1, evidence: 'hreflang 없음, lang=ko 단일 언어. 외국인 의뢰인 페이지 없음' },
// C. 콘텐츠
{ criterionId: 'C1', level: 1, evidence: 'H1 "실제사례로 입증된 프리미엄 전략, 마약 사건엔 태하가 답입니다" 슬로건형. "법무법인 태하는 서울 강남 테헤란로에 있는 마약 형사 전문 로펌으로 …" 형태의 정의문 없음' },
{ criterionId: 'C2', level: 3, evidence: 'FAQ 섹션 + FAQPage 스키마 14문항 ("초범인데도 실형이 나올 수 있나요?", "마약 양이 적어도 구속될 수 있어요?" 등 실제 질문형)' },
{ criterionId: 'C3', level: 2, evidence: 'H1 1개. H2 8개가 서술형(3STEP 솔루션, 맞춤감형 전략). 단 첫 H2가 "#필로폰 #MDMA #대마 #밀수" 해시태그 라벨. 메인 taehalaw.com H1은 "변호사추천 변호사상담" 키워드형 + 영문 H1 2개 추가' },
{ criterionId: 'C4', level: 2, evidence: '성공사례 페이지에 사건 유형별 결과(기소유예·집행유예·불송치·벌금형)가 H2로 구조화. 단 수임료 범위·사건 처리 기간·건수 같은 수치 표기 없음' },
{ criterionId: 'C5', level: 0, evidence: 'HTML <table> 없음. "마약사건 처벌현황" 메뉴는 이미지·텍스트 블록' },
{ criterionId: 'C6', level: 2, evidence: 'sitemap lastmod 2026-08-06(3주 전), 성공사례 지속 추가. 단 dateModified·datePublished 마크업 없음' },
{ criterionId: 'C7', level: 3, evidence: '"지청장 역임 임양운", "판사 역임 최승현", "부장검사 역임 이선녀" 등 전관 경력이 H3 텍스트로 노출. Attorney 스키마 병행' },
{ criterionId: 'C8', level: 2, evidence: '성공사례 각 H2가 "[집행유예] 필로폰 수수·투약 동종 전력 2회, 항소심 집행유예" 형태로 자기완결적. 메인 H2 "3STEP 솔루션"은 단독으로는 주체 불명' },
// D. 표면
{ criterionId: 'D1', level: 2, evidence: '로톡에 소속 변호사 개인 프로필 확인(김진형 5956, 김유석 8918). 로펌 단위 프로필·전체 변호사 등록 여부는 미확인. 로톡 robots.txt는 GPTBot만 차단, 검색봇은 허용', source: 'https://www.lawtalk.co.kr/directory/profile/5956-김진형' },
{ criterionId: 'D2', level: 2, evidence: 'Google 지도에 서울 본점(24시간 영업, 050-71496-4404, 웹사이트)과 수원분사무소(5.0) 등록. 서울 본점 평점 미표시. 브랜드명 검색에 경쟁사(법무법인YK·로엘) 스폰서 광고가 상단 노출' },
{ criterionId: 'D3', level: 2, evidence: 'YouTube @with_lawyer, 네이버TV·클립(@taehalaw), Instagram 운영. 언론보도 페이지 존재. 티스토리·외부 매체 언급은 미집계' },
{ criterionId: 'D4', level: 0, evidence: '전화번호가 표면마다 다름: taehadrug 1533-2403 / taehalaw 1533-1403 / 네이버 플레이스 0507-1495-4404 / Google 050-71496-4404. 콜트래킹 안심번호가 NAP 일치를 깨뜨림' },
{ criterionId: 'D5', level: 2, evidence: '네이버 플레이스 서울주사무소 방문자리뷰 220건, 24시간 연중무휴, 분사무소 5곳 등록. 홈페이지 연결은 학폭 사이트(taehaschool.com)로 걸린 광고 확인, 마약 사이트 연결은 미확인' },
{ criterionId: 'D6', level: 'unverified', evidence: 'Wikidata 조회 미실시' },
// E. 측정
{ criterionId: 'E1', level: 'unverified', evidence: '서버 로그 접근 필요 (Apache 직접 호스팅, Cloudflare 미사용)' },
{ criterionId: 'E2', level: 'unverified', evidence: 'GA4 접근 필요. 광고 링크에 utm_source=naver 파라미터 사용 중이라 채널그룹 관리 습관은 있음' },
{ criterionId: 'E3', level: 'unverified', evidence: 'GSC 접근 필요' },
{ criterionId: 'E4', level: 0, evidence: '기준선 스팟체크 미실시' },
// F. 위생
{ criterionId: 'F1', level: 3, evidence: '이미지 136개 중 alt 누락 0 (메인), 성공사례 56개 중 0' },
{ criterionId: 'F2', level: 2, evidence: 'generator 메타 없음, 자체 제작 사이트. CMS 버전 노출 없음 (보수적으로 2)' },
{ criterionId: 'F3', level: 3, evidence: '초기 HTML 274KB' },
{ criterionId: 'F4', level: 2, evidence: 'viewport meta 존재, 반응형. CWV 미측정' },
],
keyFindings: [
{
title: '마약 전용 사이트는 AI가 읽기 좋게 만들어져 있다',
detail: 'taehadrug.com은 JSON-LD 3블록이 전부 유효하고(LegalService·Attorney·FAQPage·Breadcrumb), FAQ 14문항이 실제 질문형이며, 변호사의 전관 경력이 텍스트로 노출된다. alt 누락 0, HTML 274KB, sitemap 326개 URL이 3주 전 갱신. 뷰성형외과(C 20%)와 달리 콘텐츠 카테고리가 63%다.',
severity: 'good',
},
{
title: '메인 도메인이 ChatGPT를 차단하고 있다',
detail: 'www.taehalaw.com의 가비아 ModSecurity WAF가 GPTBot과 OAI-SearchBot을 403 페이지로 보낸다. 브라우저와 PerplexityBot은 200. 즉 ChatGPT 검색은 "법무법인 태하"의 메인 사이트를 읽지 못하고, 마약 전용 사이트만 본다. 운영자가 모르는 채 걸려 있는 설정일 가능성이 높다.',
severity: 'critical',
},
{
title: '도메인 6개, 전화번호 4종. 엔티티가 쪼개져 있다',
detail: '마약·형사·이혼·군형법·학폭이 각각 별도 도메인이고, 사이트별 콜트래킹 번호(1533-2403 / 1533-1403)와 지도의 안심번호(0507-1495-4404 / 050-71496-4404)가 전부 다르다. 사람에게는 분야별 랜딩이지만 AI에게는 같은 이름의 서로 다른 업체 6개로 읽힌다. sameAs가 도메인 간 상호 연결을 하지 않는다.',
severity: 'critical',
},
{
title: 'canonical이 http://이고 URL과 어긋난다',
detail: 'taehadrug.com 메인 canonical은 http://taehadrug.com/ (https 아님). 성공사례 페이지 canonical은 /success-story/인데 실제 경로는 /success/success_story/. 메인 taehalaw.com은 모든 하위 페이지의 canonical이 루트다. 인용 신호가 잘못된 URL로 흘러간다.',
severity: 'warning',
},
{
title: '브랜드 검색에 경쟁사가 올라탄다',
detail: 'Google 지도에서 "법무법인 태하"를 검색하면 법무법인YK·로엘의 스폰서 리스팅이 상단에 뜬다. 서울 본점 GBP는 평점이 표시되지 않는다. 로톡에는 변호사 개인 프로필만 확인되고 로펌 단위 존재감이 약하다. 네이버 파워링크 1위를 사는 만큼 AI 표면의 방어는 비어 있다.',
severity: 'warning',
},
],
actions: [
{
priority: 'P0',
title: '메인 도메인 WAF에서 AI 검색봇 허용',
detail: '가비아 호스팅 ModSecurity 규칙에서 GPTBot·OAI-SearchBot·Claude-SearchBot·PerplexityBot UA를 화이트리스트. 학습봇을 막고 싶으면 robots.txt로 GPTBot만 Disallow하고 OAI-SearchBot은 연다. 12개 UA로 200 응답 재확인.',
criterionIds: ['A2', 'A1'],
effort: '1일',
},
{
priority: 'P0',
title: 'canonical https 교정 + 도메인 간 sameAs 상호 연결',
detail: 'taehadrug.com canonical을 https://로, 성공사례 canonical을 실제 경로로. taehalaw.com 하위 페이지 canonical을 self-referencing으로. 6개 도메인의 Organization 스키마에 서로의 URL을 sameAs로 넣어 한 엔티티로 묶는다. 메인 taehalaw.com에 LegalService + Attorney 전원 스키마 삽입.',
criterionIds: ['B6', 'B5', 'B2', 'B3'],
effort: '1주',
},
{
priority: 'P0',
title: '전화번호 1개로 통일, 표면 4곳 NAP 정렬',
detail: '대표번호 1개를 정하고 홈페이지 6개·네이버 플레이스·Google 지도 전화를 동일하게. 콜트래킹이 필요하면 스키마 telephone과 지도 등록은 대표번호로, 추적 번호는 화면 버튼에만. Google 본점 리뷰 수집 시작, 로톡 로펌 프로필 정비.',
criterionIds: ['D4', 'D2', 'D1', 'B4'],
effort: '1주',
},
{
priority: 'P1',
title: '정의문 + 수치 + 표 도입',
detail: '각 도메인 첫 단락에 "법무법인 태하는 서울 강남 테헤란로에 본사를 둔 형사 전문 로펌으로, 마약·성범죄·이혼을 다루며 수원·인천·대전·천안·제주 분사무소를 운영한다" 정의문. 성공사례에 사건 처리 기간·결과 분포를 HTML 표로. 메인 H1을 "변호사추천 변호사상담"에서 서술형으로.',
criterionIds: ['C1', 'C4', 'C5', 'C3'],
effort: '2~4주',
},
{
priority: 'P1',
title: '측정 인프라 설치',
detail: 'GA4 커스텀 채널그룹(chatgpt.com·perplexity.ai·gemini.google.com·copilot·claude.ai). Apache access.log에서 AI 봇 히트 추출 + IP 검증. GSC·Bing Webmaster 등록 확인 + IndexNow. "마약 변호사", "필로폰 초범 집행유예" 등 질의 10개 × 5회 기준선 스팟체크.',
criterionIds: ['E1', 'E2', 'E3', 'E4', 'A6'],
effort: '1주',
},
{
priority: 'P2',
title: '신선도 마크업 + 오픈웹 시딩',
detail: '성공사례에 datePublished·dateModified 마크업. YouTube @with_lawyer 영상을 사이트 글로 전사. 네이버 블로그 대신 티스토리·언론 기고로 naver.com 외 언급 도메인 확보. 외국인 의뢰인 대상 영문 페이지가 있다면 hreflang 연결.',
criterionIds: ['C6', 'D3', 'B7'],
effort: '지속',
},
],
notDoing: [
{ item: 'llms.txt 제작', reason: 'Google 공식(2026-06) 효과 0, 채택률 0.13%, 서버 로그에 요청 자체가 없음.' },
{ item: '도메인 통합 강요', reason: '분야별 도메인은 광고 랜딩 전환에 유리할 수 있다. 통합 대신 sameAs·canonical·NAP로 한 엔티티임을 기계에 알리는 쪽이 비용이 적다.' },
{ item: '"스키마 넣으면 AI가 인용합니다" 약속', reason: '태하는 이미 스키마가 좋다. 그런데도 ChatGPT가 메인을 못 읽는다. 스키마는 위생이고, 접근이 먼저다.' },
{ item: '단발 조회로 순위·노출 보고', reason: 'LLM 답변 분산 10~34%. 반복 측정 + 신뢰구간으로만 보고한다.' },
{ item: '네이버 블로그 증량', reason: 'blog.naver.com robots.txt가 AI 크롤링을 전면 금지. 네이버 AI 브리핑은 별도 트랙.' },
],
};

View File

@ -154,6 +154,3 @@ export const DISCOVERY_VIEWCLINIC: DiscoveryResult = {
],
};
export const DISCOVERY_RESULTS: Record<string, DiscoveryResult> = {
viewclinic: DISCOVERY_VIEWCLINIC,
};

View File

@ -3,7 +3,7 @@ import type { ComponentType, ReactNode } from 'react';
import { useParams, Link } from 'react-router';
import { motion } from 'motion/react';
import { AEO_GEO_RUBRIC } from '../data/aeoGeoRubric';
import { DISCOVERY_RESULTS } from '../data/discovery_viewclinic';
import { DISCOVERY_RESULTS } from '../data/discoveryResults';
import { scoreDiscovery, levelToSeverity } from '../lib/discoveryScore';
import type {
ActionPriority,
@ -147,7 +147,7 @@ export default function DiscoveryReportPage() {
<SectionWrapper
id="findings"
title="What AI Sees"
subtitle="AI 답변엔진이 지금 이 병원을 어떻게 읽는지. 진단의 결론"
subtitle="AI 답변엔진이 지금 이 업체를 어떻게 읽는지. 진단의 결론"
>
<div className="grid md:grid-cols-2 gap-5">
{result.keyFindings.map((f, i) => (