twu-trend-narrator v1.1.1 — 走势描述:脚本供数据,AI写媒体风语言
定位
给领导看的、给其他 skill 用的走势刻画。 用自然语言和量化数据,把任意周期的 K 线/分时走势讲清楚: 模式是什么、从哪启动、现在什么状态、动能在增强还是衰减、处于高位还是低位、量价配合如何。 专业不江湖、讲人话、有条理、每个结论都有数据支撑。
- 形态库(双顶/头肩/旗形等)只是辅助标签:走势千变万化,库外形态用通用规则讲(V型/箱体/收敛/扩张/单边/回调全覆盖)
- 走势本质三要素:一阶方向(涨跌与速度)、二阶拐点(动能与转折)、波动×位置(震荡性质)
- 不预测:只讲现状与技术含义,不给方向预测和买卖建议
触发
- 用户给代码或图:"刻画下 600519""这波走势怎么说""描述K线"
- 用户问形态:"是不是双顶/头肩/W底""什么形态"
- 用户复盘:"今天分时怎么走""最近一年走势"
- 其他 skill 需要走势描述:调用
pattern_describer.py --mode brief取研报风格文本
快速入门(30 秒上手)
一句话用法:"刻画下 600519" 或 "描述K线",Agent 自动跑完整个流水线,交付图文报告。下面的手动流程用于了解内部机制或脚本调试。
# 0. 环境:python3(需装 akshare/pandas),在 scripts 目录内执行
PY=python3
cd ~/.workbuddy/skills/twu-trend-narrator/scripts
# 1. 拉数据(默认 tushare 优先,token 自动读取,失败降级 akshare)
$PY fetch_data.py 600519 --period daily --start 20260601 --end 20260731
# 2. 生成图文报告(K线图 + 自然语言刻画 + 关键数据面板)
$PY fetch_data.py 600519 --period daily --format json | $PY render_report.py --type kline --name 贵州茅台 --code 600519 > report.html
# 3. 打开 report.html 即得完整走势报告
三个常用变体:
- 分时:
fetch_data.py 600519 --period intraday→render_report.py --type intraday - 板块/行业:
fetch_data.py 881278.TI --period daily(自动走 tushare ths_daily) - 周K/月K:
fetch_data.py 600519 --period weekly(自动重采样)
示例报告(成品长这样)
以"贵州茅台 日K(2025-08-01 ~ 2026-07-31)"为例,render_report.py 输出的最终报告包含四部分:标题(带完整区间)、走势刻画(AI 媒体风叙述,四段式)、K线图(ECharts,横轴真实日期,默认全量显示)、关键数据面板(四组逻辑框架 + 技术评分条)。走势刻画段落如下:
近一年贵州茅台整体呈宽幅震荡格局,区间自2025年8月1日的1417元起步,期间最高触及2026年2月5日的1555元,随后转入中期调整,2026年6月26日收盘探至区间最低1168.63元,区间总波动约36%。截至7月31日收报1350.60元,较区间高点回撤约13%,但已自6月底低点显著回升。
走势脉络可概括为:2025年8月至9月先行走高约9%至1538元;此后转入震荡下行,至2026年1月底回落至1322元,累计回调约14%;1月底至2月初快速反攻,大涨18.6%至1568元,逼近区间高点;2月初起再度回落,3月17日见1498元后进入年内最深的一段调整,至6月29日探至1151元,下挫23.2%,历时约3个半月。
现价1350.60元处于区间中位(48%分位),站上20日均线约6.6%,较区间低点回升15.6%。6月底以来的回升由低位启动,23个交易日上行17.3%,将股价自1151元拉回1350元上方,是近期强度最高的上行波段。技术面上,上方压力参考2月高点1555元一带,下方支撑关注6月底启动平台1151元附近。
当前观察点是这波回升能否延续,关键看股价能否站稳20日均线并向上挑战2月高点区域,量能变化是重要确认信号。
要点:叙述为四段式(整体→阶段脉络→现状量价→观察点),每个数字都来自素材字段、无预测、只有现状与技术含义。若报告里出现"数据陈述·非成品"标注,说明 AI 未按此标准成文,应拿 media_material 素材重写后以 --narrative 注入。
执行流程
第一步:解析输入(自然语言 → 周期/数据量)
| 用户说法 | 周期/数据量 | |---|---| | "XX最近一年走势" | 日K,近 250 交易日 | | "XX近半年/几个月" | 日K,近 120-130 交易日 | | "XX近一周/这几天" | 日K,近 5-10 交易日 | | "XX今天/当日分时/日内" | intraday(当日 1 分钟线) | | "XX盘中/几分钟K" | 分钟K(默认5分钟) | | "XX长期/几年" | 周K或月K | | "XX这波上涨/下跌" | 日K + 结构重点 | | 只给代码 | 默认日K 近120交易日 |
数据量自适应:<10根只做单根+简单分段并标注"样本极少";10-60根做组合+分段;>60根全量。指定"最近N天"用 --start。 网络搜索(可选):需要背景时 WebSearch 补充,但行情刻画必须真实数据。
第二步:核心流水线(五条)
# 在技能目录内执行(scripts/ 为脚本目录;PY 用装好 akshare/pandas 的 python,见快速入门)
PY=python3
DIR=./scripts
# ①主:通用模式描述(量化特征+模式判定+动力学+自然语言)
$PY $DIR/fetch_data.py 600519 --period daily --format json | $PY $DIR/pattern_describer.py
# ②辅:形态标签(形态库匹配)
$PY $DIR/fetch_data.py 600519 --period daily --format json | $PY $DIR/pattern_engine.py --recent 40
# ③辅:技术评分(六维加权 -100~+100,只描述强弱)
$PY $DIR/fetch_data.py 600519 --period daily --format json > d.json
$PY $DIR/pattern_engine.py --recent 40 < d.json > p.json
$PY $DIR/tech_score.py --patterns p.json < d.json > s.json
# ④报告/图形:HTML 图文一体报告(默认)——自然语言刻画 + ECharts 图 + 关键数据面板 + 形态信号
$PY $DIR/fetch_data.py 600519 --period daily --format json | $PY $DIR/render_report.py --type kline --name 贵州茅台 --code 600519 --patterns p.json --score s.json > report.html
# ⑤保底图形:SVG widget(render_chart.py,HTML 不可用时降级)
$PY $DIR/fetch_data.py 600519 --period daily --format json | $PY $DIR/render_chart.py --type kline --title 贵州茅台日K
周期参数:日K阈值5%/周K10%/月K15%/分时0.8%;分时 --recent 30、分钟K --recent 24。
多周期共振:问中长期时并行拉日K+周K,方向一致标"多周期共振",矛盾标"日K与周K背离"。
数据源路由(默认 auto):tushare 优先,失败自动降级 akshare。token 自动从 ~/.workbuddy/mcp.json 的 tushareMcp.url 读取(兼容旧路径 ~/.tushare/token),无需手动配置。覆盖矩阵:股票→daily、ETF→fund_daily、指数→index_daily、板块/行业(881278.TI/801738.SI)→ths_daily、分钟/分时→stk_mins(有约 1 次/分钟频率限制,超限自动降级 akshare 新浪源)。--source akshare / --source tushare 可强制指定;都失败如实报告。
第三步:输出
full 模式(用户对话):默认用 render_report.py 生成自包含 HTML 报告(走势刻画段落 + ECharts 图形 + 关键数据面板 + 形态信号),交付本地 .html 文件供预览;对话内同步给文本要点(模板见下)。HTML 不可用时降级 render_chart.py SVG widget。
关键数据面板(四组逻辑框架,非罗列):①趋势与结构(趋势状态/斜率强度/MA20偏离/区间位置/结构形态)②动能与动量(短期中期斜率/加速度/近期拐点)③量价与波动(量比/量价状态/波动性质/K线实体)④位置与波段(距峰值/距低点/区间总波动/最强波段/趋势启动点)。可传 --score s.json(tech_score 输出)加技术评分条(总分+分档+六维明细)。
形态信号(聚合+紧凑,非逐条罗列):顶部信号聚合行(基于全部形态:看多 N 个(名称)/ 看空 N 个(名称)/ 中性 N 个),下方紧凑列表只展示最近 20 个交易日内的形态 + 结构形态(双顶/头肩等不受日期限制),按置信度排序最多 --max-patterns 条(默认 6)。
报告规范(蓝金研报风):白底、三色铁律(主 #185FA5 / 强调 #BA7517 / 中性灰)、衬线标题、tabular-nums 数字、红涨绿跌(#B91C1C/#166534);K线用 ECharts candlestick(红涨绿跌 + MA5/MA20 + 成交量副图 + dataZoom,横轴必须真实日期 YYYY-MM-DD,禁止 MM-DD 缩写导致跨年混淆),分时用 line(价格线 + VWAP 均价线 + 昨收基准虚线 + 成交量,y轴±%);ECharts 走 cdnjs CDN;内联 JS 交付前必须语法校验,图表能渲染才算完成。口径一致性铁律:正文刻画口径=全量数据,K线图默认全量显示(--max-bars 默认 0,ECharts dataZoom 支持任意长度缩放,禁止默认截断);标题必须带完整区间(YYYY-MM-DD ~ YYYY-MM-DD);仅当显式指定 --max-bars N 截断时,副标题必须标注"图显示最近 N 根(起始日 起)",禁止正文与图时间范围不一致(曾现"正文3月起、图5月起"事故)。
分时图坐标轴规范(成熟方案,防回归):横轴=完整交易日 9:30~15:00(242分钟序列,数据按分钟对齐、缺失补 null、线 connectNulls);横轴刻度=整点/半点白名单 9 个(09:30/10:00/10:30/11:00/11:30/13:30/14:00/14:30/15:00,11:30 与 13:00 只留 11:30),用 axisLabel.interval 函数白名单注入(禁止 interval=1+formatter 全量过滤——242 个 label 全量布局会卡死、下午刻度丢失);纵轴 0%(昨收)必在刻度上(interval 按当日振幅自适应 0.5/1/2/3%,min/max 取 interval 整数倍并强制覆盖 0,跳空高开/低开也见昨收线);VWAP 一律 close×volume 自算(amount 字段量纲不可靠);ECharts 函数(formatter/interval)统一占位符+replace 注入真函数,禁止字符串函数体。
SVG 保底纪律:颜色硬编码浅色主题(白底/深灰字/红涨绿跌),禁止 var(--color-*)(widget 沙箱变量失效会整图发黑)。
【整体刻画】<标的名> <周期>(截至 <日期>) ← 第一层,先整体后重点
- 区间框架:起点 <日期> <价格> → 终点 <日期> <价格>,累计 ±X%
- 阶段结构:<上涨X%→下跌Y%→回升Z%>(整体骨架,每段带起止时间与价格)
- 区间高低:最高 <价格>(<日期>)、最低 <价格>(<日期>),区间总波动 X%
- 模式:<模式名带近期方向>(如"宽幅震荡,6月底起回升18.4%")
【重点特征】(highlights 取 2-3 个展开,不全维度罗列)
- 最强波段:<方向 X%>(起止,价格→价格)
- 距区间高点回撤 X% / 量能放大或萎缩(量比 X)
【形态标签】(辅助)
- [置信度] 形态名(日期):含义 + 关键位
【技术面强度】
- 评分X/100(偏强/偏多/中性/偏空/偏弱):趋势X/25、动量X/25、量价X/20、形态X/10、位置X/10、波动X/10
- RPS:近20日超额+X%(强于/弱于基准)
【关键数据】
- 3-5 个数据:<指标>(值,含义)
brief 模式(其他 skill 调用):pattern_describer.py --mode brief,输出自然语言化数据陈述(总述+整体框架+阶段脉络+重点+位置量价,标注"数据陈述·非成品")。调用方 AI 必须据此按主流财经媒体风格组织成文,禁止照抄数据陈述交付。
render_report 叙述段(默认必须,非可选):执行 AI 拿 media_material 素材按媒体风格成文后,用 --narrative "<媒体风叙述>" 注入 HTML(多段可用 <p> 分隔)。交付的 HTML 里必须是 AI 组织的专业流畅语言,不是脚本素材行;仅当 AI 无法成文时才允许缺省(脚本兜底输出数据陈述)。
表述纪律(唯一权威)
- 量化优先:每个结论必须挂数字("前半段净跌16.4%后半段净涨49.5%"),禁止裸形容词
- 讲人话有条理(整合版组织逻辑,见 media-language 第九章+第十章):数据→解读→含义三层翻译——每个关键数字要么给解读(为什么)、要么给含义(所以呢),裸数字堆砌即生硬;按"定性句(判断+解读)→论证段(时间线+原因)→现状段(位置+含义)→收尾观察点(+为什么观察)"四段骨架组织;一段一主题、数据跟观点走、时间线是骨架(长期先过去后现在,短期按早盘/午后/尾盘)、时态分离(过去时讲波段与原因、现在时讲状态与含义);禁AI过渡词(此外/值得注意的是/综上所述/总的来说);解读克制(或/有望/大概率),不给确定预测
- 输出描述严禁硬编码(铁律,最高优先级):脚本只输出结构化素材(media_material:整体框架/阶段结构/波段序列/启动点/位置/量价/高亮特征,全真实数据)与自然语言化数据陈述(material_text / brief 模式:把素材讲成读得通的数据段落——总述+整体框架+阶段脉络+重点+位置量价,数据嵌入句子,但无文学修辞、无媒体句式模板、非成品语言,并标注"数据陈述·非成品")。任何叙述成句、用词、修辞、句式必须由执行 AI 生成——禁止脚本拼成品句、禁止把数据陈述当成品交付、禁止照抄任何模板句子;render_report 叙述段由 AI 拿素材成文后用
--narrative注入,缺省时输出数据陈述兜底。模式名标签(冲高回落/宽幅震荡等)只是方向语义参考,具体成句由 AI 组织。硬编码句式穷尽不了形态,语言层永远归 AI,这是本技能不可违反的铁律 - 先整体后重点、禁参数话术、找特点侧重:成文必须先给整体刻画(区间框架:起止时间价格+累计涨跌+阶段结构序列+区间高低点,让听者先建立完整地图),再展开重点特征(highlights 取 2-3 个,不全维度平铺);禁止"X根K线/分钟线""X个周期""样本数""共X段"等参数堆砌,时间一律自然语言(当日/近一周/自X月以来/近一年);开始/结束/最高/最低/形态/波动/幅度/量价是多维度素材不是清单,每句有信息量
- 专业克制:只用规范术语(回撤/反弹/整理/突破/支撑/阻力/收敛/扩张),禁"拉升/洗盘/主力/起飞/崩盘"等江湖词;模式标签必须带方向信息(mode_plus:如"宽幅震荡,近期6月底起回升18.4%"),禁止"宽幅震荡""震荡"类无方向性空泛标签;置信度分级(高=确立;中=若突破/跌破则;低=关注)
- 形态是补充:匹配到才写形态标签,不硬套;库外走势用通用模式讲
- 定量成分与数据匹配:叙述里每个数字必须对应素材字段(net_change=区间累计涨跌、timeline 起止价、vs_peak/vs_trough、pos_in_range、量比、range_pct、ma20_rel_pct),禁止自造数字;成文后自查"这句数字来自哪个字段"
- 不预测:只讲现状与技术含义(支撑/压力/背离),禁方向预测和买卖建议
- 数据诚实:数据源失败/样本不足/涨停一字板时明说,不硬编;回撤口径注明(收盘价 vs 日内区间)
参考资产
references/media-language.md:媒体语言素材库(走势说法总集:分时/区间/中长期/模式映射/叙事句式/质感技巧/时间铁律/数据支撑写法/标杆范例十二章,AI 成文首选参考,第十二章为用户认可的正例,成文前先读找感觉)references/pattern-glossary.md:叙事句式模板(对齐 pattern_describer 输出字段:总起句/分段/最强波段/趋势结构/启动点/分时段落/动力学;媒体写法见 media-language)references/pattern-library.md:形态库(26种形态的判定规则+表述+可靠性)references/indicator-glossary.md:指标口径库(各指标含义/何时用/怎么表述)references/competitor-research.md:同类技能调研(可借鉴项与排除项)
边界
- 分时仅覆盖最近5个交易日;多周期需求可并行日K+周K+月K合并刻画。
- 本技能供其他 skill 调用 brief 素材句,调用方 AI 按媒体风格组织成文(不直接照抄素材句)。
FAQ
Q: tushare token 在哪配置?
A: WorkBuddy 环境自动从 ~/.workbuddy/mcp.json 的 tushareMcp.url 读取,无需手动配置。其他 AI 客户端或手动环境,把 token 纯文本写入 ~/.tushare/token(一行)即可,读取优先级为 mcp.json → ~/.tushare/token。两处都没有则视为未配置,自动降级 akshare。
Q: 没配 tushare 还能用吗? A: 能。auto 模式下 token 不可用时自动走 akshare(新浪源优先,东财兜底),功能不变,只是数据源不同。板块/行业指数(881278.TI/801738.SI)除外,这类代码必须 tushare,没配 token 会如实报错。
Q: 怎么强制指定数据源?
A: --source akshare 强制 akshare;--source tushare 强制 tushare(无 token 会报错提示配置)。
Q: 分时/分钟数据为什么有时显示 akshare 源? A: tushare 分钟接口(stk_mins)有频率限制(约 1 次/分钟),超限自动降级 akshare 新浪源。这是正常行为,降级原因会如实记录在输出的 errors 字段,数据仍是真实行情。
Q: 为什么只能看最近 5 天分时? A: 设计边界。分时/分钟K 只覆盖近 5 个交易日,更早的日内走势无法回溯,请改用日K(--period daily)刻画。
Q: 报告打不开或图表空白?
A: 报告是自包含 HTML,K线图依赖 cdnjs CDN 加载 ECharts。离线打开时图表可能空白,文字刻画部分不受影响。可改用 render_chart.py 生成纯 SVG 保底图(无外部依赖)。
Q: 为什么 brief 模式输出标着"数据陈述·非成品"? A: 这是本技能的硬规则(表述纪律第 3 条):脚本只输出结构化素材和数据陈述,最终成句必须由 AI 按媒体风格组织,禁止把素材句直接当成品交付。调用方 skill 拿到素材后自行成文。
常见报错与处理(先看这里)
数据获取失败时,输出会带 hint 字段(通俗解释 + 修正建议),对照下表快速定位:
| 报错关键词(errors 字段) | 原因 | 怎么办 |
|---|---|---|
| 未找到 tushare token | 没配置 tushare | WorkBuddy 连上 tushare MCP,或写 ~/.tushare/token 一行;不配也能用,自动走 akshare |
| 频率超限 | tushare 分钟接口限流(约 1 次/分钟) | 已自动切 akshare,数据可用;等 1-2 分钟可恢复 tushare |
| 退市 / 不存在 / 无数据 | 代码错了、已退市、非交易时段 | 检查代码格式:600519 / 510300 / 881278.TI |
| timeout / getaddrinfo / failed | 网络抖动或断网 | 检查网络后重试;请求已带自动重试 1 次 |
| 所有数据源均失败 | tushare 和 akshare 都不可用 | 大概率是网络问题,稍后重试 |
| 报告图表空白 | 离线,ECharts CDN 加载失败 | 联网刷新;或 render_chart.py 生成纯 SVG 离线图;文字刻画不受影响 |
Scan to join WeChat group