Implement ourdigital-presales-seo skill
SKILL.md orchestration (8 gated stages), references (rate_card.yaml, findings_to_service rubric, competitor sets), findings.schema.json contract, and scripts: kg_query.py (generalized KG examination), estimate.py (findings→rate-card 견적 md/xlsx/json), build_deck.py (9-slide branded PPTX), render_pdf.sh (Korean PDF via headless Chrome), plus client_brief.html template. Validated on Sono Hotels & Resorts findings: estimate OD-2026-001 (23-47M KRW) and a 9-slide deck generated cleanly. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -0,0 +1,23 @@
|
||||
# Default competitor benchmark sets (Korean market)
|
||||
|
||||
Used by Stage 3 (KG/entity) when the user doesn't supply competitors. Pick the set
|
||||
matching the prospect's vertical; pass as `--competitors` to `kg_query.py`.
|
||||
|
||||
## hotel_resort (호텔·리조트)
|
||||
- 롯데호텔 (Lotte Hotel) — strong KG, LodgingBusiness type, Korean Wikipedia
|
||||
- 신라호텔 / 호텔신라 (Shilla)
|
||||
- 조선호텔앤리조트 (Josun)
|
||||
- 한화리조트 / 한화호텔앤드리조트 (Hanwha)
|
||||
- 켄싱턴리조트 (Kensington)
|
||||
|
||||
## city_hotel (시티 호텔)
|
||||
- 롯데호텔, 신라호텔, 조선호텔, 글래드호텔, 나인트리
|
||||
|
||||
## condo_membership (콘도·회원권)
|
||||
- 한화리조트, 대명(소노), 한솔오크밸리, 금호리조트
|
||||
|
||||
## benchmark_signals
|
||||
For each competitor record in `findings.json.entity.competitor_benchmark`:
|
||||
`{name, score (KG result_score), type (@type), wikipedia (bool)}`.
|
||||
The benchmark table contrasts the prospect's entity strength/type/Wikipedia
|
||||
presence against these — the core competitive-gap visual in the deck.
|
||||
@@ -0,0 +1,26 @@
|
||||
# Findings → service rubric
|
||||
|
||||
How `estimate.py` maps detected findings (from `findings.json`) to `rate_card.yaml`
|
||||
service lines. The script reads the structured signals below; this file is the
|
||||
human-readable source of truth for the rules.
|
||||
|
||||
| Trigger (signal in findings.json) | Service line(s) | Scope driver |
|
||||
|---|---|---|
|
||||
| `discovery.sitemap_status != 200` OR `discovery.robots_sitemap_declared == false` OR `discovery.discoverable_urls` low vs `estimated_pages` | `technical_audit` + `technical_remediation` | site size / # templates |
|
||||
| `technical.cwv.perf < 0.5` OR `cls > 0.1` OR `lcp_ms > 2500` OR `ttfb_ms > 600` | `technical_audit` (if not already) + `technical_remediation` | # templates |
|
||||
| `technical.schema.org == "bare"/"none"` OR `entity.panel != "hotel"` OR `entity.name_split` OR `entity.legacy_contamination` OR `entity.subbrands_with_entity == 0` | `schema_build` (one-time) + `onpage_entity` (retainer) | # sub-brands + # properties |
|
||||
| `entity.properties_with_entity == 0` OR `url_hygiene` contains GBP/local mismatch | `local_seo` | # properties |
|
||||
| `findings[].class` includes measurement gap / no GSC-GA4 | `ga4_impl` and/or `dashboard` (+ `gtm_setup` if tag gaps) | — |
|
||||
| `technical.meta_dupe` OR `technical.title_i18n_mismatch` OR `technical.hreflang == "incomplete"` | `onpage_entity` | # templates |
|
||||
|
||||
**Severity → priority** (for the brief/deck ordering, not pricing):
|
||||
- `critical`: crawl/index blocking, CWV failing, entity mistyped
|
||||
- `high`: entity/sub-brand gaps, duplicate URLs, meta dupes
|
||||
- `medium`: hreflang, H1, hygiene
|
||||
|
||||
**Quantity rules**
|
||||
- `monthly` line items use `rate_card.defaults.retainer_months` (default 6).
|
||||
- `local_seo` scope note scales with property count (`entity` / discovery counts).
|
||||
- One-time items counted once even if triggered by multiple findings.
|
||||
|
||||
Edit this file and `rate_card.yaml` together when rates or rules change.
|
||||
@@ -0,0 +1,51 @@
|
||||
# OurDigital service rate card — single source for estimate.py
|
||||
# Mirrors the ourdigital-backoffice quote ranges. Values are KRW, treated as
|
||||
# pre-sales estimate RANGES (finalize after a precise diagnostic with access).
|
||||
quote_prefix: OD # quote number format: OD-YYYY-NNN
|
||||
currency: KRW
|
||||
|
||||
services:
|
||||
technical_audit:
|
||||
label_ko: "Technical Audit / 기술 SEO 진단"
|
||||
unit: one_time # one_time | monthly | project
|
||||
min: 3000000
|
||||
max: 5000000
|
||||
technical_remediation:
|
||||
label_ko: "기술 개선 실행 (sitemap/CWV/SSR)"
|
||||
unit: project
|
||||
min: 3000000
|
||||
max: 8000000
|
||||
onpage_entity:
|
||||
label_ko: "On-Page / Entity Optimization (월 운영)"
|
||||
unit: monthly
|
||||
min: 1500000
|
||||
max: 3000000
|
||||
schema_build:
|
||||
label_ko: "구조화 데이터(Schema) 구축 (1회)"
|
||||
unit: one_time
|
||||
min: 2000000
|
||||
max: 4000000
|
||||
local_seo:
|
||||
label_ko: "Local SEO (프로퍼티 로컬 최적화)"
|
||||
unit: monthly
|
||||
min: 1000000
|
||||
max: 2000000
|
||||
gtm_setup:
|
||||
label_ko: "GTM Setup / 태그 관리 구축"
|
||||
unit: project
|
||||
min: 2000000
|
||||
max: 4000000
|
||||
ga4_impl:
|
||||
label_ko: "GA4 Implementation / 분석 환경 구축"
|
||||
unit: project
|
||||
min: 1500000
|
||||
max: 3000000
|
||||
dashboard:
|
||||
label_ko: "Dashboard Development / 대시보드 개발"
|
||||
unit: project
|
||||
min: 3000000
|
||||
max: 6000000
|
||||
|
||||
defaults:
|
||||
retainer_months: 6 # default contract length for monthly line items
|
||||
disclaimer_ko: "본 견적은 공개 데이터 기반 사전 추정 범위이며, Search Console/Analytics 권한 확보 후 정밀 진단을 통해 확정됩니다."
|
||||
Reference in New Issue
Block a user