基于nonebotV2与go-cqhttp,写一个属于自己的QQ机器人
介绍
要写一个属于自己的QQ机器人,首先要了解QQ机器人的组成原理,不同组件实现的功能以及实现方式。
组件名 | 作用 | 描述 |
---|---|---|
go-cqhttp | 无头客户端 | 与QQ服务器连接,模拟真实QQ客户端,与自己的后端逻辑框架(即头)进行交互,实现各种消息通知的收发 |
nonebot2 | “头骨” | 接受无头客户端发送来的消息,提供封装好的方法供开发者编写处理逻辑,相当于“头骨”,起框架作用 |
这篇文章 (个系列) 会基于以上框架,自行编写处理逻辑,实现自己想要的功能
注意
nonebot是使用python3来编写的框架,后续的所有相关代码都是基于在nonebot可以运行的python环境(python3 >= 3.7)下编写与测试。虽然python相对比较容易入门,编写这样的机器人还是需要有少许编程基础知识的,完全没有任何相关概念的人尽早右上退出吧(~虽然我自己也就是个半吊子水平~)。
环境
编写环境是Windows10
,amd64
,python3.8
本文编写时所使用框架版本:nonebot 2.0.0a9
,go-cqhttp v0.9.39
安装所需环境:
nonebot:
pip3 install nonebot
go-cqhttp:
https://github.com/Mrs4s/go-cqhttp/releases
注意根据自己的系统、处理器架构来挑选对应的可执行文件
例如:
Windows系统,AMD64架构,则下载后缀为windows-amd64.exe
的文件
Linux系统,I386架构,则下载后缀为linux-i386
的文件
go-cqhttp配置
在go-cqhttp可执行文件同目录下创建config.hjson
,按照如下模板修改信息配置
/*
go-cqhttp 默认配置文件
*/
{
// QQ号
uin: 12345678
// QQ密码
password: "这里填机器人QQ密码"
// 是否启用密码加密
encrypt_password: false
// 加密后的密码, 如未启用密码加密将为空, 请勿随意修改.
password_encrypted: ""
// 是否启用内置数据库
// 启用将会增加10-20MB的内存占用和一定的磁盘空间
// 关闭将无法使用 撤回 回复 get_msg 等上下文相关功能
enable_db: true
// 访问密钥, 强烈推荐在公网的服务器设置
access_token: ""
// 重连设置
relogin: {
// 是否启用自动重连
// 如不启用掉线后将不会自动重连
enabled: true
// 重连延迟, 单位秒
relogin_delay: 3
// 最大重连次数, 0为无限制
max_relogin_times: 0
}
// API限速设置
// 该设置为全局生效
// 原 cqhttp 虽然启用了 rate_limit 后缀, 但是基本没插件适配
// 目前该限速设置为令牌桶算法, 请参考:
// https://baike.baidu.com/item/%E4%BB%A4%E7%89%8C%E6%A1%B6%E7%AE%97%E6%B3%95/6597000?fr=aladdin
_rate_limit: {
// 是否启用限速
enabled: false
// 令牌回复频率, 单位秒
frequency: 1
// 令牌桶大小
bucket_size: 1
}
// 是否忽略无效的CQ码
// 如果为假将原样发送
ignore_invalid_cqcode: false
// 是否强制分片发送消息
// 分片发送将会带来更快的速度
// 但是兼容性会有些问题
force_fragmented: false
// 心跳频率, 单位秒
// -1 为关闭心跳
heartbeat_interval: 0
// HTTP设置
http_config: {
// 是否启用正向HTTP服务器
enabled: false
// 服务端监听地址
host: 0.0.0.0
// 服务端监听端口
port: 5700
// 反向HTTP超时时间, 单位秒
// 最小值为5,小于5将会忽略本项设置
timeout: 0
// 反向HTTP POST地址列表
// 格式:
// {
// 地址: secret
// }
post_urls: {}
}
// 正向WS设置
ws_config: {
// 是否启用正向WS服务器
enabled: false
// 正向WS服务器监听地址
host: 0.0.0.0
// 正向WS服务器监听端口
port: 6700
}
// 反向WS设置
ws_reverse_servers: [
// 可以添加多个反向WS推送
{
// 是否启用该推送
enabled: true
// 反向WS Universal 地址
// 注意 设置了此项地址后下面两项将会被忽略
// 留空请使用 ""
reverse_url: ws://127.0.0.1:8080/cqhttp/ws
// 反向WS API 地址
reverse_api_url: ws://you_websocket_api.server
// 反向WS Event 地址
reverse_event_url: ws://you_websocket_event.server
// 重连间隔 单位毫秒
reverse_reconnect_interval: 3000
}
]
// 上报数据类型
// 可选: string array
post_message_format: array
// 是否使用服务器下发的新地址进行重连
// 注意, 此设置可能导致在海外服务器上连接情况更差
use_sso_address: false
// 是否启用 DEBUG
debug: true
// 日志等级
log_level: ""
// WebUi 设置
web_ui: {
// 是否启用 WebUi
enabled: false
// 监听地址
host: 127.0.0.1
// 监听端口
web_ui_port: 9999
// 是否接收来自web的输入
web_input: true
}
}
其中要注意的是反向WS相关设置
原理: nonebot框架与无头客户端的连接逻辑是nonebot启动一个Websocket服务端,然后QQ无头客户端主动连接至nonebot开启的WS服务端,并通过WS协议推送消息、调用API,对于无头客户端来说,主动连接至已有的WS服务器就算作是反向WS服务端,所以要根据nonebot的相关信息配置好反向WS相关配置
配置项 | 说明 |
---|---|
enabled | 开关,当然是填true 啊,否则下列配置直接就是无意义的 |
reverse_url | 目标服务器的url,如果你的nonebot与go-cqhttp运行在同一台主机上,这里就可以填写为ws://运行nonebot机器的地址:端口号/适配器名称/ws ,如果是同一台机器,地址可以填为127.0.0.1 端口号与适配器名称取决于nonebot的配置,后文会写。 |
运行go-cqhttp
以上配置文件配置完毕后,运行go-cqhttp的可执行文件:
Windows下:使用powershell
终端 ~(真别用CMD了)~ 打开可执行文件所在目录,执行./文件名
如果出现类似设备锁、安全验证等提示,按照提示完成步骤即可。出现成功提示后,代表你的QQ无头客户端已经成功运行了。
运行一个最小的nonebot实例
在要编写机器人处理程序的目录下新建文件,名为bot.py
,内容如下填写
import nonebot
from nonebot.adapters.cqhttp import Bot as CQHTTPBot
nonebot.init()
driver = nonebot.get_driver()
driver.register_adapter("cqhttp", CQHTTPBot) # 这里的第一个参数即为前文提到的“适配器名称”,要相互对应
nonebot.load_builtin_plugins()
if __name__ == "__main__":
nonebot.run(host="0.0.0.0",port=8080)
# 第一个参数代表监听地址,如果你的nonebot与go-cqhttp运行在同一个机器上,这里可以填写为127.0.0.1
# 如果在同一局域网则可以填写局域网所在网段网络号,例如`192.168.1.0`
# 而如果两个程序相互处于公网状态,则填写`0.0.0.0`吧,表示监听所有地址。
# 第二个参数代表端口号,与前文go-cqhttp配置中的端口号相对应。
如果没有出错,python3 bot.py
运行nonebot,nonebot 所在的控制台应该会输出类似下面的内容(两条访问日志):
09-14 21:31:16 [INFO] uvicorn | ('127.0.0.1', 12345) - "WebSocket /cqhttp/ws" [accepted]
09-14 21:31:16 [INFO] nonebot | WebSocket Connection from CQHTTP Bot 你的QQ号 Accepted!
这表示 CQHTTP 协议端已经成功地使用 CQHTTP 协议连接上了 NoneBot。
现在,尝试向你的机器人账号发送如下内容:
/echo hello world!
到这里如果一切 OK,你应该会收到机器人给你回复了 你好,世界
。这一历史性的对话标志着你已经成功地运行了一个 NoneBot 的最小实例。
结束
基本机器人的创建教程到此为止,后续文章会尝试从编写第一个自己的插件来记录。
未完待续