OneBot 11 channel plugin for QQ messaging (NapCat/go-cqhttp). Native OpenClaw integration with private/group chat, group reactions, block streaming, voice pipeline, message batching, allowFrom filtering, shared-dir media staging, and full text-command passthrough. 116 tests.
Scanned 9/11/2026
Install to Claude Code
npx -y skills add lxyeternal/MalSkillBench --skill openclaw-onebot --agent claude-codeInstalls into .claude/skills of the current project.
Are you the author of Openclaw Onebot?
Add the live security badge to your README — it updates automatically with every re-scan.
[](https://www.skillsdirectory.com/skills/lxyeternal-openclaw-onebot)More formats (shields.io, HTML) on the badges page.
---
name: openclaw-onebot
description: "OneBot 11 channel plugin for QQ messaging (NapCat/go-cqhttp). Native OpenClaw integration with private/group chat, group reactions, block streaming, voice pipeline, message batching, allowFrom filtering, shared-dir media staging, and full text-command passthrough. 116 tests."
metadata:
openclaw:
emoji: "🐧"
type: "channel-plugin"
requires:
config: ["channels.onebot.wsUrl", "channels.onebot.httpUrl"]
bins: ["node", "npm"]
---
# OpenClaw OneBot 11 Channel Plugin
[中文](#中文) | [English](#english)
---
## 中文
源码仓库可在 [GitHub](https://github.com/xucheng/openclaw-onebot) 查看。
OpenClaw 的 **OneBot 11 协议通道插件**,让 QQ 成为 OpenClaw 一等消息通道。
支持 [NapCat](https://github.com/NapNeko/NapCatQQ)、[go-cqhttp](https://github.com/Mrs4s/go-cqhttp) 等所有兼容 OneBot 11 协议的 QQ 机器人框架。
说明:
- 插件 `id` 是 `openclaw-onebot`
- 通道 `id` 仍然是 `onebot`
- 因此 `plugins.allow` / `plugins.entries` / `plugins.installs` 使用 `openclaw-onebot`
- `channels.onebot` 保持不变
- 当前版本对齐 OpenClaw `2026.4.9` / plugin-sdk `2026.4.9`,并声明 `setupEntry`
### 功能
- 🔌 **原生通道插件** — QQ 与 Discord / Telegram / WhatsApp 同级
- 📨 私聊和群聊收发消息
- 😀 **Reaction 支持(群聊)** — 通过 NapCat `set_msg_emoji_like` 给群消息加表情回应;QQ 私聊目前不稳定/通常不生效
- 👍 **群聊自动 reaction** — 对入站群消息自动点表情,可配置开关,默认开启
- 🌊 **Block streaming** — 支持 OpenClaw 分块回复,QQ 端会连续收到多条流式消息
- 🧭 **OpenClaw 文本命令全支持** — `/status`、`/help`、`/commands`、`/model`、`/new`、`/reset` 等命令走统一文本命令链路
- 🎤 **语音完整链路** — QQ 语音 (SILK/AMR) → MP3 → STT → TTS → 发送 QQ 语音
- 📦 **消息聚合** — 连续多条消息 1.5s 内自动合并(类似 Telegram 风格)
- 🖼️ 图片、语音、文件附件发送
- 🔄 WebSocket 自动重连(指数退避)
- 🔒 可选 access token 鉴权
- 🎯 `allowFrom` 消息来源过滤(私聊/群聊/用户级别)
- ✅ 116 个测试用例全部通过
- 📈 覆盖率可通过 `npm run coverage` 复核
### 快速开始
#### 1. 安装
```bash
# 自动安装
bash scripts/install.sh
# 或手动(先在仓库根目录准备发布包)
npm install && npm run prepare:clawhub:plugin
mkdir -p ~/.openclaw/plugins/onebot
cp -r .clawhub-plugin/openclaw-onebot-plugin/* ~/.openclaw/plugins/onebot/
cd ~/.openclaw/plugins/onebot && npm install --omit=dev --omit=peer --no-package-lock --no-audit --no-fund
```
`scripts/install.sh` 会先在源码仓库生成 `.clawhub-plugin/openclaw-onebot-plugin` 精简发布包,再把这份运行时 payload 安装到 OpenClaw 目录,并自动尝试执行 `scripts/sync-openclaw-cli.mjs`,把 `--shared-dir` / `--container-shared-dir` 接到本机 OpenClaw CLI。
#### 2. 配置
在 `openclaw.json` 中添加:
```json
{
"plugins": {
"allow": ["openclaw-onebot"],
"entries": {
"openclaw-onebot": {
"enabled": true
}
}
},
"channels": {
"onebot": {
"enabled": true,
"wsUrl": "ws://your-host:3001",
"httpUrl": "http://your-host:3001",
"accessToken": "your_token",
"sharedDir": "/Users/you/napcat/shared",
"containerSharedDir": "/shared",
"groupAutoReact": true,
"groupAutoReactEmojiId": 1
}
}
}
```
说明:
- 插件配置键使用 `openclaw-onebot`
- 通道配置键使用 `channels.onebot`
- 如果你是通过本地路径/扩展目录安装插件,通常还需要在 `plugins.installs.openclaw-onebot` 中指向实际安装目录;如果用 OpenClaw 自己的插件安装流程,这一项会自动生成
也支持环境变量:
```bash
ONEBOT_WS_URL=ws://your-host:3001
ONEBOT_HTTP_URL=http://your-host:3001
ONEBOT_ACCESS_TOKEN=your_token # 可选
```
OneBot `setup` 也支持:
- `--token wsUrl,httpUrl[,accessToken[,sharedDir[,containerSharedDir]]]`
- 或 `openclaw channels add --channel onebot --shared-dir <hostPath> --container-shared-dir /shared`
- 如果 OpenClaw 升级后覆盖了 CLI dist,可在插件目录执行 `npm run sync:openclaw-cli` 重新同步参数接线
#### 3. 重启 Gateway
```bash
openclaw gateway restart
```
### 高级配置
```json
{
"channels": {
"onebot": {
"enabled": true,
"wsUrl": "ws://your-host:3001",
"httpUrl": "http://your-host:3001",
"accessToken": "your_token",
"sharedDir": "/Users/you/napcat/shared",
"containerSharedDir": "/shared",
"allowFrom": ["private:12345", "group:67890"],
"groupAutoReact": true,
"groupAutoReactEmojiId": 1
}
}
}
```
| 参数 | 说明 |
|------|------|
| `allowFrom` | 消息来源白名单 — `private:<QQ号>`、`group:<群号>`、或 `*`(允许所有) |
| `accessToken` | HTTP API 用 Bearer token,WebSocket 用 query 参数 |
| `sharedDir` | 宿主机共享目录;默认 `~/napcat/shared`,用于把语音/图片 stage 给 NapCat |
| `containerSharedDir` | 容器内共享目录;默认 `/shared`,与 `sharedDir` 对应 |
| `groupAutoReact` | 是否对入站群消息自动添加 reaction,默认 `true` |
| `groupAutoReactEmojiId` | 群聊自动 reaction 使用的 QQ emoji id,默认 `1` |
### Reaction 与流式回复
- **Reaction**
- 插件实现了 OpenClaw channel action `react`
- 通过 NapCat `set_msg_emoji_like` 对群消息或指定群消息 `message_id` 添加表情
- QQ 私聊 reaction 目前不可靠,接口可能返回成功,但不会真正落到消息上
- 入站群消息还支持自动 reaction,受 `groupAutoReact` / `groupAutoReactEmojiId` 控制,默认开启
- **流式回复**
- 这里支持的是 **OpenClaw block streaming**
- QQ 端表现为连续多条分块消息,不是“编辑同一条消息”的 draft stream
- 开启方式:
```json
{
"agents": {
"defaults": {
"blockStreamingDefault": "on"
}
}
}
```
- 可选调优:
```json
{
"channels": {
"onebot": {
"blockStreamingCoalesce": {
"minChars": 80,
"idleMs": 600
}
}
}
}
```
### 验证
- **Reaction**
- 先让群里出现一条新消息
- 从 gateway 日志里拿到 `msg=<message_id>`
- 再执行:
```bash
npm run build
npm run react-test -- --message-id <message_id> --emoji 76
```
- 当前建议只把这项验证用于群聊消息;私聊 reaction 在 QQ/NapCat 上通常不生效
- **Streaming**
- 在 OpenClaw 配置里开启 `agents.defaults.blockStreamingDefault = "on"`
- 然后在 QQ 里发一条明确要求“分段回复”的消息
- 成功时,QQ 会连续收到多条消息,日志里会出现 `deliver(block)`,最后再有 `deliver(final)`
### 语音支持(可选)
支持 QQ 语音消息的完整自动处理链路:
- **入站**:QQ 语音 (SILK/AMR) → 下载 → 转 MP3 → OpenClaw STT 转文字 → Agent 生成回复
- **出站**:Agent 回复 → TTS 生成音频 → `sendRecord` 发送 QQ 语音
**依赖**:
- `ffmpeg` — 音频格式转换
- `uv` — 运行 `pilk` 解码 SILK 格式(AMR 仅需 ffmpeg)
不需要语音功能时可以跳过这些依赖。
### 消息目标格式
- `private:<QQ号>` — 私聊消息
- `group:<群号>` — 群聊消息
- `<QQ号>` — 自动识别为私聊
### 开发
```bash
npm install
npm test # 116 tests
npm run build # 编译 TypeScript
npm run coverage # 覆盖率报告
npm run sync:openclaw-cli # 重新同步 OpenClaw CLI 的 shared-dir 参数
```
---
## English
Source code is available on [GitHub](https://github.com/xucheng/openclaw-onebot).
An [OpenClaw](https://github.com/openclaw/openclaw) **native channel plugin** that connects to [NapCat](https://github.com/NapNeko/NapCatQQ), [go-cqhttp](https://github.com/Mrs4s/go-cqhttp), or any OneBot 11 compatible QQ bot framework.
Note:
- Plugin `id`: `openclaw-onebot`
- Channel `id`: `onebot`
- Use `openclaw-onebot` in `plugins.allow` / `plugins.entries` / `plugins.installs`
- Keep `channels.onebot` unchanged
- This release targets OpenClaw `2026.4.9` / plugin-sdk `2026.4.9` and declares `setupEntry`
### Features
- 🔌 **Native channel plugin** — QQ on par with Discord / Telegram / WhatsApp
- 📨 Private & group chat (inbound + outbound)
- 😀 **Reaction support (groups)** — react to a QQ group message via NapCat `set_msg_emoji_like`; QQ private-chat reactions are currently unreliable
- 👍 **Automatic group reactions** — auto-react to inbound group messages with a configurable switch, enabled by default
- 🌊 **Block streaming** — OpenClaw partial replies arrive as multiple QQ messages
- 🧭 **Full OpenClaw text-command passthrough** — `/status`, `/help`, `/commands`, `/model`, `/new`, `/reset`, etc.
- 🎤 **Full voice pipeline** — QQ voice (SILK/AMR) → MP3 → STT → TTS → send QQ voice
- 📦 **Message batching** — auto-merge rapid messages within 1.5s (Telegram-style)
- 🖼️ Image, audio, and file attachments
- 🔄 WebSocket auto-reconnect with exponential backoff
- 🔒 Optional access token authentication
- 🎯 `allowFrom` filtering (private/group/user-level)
- ✅ 116 tests passing
- 📈 Coverage can be re-generated with `npm run coverage`
### Quick Start
#### 1. Install
```bash
# Auto install
bash scripts/install.sh
# Or manual
npm install && npm run prepare:clawhub:plugin
mkdir -p ~/.openclaw/plugins/onebot
cp -r .clawhub-plugin/openclaw-onebot-plugin/* ~/.openclaw/plugins/onebot/
cd ~/.openclaw/plugins/onebot && npm install --omit=dev --omit=peer --no-package-lock --no-audit --no-fund
```
`scripts/install.sh` prepares `.clawhub-plugin/openclaw-onebot-plugin` in the source repo first, installs that trimmed runtime payload, and then runs `scripts/sync-openclaw-cli.mjs` so the local OpenClaw CLI keeps the OneBot `--shared-dir` / `--container-shared-dir` flags wired in.
#### 2. Configure
Add to `openclaw.json`:
```json
{
"plugins": {
"allow": ["openclaw-onebot"],
"entries": {
"openclaw-onebot": {
"enabled": true
}
}
},
"channels": {
"onebot": {
"enabled": true,
"wsUrl": "ws://your-host:3001",
"httpUrl": "http://your-host:3001",
"accessToken": "your_token",
"sharedDir": "/Users/you/napcat/shared",
"containerSharedDir": "/shared",
"groupAutoReact": true,
"groupAutoReactEmojiId": 1
}
}
}
```
Notes:
- Use `openclaw-onebot` for plugin config keys
- Keep runtime channel config under `channels.onebot`
- If you install from a local path or extension directory, you may also need `plugins.installs.openclaw-onebot` pointing at the actual install directory; OpenClaw usually writes this automatically during plugin install
Or via environment variables:
```bash
ONEBOT_WS_URL=ws://your-host:3001
ONEBOT_HTTP_URL=http://your-host:3001
ONEBOT_ACCESS_TOKEN=your_token # optional
```
OneBot setup also supports:
- `--token wsUrl,httpUrl[,accessToken[,sharedDir[,containerSharedDir]]]`
- or `openclaw channels add --channel onebot --shared-dir <hostPath> --container-shared-dir /shared`
- if an OpenClaw upgrade overwrites the installed CLI dist, run `npm run sync:openclaw-cli` from the plugin directory to re-apply the flags
#### 3. Restart Gateway
```bash
openclaw gateway restart
```
### Advanced Configuration
```json
{
"channels": {
"onebot": {
"enabled": true,
"wsUrl": "ws://your-host:3001",
"httpUrl": "http://your-host:3001",
"accessToken": "your_token",
"sharedDir": "/Users/you/napcat/shared",
"containerSharedDir": "/shared",
"allowFrom": ["private:12345", "group:67890"],
"groupAutoReact": true,
"groupAutoReactEmojiId": 1
}
}
}
```
| Option | Description |
|--------|-------------|
| `allowFrom` | Whitelist — `private:<qq>`, `group:<id>`, or `*` (allow all) |
| `accessToken` | Bearer token for HTTP, query param for WebSocket |
| `sharedDir` | Host-side shared directory; defaults to `~/napcat/shared` for staging outbound media |
| `containerSharedDir` | Container-side mount path; defaults to `/shared` and should map to `sharedDir` |
| `groupAutoReact` | Whether to auto-react to inbound group messages; defaults to `true` |
| `groupAutoReactEmojiId` | QQ emoji id used for automatic group reactions; defaults to `1` |
### Reactions and Streaming Replies
- **Reactions**
- The plugin implements the OpenClaw `react` channel action
- It maps to NapCat `set_msg_emoji_like`
- Group-message reactions are supported
- QQ private-chat reactions are currently unreliable: the API may return success while no visible reaction is persisted
- Inbound group messages can also be auto-reacted, controlled by `groupAutoReact` / `groupAutoReactEmojiId`, enabled by default
- **Streaming replies**
- This plugin supports **OpenClaw block streaming**
- QQ receives multiple incremental messages instead of a single edited draft message
- Enable it with:
```json
{
"agents": {
"defaults": {
"blockStreamingDefault": "on"
}
}
}
```
- Optional coalescing hint for OneBot:
```json
{
"channels": {
"onebot": {
"blockStreamingCoalesce": {
"minChars": 80,
"idleMs": 600
}
}
}
}
```
### Verification
- **Reaction**
- Send a fresh QQ group message first
- Read the inbound `msg=<message_id>` from the gateway log
- Then run:
```bash
npm run build
npm run react-test -- --message-id <message_id> --emoji 76
```
- For now, treat this as a group-chat verification flow; private-chat reactions are not a reliable capability
- **Streaming**
- Enable `agents.defaults.blockStreamingDefault = "on"` in OpenClaw config
- Send a QQ prompt that explicitly asks for chunked or stepwise output
- Success looks like multiple QQ messages plus `deliver(block)` entries in the gateway log, followed by `deliver(final)`
### Voice Support (Optional)
End-to-end voice flow:
- **Inbound**: QQ voice (SILK/AMR) → download → MP3 → OpenClaw STT → Agent reply
- **Outbound**: Agent reply → TTS audio → `sendRecord` → QQ voice
**Dependencies**:
- `ffmpeg`
- `uv` (for SILK decoding via `pilk`; AMR only needs ffmpeg)
Skip these if you only need text and image delivery.
### Target Format
- `private:<qq_number>` — Private message
- `group:<group_id>` — Group message
- `<qq_number>` — Auto-detected as private
### Development
```bash
npm install
npm test # Run 116 tests
npm run build # Compile TypeScript
npm run coverage # Coverage report
npm run sync:openclaw-cli # Re-apply shared-dir CLI wiring after OpenClaw upgrades
```
## License
MIT
Is this your skill, or is something wrong with this listing? Request removal or report an issue. Author removals are honored within 72 hours.
No comments yet. Be the first to comment!