【Nanobot】README09_LEVEL4 添加新聊天渠道

【Nanobot】README09_LEVEL4 添加新聊天渠道

源码地址:https://github.com/HKUDS/nanobot


🎯 目标

指导如何为 nanobot 添加新的聊天渠道(如 Signal、Matrix、Line 等)。


📋 添加新 Channel 的步骤

步骤 1:创建 Channel 类

文件nanobot/channels/signal.py

python 复制代码
from nanobot.channels.base import BaseChannel
from nanobot.bus.events import InboundMessage, OutboundMessage
from nanobot.bus.queue import MessageBus
from typing import Any

class SignalChannel(BaseChannel):
    """
    Signal 消息渠道实现。

    特性:
    1. 接收 Signal 消息
    2. 发送消息到 Signal
    3. 支持流式输出(可选)
    """

    name = "signal"
    display_name = "Signal"

    def __init__(self, config: Any, bus: MessageBus):
        super().__init__(config, bus)

        # 初始化 Signal 客户端
        import signalbot

        self.bot = signalbot.Bot(config.phone_number)
        self._running = False

    async def start(self) -> None:
        """启动 Signal Bot。"""
        self._running = True

        # 注册消息处理器
        @self.bot.handler()
        async def on_message(message):
            await self._handle_message(
                sender_id=str(message.source),
                chat_id=str(message.chat_id),
                content=message.text,
                media=message.attachments or [],
            )

        # 启动 Bot
        await self.bot.start()

    async def stop(self) -> None:
        """停止 Signal Bot。"""
        self._running = False
        await self.bot.stop()

    async def send(self, msg: OutboundMessage) -> None:
        """发送消息到 Signal。"""
        await self.bot.send_message(
            chat_id=msg.chat_id,
            text=msg.content,
            quote_reply_to=msg.reply_to,
        )

步骤 2:实现流式输出(可选)

如果 Channel 支持编辑消息(如 Telegram),可以实现流式输出:

python 复制代码
async def send_delta(
    self,
    chat_id: str,
    delta: str,
    metadata: dict[str, Any] | None = None,
) -> None:
    """
    交付流式文本块。

    实现:
    1. 提取 stream_id
    2. 第一条消息 → 发送新消息
    3. 后续消息 → 编辑已有消息
    4. _stream_end → 清理缓冲区
    """
    stream_id = metadata.get("_stream_id") if metadata else None
    if not stream_id:
        return

    if metadata.get("_stream_delta"):
        # 增量内容
        if stream_id not in self._edit_buffers:
            # 发送第一条消息
            sent_msg = await self.bot.send_message(
                chat_id=chat_id,
                text=delta,
            )
            self._edit_buffers[stream_id] = sent_msg
        else:
            # 编辑已有消息
            old_msg = self._edit_buffers[stream_id]
            new_content = old_msg.text + delta
            await old_msg.edit(text=new_content)

    elif metadata.get("_stream_end"):
        # 流式结束
        if stream_id in self._edit_buffers:
            del self._edit_buffers[stream_id]

步骤 3:添加配置字段

文件nanobot/config/schema.py

ChannelsConfig 中添加字段:

python 复制代码
class ChannelsConfig(Base):
    telegram: TelegramConfig | None = None
    discord: DiscordConfig | None = None
    signal: SignalConfig | None = None  # 新增

class SignalConfig(Base):
    enabled: bool = False
    phone_number: str = ""
    allow_from: list[str] = ["*"]  # 访问控制列表

步骤 4:配置新 Channel

文件~/.nanobot/config.json

json 复制代码
{
  "channels": {
    "signal": {
      "enabled": true,
      "phoneNumber": "+1234567890",
      "allowFrom": ["*"]
    }
  }
}

步骤 5:测试新 Channel

bash 复制代码
# 启动 gateway
nanobot gateway

# 在 Signal 中发送消息给 Bot
# 应该收到回复

🔧 高级:插件化 Channel

如果希望将 Channel 作为独立插件发布(不修改核心代码),可以使用 entry_points

项目结构

复制代码
nanobot-signal/
├── nanobot_signal/
│   └── __init__.py
└── pyproject.toml

pyproject.toml

toml 复制代码
[project]
name = "nanobot-signal"
version = "0.1.0"

[project.entry-points."nanobot.channels"]
signal = "nanobot_signal:SignalChannel"

[project.dependencies]
nanobot-ai = ">=0.1.0"
signalbot = "*"

nanobot_signal/__init__.py

