botuniverse / onebot

OneBot:统一的聊天机器人应用接口标准

Home Page:https://onebot.dev

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

多机器人账号连接复用

abrahum opened this issue · comments

摘要

为 OneBot 标准添加单 OneBot Connect 连接上多机器人账号支持。

动机

以便于实现 OneBot 多账号控制器、单个实现进程登录多个账号等。

具体描述

基本数据类型

  • 页面移动到“OneBot Connect - 数据协议”

  • 新增 Self 类型,形如:

    {
        "platform": "qq",
        "user_id": "1234567"
    }

OneBot Connect - 通信方式

  • HTTP Webhook 和反向 WebSocket 去掉 X-Self-IDX-Platform

OneBot Connect - 数据协议 - 事件

  • 移除 self_idplatform 字段
  • 除元事件外,新增 self 字段,类型 Self

OneBot Connect - 数据协议 - 动作请求

  • 除元动作外,新增 self 字段,单 bot 时可选,多 bot 时必须

OneBot Connect - 数据协议 - 动作响应

  • 新增返回码 10101 Who Am I:未指定机器人账号,备注“OneBot 实现在单个 OneBot Connect 连接上支持多个机器人账号,但动作请求未指定要使用的账号”

接口定义 - 元接口 - 元动作

  • get_status 接口响应修改为:

    {
        "status": "ok",
        "retcode": 0,
        "data": {
            "good": true,
            "bots": [
                {
                    "self": {
                        "platform": "qq",
                        "user_id": "1234567"
                    },
                    "online": true,
                    "qq.status": "信号弱"
                },
                {
                    "self": {
                        "platform": "tg",
                        "user_id": "2345678"
                    },
                    "online": true
                }
            ]
        },
        "message": ""
    }

局限

替代方案

下面是一种修改更大的方案:

  • 动作请求:

    {
        "id": "...", // 原 echo
        "self": {
            "platform": "qq",
            "user_id": "1234567"
        },
        "name": "get_user_info",
        "params": {
            // ...
        }
    }
  • 事件:

    {
        "id": "...",
        "self": {
            "platform": "qq",
            "user_id": "1234567"
        },
        "time": 123.456,
        "name": "message.private",
        "data": {
            // 具体的事件数据
        }
    }

如果如果这个方案以后证明确实好的话,或许可以在下一个 OneBot 大版本引入,OneBot 12 先不引入了。

约定 action params 内可扩展字段 self_id 的作用为指定当前 OBC 上执行该 action 的 Bot 的 self_id

这个建议赞同,影响不大,对现有情况也可以做兼容。

如果当前连接存在复数 Bot,应当返回 action failed response

此问题我个人感觉应该由实现进行定义,不在标准里特别说明。但对于标准本身而言,我认为标准内应该对其定义一个新的独立错误码给予提示和引导。

在 action 根字段与 type params echo 同级增加 self_id 可选字段

Action 理论上是包含所有通信的请求形式,而不是机器人特有的动作,比如未来扩展很可能都会有关于实现本身的状态返回,这时带上 self_id 字段显然是不应该的,而且理论上来说,单 OBC 多 Bot 支持最终完成的情况下,self_id 也应该和 user_id 一样属于一个必需的参数值。

  • 如果当前连接存在复数 Bot,应当返回 action failed response

或许可以直接定义一个 error code 来应对这种情况,10008 Missing Self ID 听起来不错。

get_status 响应数据中移除 online 字段,增加类型为 String 的 status 字段,与增加的 event.meta.status_update 事件中的 status 字段保持一致

增加 event.meta.status_update 事件,该事件仅持有一个类型为 String 的 status 字段,并约定 online 为 Bot 上线(可以执行 action),offline 为 Bot 离线(不再具备执行 action 能力)。status 字段可以接收其他扩展状态。

我更建议我们保留 online 为 bool,表示是否能够连通 IM 服务器(也就是收发消息),然后有多种不同在线状态的平台自行扩展字段,不然的话如果实现定义了特别的字符串 variant,用户那边判断就会有点麻烦。

由于单个 OBC 上允许存在多个不同 self_id 的 Bot,因此应当去除 X-Self-ID header,OBC 连接后的 Bot 增删可以由 event.meta.status_update 事件判断。

同意,但同时我们需要能够通过某种方式获取现在所有的 bot 列表。

一个提议:由于 get_status 是元动作,我们其实可以假设所有元动作在单 OBC 多 bot 的情况下都不需要指定 self_id,于是我们就可以把 get_status 返回值改为:

{
    "status": "ok",
    "retcode": 0,
    "data": {
        "good": true,
        "bots": {
            "12345": {
                "online": true,
            }
        }
    },
    "message": ""
}

这样就可以优雅地获取 bot 列表。

替代方案是新增一个获取 bot 列表的元动作、同时 get_status 要求 self_id,看起来不是非常简约。

还需要考虑 X-Impl 与 X-Platform header 是否还有必要存在

那有没有可能直接用 (platform, impl, self_id) 三元组?这样也可以在一个 OBC 连接上调用不同平台同名的 self id。

基本赞成 rc 的意见。

还需要考虑 X-Impl 与 X-Platform header 是否还有必要存在

那有没有可能直接用 (platform, impl, self_id) 三元组?这样也可以在一个 OBC 连接上调用不同平台同名的 self id。

我的考虑是同时去除这三个 header,应该以 meta.status_update 中的相应字段提供该信息。

相应的需要补充说明,在新的链接建立时应当推送 meta.status_update 事件(也就是需要维护链接上的状态信息)

RFC 内容已在上面原文更新