- domestic_full.sh / pipeline.sh 新增 --no-report 参数:跳过日报生成, 保持 M1 抓取 + M2→M6 管道不变,用于 12:00/18:00 只抓不生成日报 - crontab: 07:00 全量含日报,12:00/18:00 --no-report(日报每日一次,降低 LLM 费用) - docs/llm-models.md: 各 LLM 调用点分别用的 provider/model 事实清单 - docs/llm-cost-analysis.md: 真实 token 消耗与费用构成、降本建议 - docs/llm-cache-optimization.md: DeepSeek 上下文缓存机制与命中率提升设计 - docs/README.md 增加上述三个文档索引
7.7 KiB
7.7 KiB
LLM 使用点与成本分析
本文档基于 2026-08-30 的代码与真实运行数据编写,用于:
- 盘点本项目所有使用大模型(LLM / embedding)的位置与调用方式;
- 分析 DeepSeek 每日费用的构成与量级;
- 给出降本改善建议(不改写生产代码,仅供决策参考)。
一、本项目所有用到「大模型」的地方
本项目有两类大模型能力,计费方式和对成本的影响完全不同:
- 对话 / 补全类(chat completion):贵,按「输入 token + 输出 token」计费。目前全部走 DeepSeek(
deepseek-v4-flash)。 - 向量化(embedding):便宜,按 token 计费。目前走 DashScope(
text-embedding-v3),与 DeepSeek 是两套账户/两笔账单。
1.1 对话类 LLM 调用点(付费大头,DeepSeek)
| # | 场景 | 位置 | 触发频率 | 单次 token 规模 | 说明 |
|---|---|---|---|---|---|
| 1 | M4 全文英译中 + 投资事件抽取 | llm/extractor.py::translate_and_extract(_call_llm_sync) |
每个去重后的唯一文章 1 次(失败重试最多 3 次) | 单篇平均 输入≈1667 / 输出≈2342 | 这是最大的成本来源,每篇独立调用、整篇中文全文均输出 |
| 2 | M7 日报 AI 摘要 | scheduler/reporter.py::_call_llm_simple(_generate_ai_summary) |
每天 3 次定时(07:00/12:00/18:00),每次 1~N 批 + 截断重试 | 每批 max_tokens 500–800(截断重试 1200) | 依赖当日高重要度事件条数;事件 ≤10 一条批,超过则分批 |
⚠️ 是否重复翻译(重要成本放大项): M4 设计了增量机制——同一
url_hash的data/events/{date}/{hash}.json已存在就跳过,不重复调用 LLM。但每天 3 次定时全流程都会把当天新增的去重文章翻译一遍,若某天连续中断/失败多次,缺的篇会在下次补齐,当周补跑可能一次性翻译多天积压文章。
1.2 向量类(embedding,DashScope,低费用)
| # | 场景 | 位置 | 触发 | 说明 |
|---|---|---|---|---|
| 3 | M5 向量生成(入库) | embedding/pipeline.py::embed_all_events |
每天对已翻译文章批量 | text-embedding-v3,dim=1024,batch_size=10 |
| 4 | M6 / MCP 检索查询向量化 | vectorstore/pipeline.py::search_news、mcp_server/server.py |
每次语义搜索 | 单个查询向量化,量极小 |
1.3 不使用大模型的环节
- M1 抓取、M2 正文提取(trafilatura)、M3 去重(SimHash/指纹库)、M6 Qdrant 入库、M9 MySQL 写入 —— 均不调用大模型。
二、真实 token 消耗与费用估算
以 deepseek-v4-flash(官方模型名 DeepSeek-V4-Flash-0731)当前价格计(官方定价):
| 计价项 | 空闲时段 | 高峰时段(周一至五 9:00–12:00、14:00–18:00) |
|---|---|---|
| 输入(缓存未命中) | 1.5 元 / 百万 token | 3.0 元 / 百万 token |
| 输出 | 4.5 元 / 百万 token | 9.0 元 / 百万 token |
注:本项目常见的定时运行在 07:00(空闲)与 12:00/18:00(接近高峰边界),因此同一日费用波动约 ±100%。
2.1 M4 翻译实测 token(来自 data/events/*/ 的 prompt_tokens/completion_tokens)
| 日期 | 去重后篇数 | 输入 token | 输出 token | 合计 |
|---|---|---|---|---|
| 2026-08-21(大日) | 82 | 135,616 | 208,146 | 343,762 |
| 2026-08-22(中) | 43 | 74,063 | 88,893 | 162,956 |
| 2026-08-30(小日) | 44 | 73,364 | 103,091 | 176,455 |
单篇平均:输入 ≈1650–1720,输出 ≈2050–2540 token。
2.2 单日费用估算(仅 M4)
小日(约 44 篇,176k token)
- 空闲:176,455 输入˝中位 ×1.5 + … 简化按 输入73k×1.5 + 输出103k×4.5 = 0.11 + 0.46 = ≈ 0.57 元
- 高峰:输入73k×3 + 输出103k×9 = 0.22 + 0.93 = ≈ 1.15 元
大日(约 82 篇,344k token)
- 空闲:135,616×1.5 + 208,146×4.5 = 0.20 + 0.94 = ≈ 1.14 元
- 高峰:135,616×3 + 208,146×9 = 0.41 + 1.87 = ≈ 2.28 元
2.3 日报摘要(M7)
每次约 1–3 批,每批输出几百 token、输入为事件列表,单日 3 次合计约几千 token,费用 ≈ 0.03–0.1 元/天,可忽略。
2.4 结论:费用的绝对构成
- M4 翻译是绝对主力(>95% 费用),日报摘要与 embedding 开销可忽略。
- 单日正常落在 1–3 元 区间(视当天文章量与命不命中高峰时段)。
- 若出现 补跑/积压:一次把一两天缺的篇全翻,或当日文章量冲到 80+ 篇,单日可能到 3–6 元。这通常是用户感受到「费用较高」的真实触发点。
三、成本高的根因分析
- 输出 token 巨大:M4 做的是「全文英译中」,每篇都把整篇中文翻译完整输出,单篇输出 2000+ token,是费用的绝对主体(输出单价是输入的 3 倍)。
- 每篇独立调用:82 篇文章 = 82 次往返,system prompt(约 3000 字符模板)每篇重复计入输入。
- 每天 3 次全流程:虽增量去重,但当天新文章都翻译,且 07/12/18 各跑一次,频繁触发。
- 重试放大:
max_attempts=3,失败自动重试(实测约 +3%)。 - 高峰时段触发:12:00/18:00 的定时可能落入高峰计价,费用 ×2。
- 付费墙源白跑:CNBC/Reuters/FT/WSJ 等源抓不到正文,M2 标记 no_content 后不会进入 LLM(有防御过滤),因此不会为这些源付费——但它们也没产出,相当于 M1/M2 白耗。真正进 LLM 的只有 investinglive/zerohedge 等能抓到的源,这些源文章较长、翻译输出也就大。
四、降本改善建议(按性价比排序)
以下均为「建议」,未改动生产代码;实施前请评估收益与副作用。
建议 A(收益最大):限制 / 缩短 M4 输出
- 全文英译中的输出是主要开销。考虑:
- 将
llm_scenes.translation.max_tokens从 8192 降到合理值(如 4096),或 - 改 prompt,只输出中文摘要 + 关键事件,不再整篇英译中(日报和检索实际只消费
content_zh_preview前 300 字与 events,不必整篇全文翻译)。 - 收益:可显著削减输出 token(目前占费用 >60%)。
- 将
建议 B:尽量把翻译放在空闲时段
- M4 翻译集中到 07:00(空闲,半价)。避免 12:00/18:00 落入高峰计价。
- 仅日报生成放在 18:00(摘要量小,价差影响可忽略)。
建议 C:减少不必要的重复翻译(积压/补跑)
- 确保增量机制生效,避免因重复运行把同日文章翻译多遍。
- 若当日中断,下个定时点补齐即可;不要为了「补日报」频繁手动全流程重跑。
建议 D:缓存命中优化
- DeepSeek 对「缓存命中」输入大幅降价(0.05 元 vs 1.5 元/百万)。把 system prompt 固定化、相同前缀复用,可提高缓存命中率,降低输入成本(输入约占 40% 费用)。
建议 E:换更便宜的模型 / 分流
- 若质量可接受,翻译/摘要改用更低价的同类模型或「空闲时段」更明显的档位。
- embedding 已用 DashScope 低价档,无需动。
建议 F:成本监控
- 为
_process_one的成功返回顺带累计 token 到日报stats,或定期统计data/events/*/prompt_tokens总和,用于成本对账与异常预警。
五、参考
- DeepSeek 官方模型与价格
- 相关代码:
llm/extractor.py、llm/pipeline.py、scheduler/reporter.py - 配置:
configs/system.yaml的llm/llm_scenes/embedding段