cd83cd9271
- fetch_prices.py: 标准库实现,C1-C7 合规红线硬编码 - targets.yaml: BIZ-144 v2 名单(4 家品牌旗舰店 + 月度白牌轮换) - cron/competitor-price.cron: 每周一 09:00 Asia/Shanghai - README.md: 本地运行 + cron 安装 + 失败告警说明 - data/2026-09-20/: 手动试跑样例(4 家被 robots 禁止=预期合规行为,白牌待回填) 修复: MULTICA_PARENT_ISSUE 空字符串时错误发评,改为空值回退默认父单 Co-authored-by: multica-agent <github@multica.ai>
2.8 KiB
2.8 KiB
竞品价格监控采集(BIZ-145 / S2)
按 BIZ-144 v2 竞品名单每周采集一次公开价格信息,落地 JSON/CSV 快照,供 BIZ-146 生成周报。
合规红线(硬编码于 fetch_prices.py,不可命令行覆盖)
| 条目 | 实现 |
|---|---|
| C1 频率 | 每周一次(cron);单店 ≤10 页;请求间隔 ≥5s |
| C2 robots.txt | 被禁止即跳过,记 skipped_robots |
| C3 不绕反爬 | 固定常规 UA;遇验证码/登录墙(401/403/特征词)即放弃该页 |
| C4 字段白名单 | name / list_price / promo_text / sales_display,只抽公开页面展示字段 |
| C5 留存 | 原始快照保留 90 天,每次运行自动清理过期目录 |
| C7 无代理/账号 | 直连、无登录态 |
目录结构
competitor-price/
├── fetch_prices.py # 采集脚本(仅标准库,Python ≥3.10)
├── targets.yaml # 竞品名单与 SKU URL(数据 Owner 维护,见文件头注释)
├── cron/
│ └── competitor-price.cron # 每周一 09:00 GMT+8
└── data/YYYY-MM-DD/
├── prices.json # 含合规元信息 run_meta + results + failures
├── prices.csv # 同数据的 CSV 版(UTF-8 BOM,Excel 可直接打开)
└── fetch.log # 运行日志
本地手动运行(调试用)
cd monitoring/competitor-price
python3 fetch_prices.py # 退出码 0=全部成功,1=存在失败/跳过
调试时不触发父单告警:
MULTICA_PARENT_ISSUE="" python3 fetch_prices.py # 空值视为未配置,只写日志
安装 cron(每周一 09:00 Asia/Shanghai)
crontab -l > /tmp/mycron 2>/dev/null || true
cat cron/competitor-price.cron >> /tmp/mycron
crontab /tmp/mycron && rm /tmp/mycron
crontab -l | grep competitor-price # 验证
cron 机器需满足:python3 ≥3.10、multica CLI 已登录(用于失败时在父单 BIZ-143 评论告警)。
服务器并非 24h 开机的话,cron 条目含 flock 防重入;漏跑可在下周一前手动补跑一次即可。
失败告警
任一条目非 ok 时,脚本在父单 BIZ-143 留一条失败汇总评论(需 multica 可用),
同时本地 fetch.log 留痕。白牌店铺未回填 URL 记为 skipped_no_url,属预期,不告警。
已知边界(如实说明)
- Tmall 店铺首页
robots.txt对通用 UA 默认禁止 → 当前 4 家品牌旗舰店均记skipped_robots, 这是合规设计的预期行为,不是脚本故障。要拿到真实价格,需要数据 Owner 在targets.yaml的sku_urls中回填允许抓取的页面,或由业务方决定改用其他公开数据源。 - 价格抽取基于页面公开 HTML 的通用正则(
"price"字段 / ¥ 符号),对重前端渲染页面 可能抽不到 → 记ok_no_price_field,周报侧据此人工复核。