一键导入
gguide-tv
Platform rules, API authentication, date parsing, and Taiwan relevance filtering for the 番組表Gガイド (bangumi.org) TV program scraper
用 Codex 或 Claude 帮你安装 复制这段 Prompt,粘贴到 Codex、Claude 或其他助手里,让它检查 Skill 页面并帮你完成安装。
菜单
Platform rules, API authentication, date parsing, and Taiwan relevance filtering for the 番組表Gガイド (bangumi.org) TV program scraper
用 Codex 或 Claude 帮你安装 复制这段 Prompt,粘贴到 Codex、Claude 或其他助手里,让它检查 Skill 页面并帮你完成安装。
基于 SOC 职业分类
Planning principles, model selection, and scope rules for the Architect agent
Implementation rules for database migrations, Python scrapers, and Next.js web for the Engineer agent
BaseScraper contract, field rules, and Peatix-specific conventions for the Scraper Expert agent
Scraper test execution rules, output validation criteria, and report format for the Tester agent
BaseScraper contract, field rules, and Peatix-specific conventions for the Scraper Expert agent
Platform rules and field mappings for the 誠品生活日本橋 (eslite spectrum Nihonbashi) scraper
| name | gguide_tv |
| description | Platform rules, API authentication, date parsing, and Taiwan relevance filtering for the 番組表Gガイド (bangumi.org) TV program scraper |
| applyTo | scraper/sources/gguide_tv.py |
| Field | Value |
|---|---|
| Site URL | https://bangumi.org |
| API/Rendering | 2-step HTTP (static HTML fragment) — no Playwright required |
| Auth | None — session cookie obtained from Step 1 GET |
| Rate limit | Not published; use 0.3–0.5 s sleep between requests |
| Source name | gguide_tv |
| Source ID format | gguide_{ebisId} (e.g. gguide_AlhwDA0YgAE) |
| Official source | 番組表.Gガイド(放送局公式情報) |
Step 1: GET https://bangumi.org/search/?q={kw}
→ sets _ggm-web_session cookie (required for Step 2)
Step 2: GET https://bangumi.org/fetch_search_content/?q={kw}&type=tv
Headers: Referer: https://bangumi.org/search/?q={kw}
→ returns HTML fragment (no page shell)
Step 3 (per item): GET https://bangumi.org/tv_events/{ebisId}
→ static HTML detail page with synopsis
| Data | Selector | Notes |
|---|---|---|
| Program list | ul.list-style-1 li.block | Skip li.ads |
| Genre | .box-2 p [0] | e.g. バラエティ, ドキュメンタリー/教養 |
| Title | .box-2 p [1] | May contain accessibility emoji (🈑🈞🈓) |
| Schedule | .box-2 p [2] | "4月29日 水曜 12:00 テレ東" — use get_text(separator="\n", strip=True) to preserve multi-line structure |
| ebisId | a.js-logging[data-content] → JSON → .ebisId | Stable across runs |
get_text(separator="\n")required: Withoutseparator, HTML child elements are concatenated directly (e.g."23:450:00 歌謡ポップス"), breaking multi-line schedule parsing. Always useps[2].get_text(separator="\n", strip=True).
| Event field | Source | Notes |
|---|---|---|
source_id | gguide_{ebisId} | Stable dedup key |
source_url | https://bangumi.org/tv_events/{ebisId} | |
name_ja | .box-2 p[1] stripped | Emoji marks removed with regex |
raw_title | Same as name_ja | |
raw_description | 開催日時: …\n放送: …\nジャンル: …\n{detail_text} | See Date Extraction |
start_date | Parsed from schedule string | See Date Parsing |
category | Inferred from genre | See Category Mapping |
original_language | "ja" | Always Japanese |
official_url | None | Aggregator, not organiser |
Schedule format: "4月29日 水曜 12:00 テレ東" (full-width space before channel).
Regex: (\d{1,2})月(\d{1,2})日\s+\S+?\s+(\d{1,2}):(\d{2})\s*(.+)
Year inference:
current_yearLOOKBACK_DAYS days, try current_year + 1Late-night convention (25:00 style): hour >= 24 → subtract 24 hours and add 1 day.
Always prepend 開催日時: YYYY年MM月DD日\n to raw_description.
Multi-line schedule with end time ("23:45\n-\n0:00 歌謡ポップス" format):
_parse_schedule() returns (datetime, channel, end_time_str) — end_time_str is "HH:MM" or None.end_time_str is not None: business_hours = f"{start_hhmm}〜{end_time_str}".end_time_str = None (single-line list page): fallback to detail page text using r"(\d{1,2}:\d{2})\s*\n[-−]\s*\n(\d{1,2}:\d{2})". If match found, same format applies.business_hours = None.| Keyword | Filter applied |
|---|---|
台湾 | None — all results are already Taiwan-relevant by definition |
テレサ・テン | Only keep if full string テレサ・テン appears in title (blocks shows where テレサ is a minor guest, e.g. 昭和の名曲...明菜・テレサ・八代亜紀!) |
| Gガイド Genre | Category |
|---|---|
| ドラマ | performing_arts |
| 映画 | performing_arts |
| 音楽 | performing_arts |
| ドキュメンタリー/教養, 報道 | report |
| バラエティ, スポーツ, other | report |
SEARCH_KEYWORDS = ["台湾", "テレサ・テン"]
台湾ドラマ is a subset of 台湾 and returns the same results — no need to include.
台湾特集 is optional; adds low volume and typically already matched by 台湾.
LOOKBACK_DAYS = 7 — skip programs that aired more than 7 days ago.
Upcoming broadcasts (future dates) are always included.
seen_ebis_ids set prevents same ebisId from being fetched twice across keyword searches.dedup_events() deduplicates by (name_ja, start_date.date()).| Symptom | Cause | Fix |
|---|---|---|
fetch_search_content returns empty | Step 1 GET failed / no session cookie | Check if resp1.raise_for_status() passes; log cookie headers |
start_date is in the wrong year | Year inference edge case | Check Dec→Jan rollover logic in _parse_schedule |
Genre has extra whitespace (e.g. バラ エティ) | BeautifulSoup joining text nodes from HTML line breaks | Minor cosmetic issue; annotator handles it |
| テレサ・テン search returns J-pop variety show | テレサ appears without ・テン in title | Already filtered — only full テレサ・テン passes |
| 0 results | Gガイド changed HTML structure | Re-inspect ul.list-style-1 li.block selector |
Detail page returns empty <main> | Gガイド changed layout | Fall back to list-page title+schedule without description |
台湾特集 adds unique high-value results worth adding to SEARCH_KEYWORDStitle-only Taiwan filter for 台湾 keyword to reduce sports-broadcast false positives