python 复制代码
from nanobot.channels.base import BaseChannel
from nanobot.bus.queue import MessageBus
from typing import Any

class SignalChannel(BaseChannel):
    name = "signal"
    display_name = "Signal"

    def __init__(self, config: Any, bus: MessageBus):
        super().__init__(config, bus)
        # ... 实现代码 ...

安装和使用

bash 复制代码
# 安装插件
pip install nanobot-signal

# 配置(不需要修改核心代码)
cat > ~/.nanobot/config.json << EOF
{
  "channels": {
    "signal": {
      "enabled": true
    }
  }
}
EOF

# 启动
nanobot gateway

📝 检查清单

  • 实现 BaseChannel 接口
    • start() - 启动监听
    • send() - 发送消息
    • stop() - 停止监听
  • 处理消息
    • 接收消息并调用 _handle_message()
    • 支持媒体文件(图片、文档等)
    • 支持音频转录(可选)
  • 实现流式输出(可选)
    • send_delta() - 增量更新
    • 消息编辑缓冲区
  • 添加配置字段
    • schema.py 中添加配置类
    • config.json 中启用
  • 测试
    • 基本对话功能
    • 工具调用
    • 流式输出(如果支持)
    • 访问控制(allow_from

🎯 完整示例:添加 Email Channel

Email Channel 已经内置,参考实现:

文件nanobot/channels/email.py

python 复制代码
class EmailChannel(BaseChannel):
    """电子邮件渠道。"""

    name = "email"
    display_name = "Email"

    async def start(self):
        """启动 IMAP 监听。"""
        import imaplib

        self.imap = imaplib.IMAP4_SSL(self.config.imap_server)
        self.imap.login(self.config.email, self.config.password)
        self.imap.select("INBOX")

        while self._running:
            # 轮询新邮件
            await self._check_new_emails()
            await asyncio.sleep(30)

    async def send(self, msg: OutboundMessage):
        """发送邮件。"""
        import smtplib
        from email.message import EmailMessage

        email = EmailMessage()
        email["From"] = self.config.email
        email["To"] = msg.chat_id
        email.set_content(msg.content)

        with smtplib.SMTP_SSL(self.config.smtp_server) as smtp:
            smtp.login(self.config.email, self.config.password)
            smtp.send_message(email)

📚 相关文件

  • nanobot/channels/base.py - BaseChannel 抽象基类
  • nanobot/channels/telegram.py - Telegram 实现示例
  • nanobot/channels/discord.py - Discord 实现示例
  • nanobot/config/schema.py - 配置模式

🎉 完成分析

全部 9 个分析单元已完成!

生成的文档列表

  1. ✅ README01_LEVEL1_项目架构与目录说明.md
  2. ✅ README02_LEVEL2_Agent核心循环设计.md
  3. ✅ README03_LEVEL2_工具系统架构.md
  4. ✅ README04_LEVEL2_提供商系统设计.md
  5. ✅ README05_LEVEL2_渠道系统设计.md
  6. ✅ README06_LEVEL3_消息流转深度追踪.md
  7. ✅ README07_LEVEL3_会话管理与记忆.md
  8. ✅ README08_LEVEL4_添加新LLM提供商.md
  9. ✅ README09_LEVEL4_添加新聊天渠道.md

文档位置.aitalk/ 目录

建议阅读顺序:README01 → README02 → ... → README09

相关推荐
xhbh6667 小时前
光纤端口映射完全教程:光猫虚拟服务器配置+免费穿透工具实战
运维·服务器·网络·智能路由器·端口映射·流量端口转发·ssh端口转发
Mr.朱鹏7 小时前
9-检索增强生成RAG详解
python·gpt·langchain·大模型·llm·rag
shehuiyuelaiyuehao7 小时前
算法27,二维前缀和
开发语言·python·算法
深念Y7 小时前
网络多播与广播:到底能不能节省带宽和流量?
网络·直播·p2p·点对点·多播·流量·单播
随身数智备忘录7 小时前
MES安灯管理程序这套方法,专治MES安灯管理程序中的流程空转
大数据·服务器·网络
IpdataCloud7 小时前
企业安全运营中,如何用IP风险识别工具快速发现异常终端?操作指南
开发语言·php
码界筑梦坊7 小时前
125-基于Flask的客户购物偏好数据可视化分析系统
python·信息可视化·flask·毕业设计
兩尛7 小时前
C++多线程,并发
java·开发语言
测试秃头怪7 小时前
接口测试与常用接口测试工具详解
自动化测试·软件测试·python·测试工具·职场和发展·测试用例·接口测试