fix(feishu): render Markdown tables via post+md instead of text downgrade - #62161
fix(feishu): render Markdown tables via post+md instead of text downgrade#62161yuanchenglu wants to merge 4 commits into
Conversation
…efaults
Introduce a three-tier model resolution chain: global default < group
default (by chat_id) < per-session /model override. Operators can now
assign a different default model to each Feishu/Telegram/Discord group
without affecting other groups or requiring users to type /model manually.
Changes:
- gateway/config.py: add group_model_defaults: Dict[str, str] field to
GatewayConfig, with _normalize_group_model_defaults() helper and YAML
pass-through in load_gateway_config()
- gateway/run.py: check group_model_defaults[chat_id] in
_resolve_session_agent_runtime() AFTER global model.default but BEFORE
per-session /model overrides
Usage in config.yaml:
group_model_defaults:
oc_869c1d931f317119d8f51f20797b599c: deepseek-v4-flash
oc_53d22ce34646cebabf06e48ff986ee4c: mistral-large
/ 新增群默认模型覆盖功能,实现三层模型解析链。操作员可为每个群独立设置默认模型,
/ 而不影响其他群或要求用户手动 /model 切换。
…lain text downgrade
teknium1
left a comment
There was a problem hiding this comment.
Thanks for identifying the Feishu table routing issue. Current main still forces detected pipe tables to text in plugins/platforms/feishu/adapter.py:4524-4534, so the focused fix is useful.
Problems
gateway/config.py:511andgateway/run.py:2278add unrelated per-group model routing. This should not be bundled with a Feishu markdown rendering change.plugins/platforms/feishu/adapter.py:155only recognizes a table row beginning with|. Valid GFM tables without outer pipes still fall through to the plain-text branch.- The PR changes no tests. Add a Feishu outbound regression that asserts table-only content is sent as
postwith anmdelement.
Suggested changes
- Re-scope to the Feishu adapter change.
- Cover optional outer-pipe GFM syntax and add routing tests in
tests/gateway/test_feishu.py.
Automated hermes-sweeper review.
| # fresh session exactly as if the reset policy had fired. 0 = disabled. | ||
| session_store_max_age_days: int = 90 | ||
|
|
||
| # Per-group default model overrides: {chat_id: model_name} |
There was a problem hiding this comment.
This introduces a separate gateway-wide model-routing feature unrelated to Feishu table rendering. Please split or remove the group_model_defaults changes so this PR remains focused on the reported outbound-format bug.
| # --------------------------------------------------------------------------- | ||
|
|
||
| _MARKDOWN_HINT_RE = re.compile( | ||
| r"(^#{1,6}\s)|(^\s*[-*]\s)|(^\s*\d+\.\s)|(^\s*---+\s*$)|(```)|(`[^`\n]+`)|(\*\*[^*\n].+?\*\*)|(~~[^~\n].+?~~)|(<u>.+?</u>)|(\*[^*\n]+\*)|(\[[^\]]+\]\([^)]+\))|(^\|.*\|)|(^>\s)", |
There was a problem hiding this comment.
This only detects table rows beginning with |. GFM also permits Header | Value\n--- | ---\nA | B, which still reaches the plain-text branch. Please recognize optional outer pipes and add a regression test for both forms.
Related to the saturated Feishu markdown-table cluster: #52790 (earliest-open canonical) and #58019 use the same adapter mechanism; #31056 / #57566 / #53453 use different mechanisms. Not marking this a duplicate because it also bundles an undisclosed, unrelated core-gateway feature ( |
|
Closing — the table-rendering half of this PR was fixed on main by #68121 (force-text downgrade removed; tables route through post/md, same direction as yours). The per-group model-defaults feature bundled in this PR (gateway/config.py, gateway/run.py) is unrelated to the table fix and deserves its own review — please resubmit it as a focused standalone PR and it will get a proper look. Thanks! |
Summary
The Feishu outbound payload builder (
_build_outbound_payloadinplugins/platforms/feishu/adapter.py) was force-routing any message containing a Markdown table to thetextmessage type, based on an outdated assumption that post-typemdelements cannot render tables. This caused users to see raw pipe-and-dash markdown syntax (| col | col |) instead of a formatted table in Feishu IM clients.This assumption is no longer valid. Feishu's
postmessage type withmdtag now natively supports GFM (GitHub Flavored Markdown) tables, as documented in the official Feishu API docs:Changes
_MARKDOWN_HINT_RE— Added(^\|.*\|)so that a pure table content (without other markdown like bold/headings) still matches and routes through thepost(md)rendering path instead of falling through to plaintext._build_outbound_payload— Removed the_MARKDOWN_TABLE_REforce-text guard. Table content now flows through the samepost+mdelement rendering path as all other markdown features.Outdated comments — Removed stale comments about Feishu not rendering tables in
post(md)mode.Related Issues
Closes: #9549, #52786, #58269, #61643 (and possibly other duplicates)
Testing
Verified on live Feishu IM (feishu.cn, PC + mobile clients):
Risk Assessment
Low. The
_MARKDOWN_TABLE_REregex constant is retained at module level for backward compatibility with any external caller that may reference it (though none exist in the Hermes codebase). The change is entirely within_build_outbound_payloadand only affects the outbound message format selection — no inbound parsing, no session logic, no persistence.概要
Feishu/Lark 消息中的 Markdown 表格一直以原始管道符语法(
| 列1 | 列2 |)显示,而不是渲染为带格线的表格。原因是_build_outbound_payload检测到表格后强制将消息降级为纯文本类型。这个降级逻辑基于一个过时的假设——飞书 post 消息的 md 标签不支持表格渲染。修改内容
_MARKDOWN_HINT_RE— 新增(^\|.*\|)模式,使纯表格内容也能被识别为 Markdown_build_outbound_payload— 移除_MARKDOWN_TABLE_RE强制纯文本分支,表格内容走正常的 post(md) 渲染路径测试验证
已在飞书 PC 和移动客户端上验证:表格正确渲染为带格线的原生表格,粗体/代码块/列表等格式正常保留。
相关 Issue
解决 #9549、#52786、#58269、#61643 等 4 个已上报的同一 bug 报告。