Skip to content

Enhance chatv2 module with agent mode, tools, and dependency updates#760

Merged
hugefiver merged 67 commits into
masterfrom
dev
Apr 29, 2026
Merged

Enhance chatv2 module with agent mode, tools, and dependency updates#760
hugefiver merged 67 commits into
masterfrom
dev

Conversation

@hugefiver
Copy link
Copy Markdown
Collaborator

This pull request primarily upgrades the Go version required by the project from 1.25 to 1.26 across all documentation, CI/CD workflows, and the Dockerfile. In addition, it refactors various bot command handlers to use new utility functions for sending replies and error handling, and improves string formatting in message entity handling for better code clarity and maintainability.

Go Version Upgrade:

  • Updated the Go version from 1.25 to 1.26 in all relevant files, including documentation (README.md, README_zh-CN.md, AGENTS.md), CI/CD workflows (.github/workflows/*.yml, .travis.yml), Dockerfile, and linter configuration (.golangci.yaml). [1] [2] [3] [4] [5] [6] [7] [8] [9] [10] [11] [12]

Bot Command Handler Refactoring:

  • Refactored multiple command handlers in base/ to use new utility functions like util.SendWithError, util.ReplyWithError, and util.RawTgText for sending replies and handling errors more consistently. [1] [2] [3] [4] [5] [6] [7] [8] [9]

Bot Status and Info Improvements:

  • Enhanced the /info command in base/helper.go to include detailed bot status (shutdown, MC dead, sticker mode, bye_world) by adding currentBotStatus and formatBotStatus helper functions.

Message Formatting Improvements:

  • Replaced repetitive fmt.Sprintf and WriteString calls with fmt.Fprintf in message entity formatting functions in chat/context.go for improved readability and maintainability. [1] [2] [3]

Imports and Utility Integration:

  • Added necessary imports of the new util package in multiple files to support the refactored reply and error handling functions. [1] [2] [3] [4] [5]

These changes collectively modernize the codebase, improve error handling and message formatting, and ensure compatibility with Go 1.26.

Generated by Github Copilot

dependabot Bot and others added 30 commits February 27, 2026 17:08
Bumps [github.com/meilisearch/meilisearch-go](https://github.com/meilisearch/meilisearch-go) from 0.36.0 to 0.36.1.
- [Release notes](https://github.com/meilisearch/meilisearch-go/releases)
- [Commits](meilisearch/meilisearch-go@v0.36.0...v0.36.1)

---
updated-dependencies:
- dependency-name: github.com/meilisearch/meilisearch-go
  dependency-version: 0.36.1
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
Add chatv2 package implementing LLM agent mode for the Telegram bot,
built on cloudwego/eino react agent framework with MCP tool support.

Key components:
- Agent builder with sub-agent delegation and MCP server integration
- Streaming output with sentence-boundary chunking and periodic edits
- HTML/MarkdownV2 output formatting with reasoning block support
- Configurable filters (whitelist) and prompt templates
- Built-in tools: get_message, get_image, web_fetch

Bug fixes applied during review:
- Fix malformed HTML closing tag in markdown block formatting
- Fix streaming response saving with placeholder message ID instead of 0
- Fix get_message tool to use direct Redis lookup instead of 1-msg context
- Remove dead code (extractImageHint) and pointless post-send Notify
- Unify input extraction logic between Chat() and template rendering

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-authored-by: Claude <noreply@anthropic.com>
Add 40 unit tests across 4 test files covering format, mapping, filter, and types packages. Fix all golangci-lint issues including err113 sentinel errors, staticcheck deprecated API removal, gocritic if-else to switch, errcheck deferred close handling, goconst string constants, prealloc slice optimization, and godox comment cleanup.
External redirect targets change over time, causing false failures.
bytedance/sonic deliberately does not support 32-bit architectures. Gate all chatv2 source and test files with //go:build !386 && !arm, and provide a no-op stub (stub_32bit.go) so the project compiles on GOARCH=386 and GOARCH=arm with agent mode disabled.
- Fix bot reply detection: compare msg.User (username) not msg.UserNames.String() (display name)
- Guard whitelist rejection log against nil Sender (channel posts/anonymous admins)
- Export HasCompiledChat and use it in main.go routing to avoid errNoCompiledConfig
- Close existing MCP client before replacing to prevent connection leak
- Remove unimplemented scope param from get_context tool
- Fix main.go import ordering
- Remove unused Format field from getImageArgs
- Add ReplyTo to streaming placeholder Send for proper threading
- Fix race between ticker goroutine and finalize with sync.WaitGroup
- chatv2/chatv2.go: return streamErr or send error message on streaming failure
- chatv2/streaming.go: remove double blank line
- config/chat.go: fix Agent field alignment, gofmt struct tags
- main.go: add agent-routing check to reply-to-bot handler
- chat/context.go, meili/bot_handle.go: fmt.Fprintf perfsprint fixes
feat(chatv2): add agent mode chat module with streaming, MCP and tools
…fig refactoring

- Introduce update_progress tool for real-time status updates during agent execution
- Add analyze_image tool for vision-based image analysis with optional query support
- Implement progress placeholder messaging with configurable summarization via small models
- Refactor configuration to support agent-based architecture with separate Chats/Agents
- Add model configuration support for individual tools with ToolModels mapping
- Enhance media attachment handling with improved image/document reference hints
- Implement thread-safe progress message editing with lifecycle state management
- Support configurable chat engine selection (v1/v2) with backward compatibility
This commit updates all instances of interface{} to the newer 'any' type
for better Go 1.18+ compatibility and consistency. Additionally,
replaces manual string indexing with strings.Cut for safer and more
efficient key-value parsing in utility functions.

BREAKING CHANGE: Changes function signatures in mockContext to use 'any'
instead of 'interface{}' which may affect consumers of these methods.
…720)

Bumps [github.com/mark3labs/mcp-go](https://github.com/mark3labs/mcp-go) from 0.43.0 to 0.44.1.
- [Release notes](https://github.com/mark3labs/mcp-go/releases)
- [Commits](mark3labs/mcp-go@v0.43.0...v0.44.1)

---
updated-dependencies:
- dependency-name: github.com/mark3labs/mcp-go
  dependency-version: 0.44.1
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
Bumps [github.com/mark3labs/mcp-go](https://github.com/mark3labs/mcp-go) from 0.44.1 to 0.45.0.
- [Release notes](https://github.com/mark3labs/mcp-go/releases)
- [Commits](mark3labs/mcp-go@v0.44.1...v0.45.0)

---
updated-dependencies:
- dependency-name: github.com/mark3labs/mcp-go
  dependency-version: 0.45.0
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>
Bumps [github.com/cloudwego/eino](https://github.com/cloudwego/eino) from 0.7.37 to 0.8.3.
- [Release notes](https://github.com/cloudwego/eino/releases)
- [Commits](cloudwego/eino@v0.7.37...v0.8.3)

---
updated-dependencies:
- dependency-name: github.com/cloudwego/eino
  dependency-version: 0.8.3
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>
Bumps [golang.org/x/image](https://github.com/golang/image) from 0.37.0 to 0.38.0.
- [Commits](golang/image@v0.37.0...v0.38.0)

---
updated-dependencies:
- dependency-name: golang.org/x/image
  dependency-version: 0.38.0
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>
Bumps [github.com/cloudwego/eino](https://github.com/cloudwego/eino) from 0.8.4 to 0.8.5.
- [Release notes](https://github.com/cloudwego/eino/releases)
- [Commits](cloudwego/eino@v0.8.4...v0.8.5)

---
updated-dependencies:
- dependency-name: github.com/cloudwego/eino
  dependency-version: 0.8.5
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
Bumps [github.com/mark3labs/mcp-go](https://github.com/mark3labs/mcp-go) from 0.45.0 to 0.46.0.
- [Release notes](https://github.com/mark3labs/mcp-go/releases)
- [Commits](mark3labs/mcp-go@v0.45.0...v0.46.0)

---
updated-dependencies:
- dependency-name: github.com/mark3labs/mcp-go
  dependency-version: 0.46.0
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>
- centralize Telegram text escaping by parse mode in util
- add RawTgText to preserve preformatted Markdown/HTML output
- route chat/chatv2 streaming, placeholder, error, and edit paths through safe helpers
- update legacy MarkdownV2/HTML reply sites to avoid Telegram entity parse failures
- add regression tests for util, chat, and chatv2 escaping/formatting behavior
- 为启用工具调用的代理自动提升最低步数限制,防止因步数不足导致任务中断
- 在步数即将耗尽时注入动态引导提示,强制代理收敛并输出最终结果
- 重构错误处理逻辑,将工具调用、图片访问及生成失败区分展示友好提示
- 改进 MCP 客户端管理,引入连接缓存机制并强制执行初始化握手协议
- 统一所有时间戳输出为 Asia/Shanghai 时区,支持中文日期格式渲染
- 新增针对代理配置逻辑、错误恢复路径及 MCP 生命周期的单元测试
- 更新 .gitignore 以排除 Go 模块缓存及 linter 临时目录
重构历史消息加载逻辑,引入 `RichHistory` 结构体以同时保留渲染后的文本上下文和原始 Telegram 消息对象。
此举旨在恢复历史消息中的图片附件,从而支持多模态输入场景下的图像分析。
主要变更包括:
- 新增 `RichHistory` 类型,整合 `ContextMessages` 和 `FullMessages`。
- 修改 `LoadHistory` 函数,增加加载完整 Telegram 消息链的逻辑以支持媒体恢复。
- 更新 `BuildMessages` 及 `buildUserMessage` 函数,使其能够利用完整的消息上下文传递多模态提示。
- 将 `promptData` 重命名为 `PromptData` 以符合导出规范。
- 新增 `image_context.go` 及相关测试文件以支持上下文处理。
dependabot Bot and others added 21 commits April 17, 2026 12:06
Bumps [github.com/meilisearch/meilisearch-go](https://github.com/meilisearch/meilisearch-go) from 0.36.1 to 0.36.2.
- [Release notes](https://github.com/meilisearch/meilisearch-go/releases)
- [Commits](meilisearch/meilisearch-go@v0.36.1...v0.36.2)

---
updated-dependencies:
- dependency-name: github.com/meilisearch/meilisearch-go
  dependency-version: 0.36.2
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
Hand-rolled CustomAgent replaces eino react.Agent to fix non-convergent tool calls, stray quotes in reasoning, truncated thinking chain after first round, and empty markdown blocks.

- new chatv2/loop.go: per-turn streaming, duplicate-call detection via sha256 of canonicalized args, soft/hard/dup-warn guidance merged into the first system message (safe for strict providers), stage markers streamed as visible progress trail between tool phases, final-round trailer when max_steps reached

- streaming: rate-limited placeholder edits via TurnContext.ShouldAllowEdit under editMu, defaultEditInterval 3s; single-point unquoteJSONString on reasoning chunks

- tools: update_progress honors the same rate limiter; when throttled returns a 'continue working' signal instead of 'ok' to avoid triggering the stop-on-done directive

- format: drop whitespace-only text to prevent empty markdown fences
- promote ad-hoc errors in loop.go to package-level static errors (errMaxStepsInvalid, errDownstreamClosed) in agent.go's var block

- wrap errMaxStepsInvalid with %w in NewCustomAgent

- add missing guidanceNone case in computeGuidanceText switch
update_progress now renders content via formatText with a configurable
style (plain/quote/collapse, defaults to expandable quote). Stage markers
from the agent loop are routed to the progress message instead of being
inlined into the final answer, and the streaming/non-streaming handlers
no longer reuse the progress placeholder for the final reply. Also drops
the streamingStarted gate that silently blocked progress updates during
streaming.
Avoid overwriting structured progress with automatic tool markers and cover MarkdownV2 wrapper escaping for progress output.
Extract repeated format and progress literals so golangci-lint passes without changing behavior.
Use testing contexts and remove stale imports so typechecking remains clean.
Bumps [github.com/mark3labs/mcp-go](https://github.com/mark3labs/mcp-go) from 0.48.0 to 0.49.0.
- [Release notes](https://github.com/mark3labs/mcp-go/releases)
- [Commits](mark3labs/mcp-go@v0.48.0...v0.49.0)

---
updated-dependencies:
- dependency-name: github.com/mark3labs/mcp-go
  dependency-version: 0.49.0
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>
Bumps [github.com/cloudwego/eino](https://github.com/cloudwego/eino) from 0.8.10 to 0.8.11.
- [Release notes](https://github.com/cloudwego/eino/releases)
- [Commits](cloudwego/eino@v0.8.10...v0.8.11)

---
updated-dependencies:
- dependency-name: github.com/cloudwego/eino
  dependency-version: 0.8.11
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
Bumps [github.com/puzpuzpuz/xsync/v4](https://github.com/puzpuzpuz/xsync) from 4.4.0 to 4.5.0.
- [Release notes](https://github.com/puzpuzpuz/xsync/releases)
- [Commits](puzpuzpuz/xsync@v4.4.0...v4.5.0)

---
updated-dependencies:
- dependency-name: github.com/puzpuzpuz/xsync/v4
  dependency-version: 4.5.0
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>
Copilot AI review requested due to automatic review settings April 28, 2026 12:48
@hugefiver hugefiver requested review from Anthony-Hoo and icceey April 28, 2026 12:49
Copy link
Copy Markdown
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR upgrades the project’s Go toolchain baseline and introduces the new chatv2 agent-based chat engine (with MCP/MCPO tool support), while also standardizing Telegram send/edit escaping via new util helpers.

Changes:

  • Bump required Go version to 1.26 across module config, CI, and Docker build tooling.
  • Add chatv2 agent mode (custom tool-calling loop, streaming, MCP/MCPO tool discovery, multimodal image context, filters) and integrate it into main.go.
  • Refactor multiple handlers to use new util.*WithError + util.RawTgText and add escaping/parse-mode normalization utilities with tests.

Reviewed changes

Copilot reviewed 65 out of 67 changed files in this pull request and generated 2 comments.

Show a summary per file
File Description
util/utils.go Introduces RawTgText, parse-mode-based escaping normalization, and new SendWithError/ReplyWithError helpers.
util/telegram_test.go Adds unit tests for parse-mode escaping, message normalization, and parse-mode extraction.
sd/sd.go Uses ReplyWithError + RawTgText and escapes prompt for MarkdownV2 in /last_prompt.
sd/cfg.go Switches help/replies to ReplyWithError + RawTgText and escapes config values for MarkdownV2.
orm/redis.go Removes AI regeneration metadata storage (AIResponseMetadata + Redis helpers).
meili/meili_search.go Minor Go style update ([]any instead of []interface{}).
meili/bot_handle.go Uses ReplyWithError + RawTgText and simplifies string building with fmt.Fprintf.
main.go Integrates chatv2 init/close, routes eligible chats to agent mode, removes reaction middleware, refactors shutdown/mc-dead allowlists.
main_test.go Adds tests for shutdown/mc-dead command allowlist helpers.
inline/bili_url_test.go Disables unstable b23.tv redirect test cases.
go.mod Bumps go directive to 1.26.0 and updates/adds dependencies for agent/MCP support.
config/config.go Splits chat configs into Chats (v1) and Agents (v2) and adds ChatEngine + ActiveChatConfig().
config/config_test.go Uses an isolated temp config copy to avoid cross-test pollution; renames/updates chat config test.
config/chat.go Adds agent/tool configuration structs, tool server config parsing, progress summary config, and agents config decoding.
config/chat_test.go Updates chat config tests to V1 naming and adds GetMaxSteps clamping tests for agents.
chatv2/types.go Adds agent runtime types: TurnContext, compiled chat, prompt data, progress state fields.
chatv2/types_test.go Tests TurnContext storage/retrieval in context.Context.
chatv2/streaming.go Implements Telegram streaming/non-stream send/edit pipeline with formatting + edit rate-limiting.
chatv2/streaming_test.go Tests streaming helpers including finalize error behavior and chunk processing.
chatv2/format.go Adds chatv2 formatting (MarkdownV2/HTML) including reasoning/payload wrappers.
chatv2/format_test.go Tests formatting escaping, wrappers, parse-mode selection, delimiter logic.
chatv2/mapping.go Maps Telegram messages/history to eino schema messages; adds CN date template field.
chatv2/mapping_test.go Tests input extraction, prompt data, schema message mapping, and subagent message building.
chatv2/filter.go Adds chatv2 filter framework (currently whitelist).
chatv2/filter_test.go Tests whitelist filter behavior and filter processing.
chatv2/memory.go Loads rich history including stored Telegram messages for multimodal context; saves responses to Redis stream/store.
chatv2/image_context.go Builds multimodal image context (album/reply/history), encodes/resizes images, and injects manifest/hints.
chatv2/image_context_test.go Tests multimodal image context composition, skipping broken images, album sibling loading, and stored message fallback.
chatv2/mcp.go Implements MCP client lifecycle, tool discovery, caching, and close handling.
chatv2/mcp_test.go Tests MCP lifecycle initialization and error wrapping.
chatv2/mcpo.go Implements MCPO OpenAPI discovery to tool definitions and HTTP invocation wrapper.
chatv2/loop.go Adds custom tool-calling agent loop with streaming every turn, dedupe detection, and directive injection.
chatv2/agent.go Builds models/tools/subagents/skills into a CustomAgent, including max-step guidance and tool error handling.
chatv2/agent_test.go Tests guidance-level calculation, friendly error messaging, and intermediate turn output suppression.
chatv2/tools_test.go Tests tool soft-failure behavior and progress formatting/state updates.
chatv2/stub_32bit.go Provides no-op stubs on 32-bit architectures where deps aren’t supported.
chatv2/chatv2.go Main chatv2 entry: compile agent configs on init, run filters/history, stream/send responses, and persist results.
chat/streaming.go Routes streaming send/edit through util helpers and RawTgText to avoid double escaping.
chat/streaming_test.go Adds regression test to ensure final Telegram text is escaped exactly once.
chat/gacha_reply.go Switches gacha config initialization to use ActiveChatConfig().
chat/filter_test.go Updates mock context signatures to use any and align with updated interfaces.
chat/context_test.go Refactors reply pointer helper usage (currently introduces a compile issue).
chat/context.go Replaces repeated Sprintf/WriteString with fmt.Fprintf for entity formatting and XML output.
chat/chat.go Sends placeholder via util reply helper (now subject to message normalization).
base/time_task.go Uses util send/reply helpers and RawTgText for HTML responses.
base/sticker.go Uses ReplyWithError + RawTgText for MarkdownV2 code block replies.
base/search-engines.go Uses ReplyWithError + RawTgText for HTML mapper replies.
base/mc.go Uses SendWithError + RawTgText for HTML output.
base/hitokoto.go Uses ReplyWithError + RawTgText for HTML output.
base/helper.go Enhances /info with per-chat bot status (shutdown/mc-dead/no-sticker/bye-world) and uses util send helper.
base/get_voice.go Uses SendWithError + RawTgText for HTML error captions.
base/decode.go Marks preformatted MarkdownV2 response as RawTgText when replying.
README.md Updates documented Go requirement to 1.26+.
README_zh-CN.md Updates documented Go requirement to 1.26+.
Dockerfile Updates build image to golang:1.26-alpine.
AGENTS.md Updates architecture doc header to Go 1.26+.
.travis.yml Updates Go version to 1.26.
.golangci.yaml Updates golangci-lint Go version to 1.26.
.gitignore Adds Go-related cache directories; normalizes custom.yaml entry.
.github/workflows/test.yml Updates setup-go version constraint to ^1.26.
.github/workflows/lint.yml Updates setup-go version constraint to ^1.26.
.github/workflows/go-build.yml Updates setup-go version constraint to ^1.26.
.github/workflows/copilot-setup-steps.yml Updates setup-go version constraint to ^1.26.
chat/reaction.go Removes message reaction regeneration implementation.
chat/reaction_test.go Removes tests for message reaction regeneration and related helpers.

Comment thread chat/chat.go
Comment thread chat/context_test.go
@icceey
Copy link
Copy Markdown
Contributor

icceey commented Apr 28, 2026

@codex

Copy link
Copy Markdown

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 8e35fc06dc

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread chatv2/tools.go
@hugefiver hugefiver merged commit 7e5acfe into master Apr 29, 2026
17 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants