JavBus 插件

对接自部署的 javbus-api,在群聊中完成番号查询、关键词搜索与最新影片获取。
作者: 蜥蜴


⚠️ 免责声明

本插件仅用于学习与研究目的。请勿配置于 QQ 或其他国内社交平台,由此产生的后果由使用者自行承担。


背景

在相关社群中查询番号信息,传统流程通常为:

  1. 打开浏览器访问 JavBus 网站
  2. 输入番号或关键词搜索
  3. 手动复制磁力链接
  4. 截图封面与预览图并转发至群聊

该流程操作繁琐,尤其在移动端不便。koishi-plugin-javbus-lizard 将上述步骤整合为一条聊天指令,可在群聊或私聊中直接完成查询。


工具定位

koishi-plugin-javbus-lizard 是一款基于 Koishi 框架的查询插件,当前版本为 4.4.0,依赖 Koishi ^4.18.0。

能力 说明
番号查询 通过番号获取影片详情与磁力链接
关键词搜索 按女优名或关键词搜索影片列表
最新影片 获取最新上架的有码 / 无码影片
磁链管理 支持按中文字幕、大小排序,并可限制数量
封面与预览 可选返回封面图与预览截图
合并转发 在 onebot 平台支持合并转发

安装

前置条件

  • 已搭建并可正常运行的 Koishi 项目(koishi-app)
  • 已部署 javbus-api 后端服务,并可从 Koishi 所在服务器访问
  • 部署环境具备访问 JavBus 网站的网络条件(必要时配置代理)

步骤一:部署后端 API

本插件不自带数据源,需先部署 javbus-api。以源码方式部署为例:

1
2
3
4
git clone https://github.com/ovnrain/javbus-api.git
cd javbus-api
npm install
npm start

服务默认监听 http://localhost:3000。部署完成后,需在浏览器或命令行中访问该地址以确认接口可用。

若 Koishi 与 javbus-api 部署于同一台机器,可将 api 配置为 http://localhost:3000;若分机部署,需使用内网或公网可达地址。

步骤二:通过插件市场安装(推荐)

  1. 启动 Koishi 项目,打开控制台(默认地址 http://localhost:5140)。
  2. 进入左侧「插件市场」。
  3. 在搜索框中输入 javbus-lizard。
  4. 找到插件后点击「添加」,Koishi 会自动完成依赖安装与配置写入。

步骤三:通过 npm 安装

在 Koishi 项目根目录执行:

1
npm install koishi-plugin-javbus-lizard

随后在 koishi.yml 中手动添加配置:

1
2
3
4
5
6
7
plugins:
javbus-lizard:
api: 'http://localhost:3000'
count: 5
cover: false
preview: false
magnet: true

步骤四:通过 yarn / pnpm 安装

若项目使用 yarn 或 pnpm,可执行:

1
2
3
4
5
# yarn
yarn add koishi-plugin-javbus-lizard

# pnpm
pnpm add koishi-plugin-javbus-lizard

验证安装

在任意已接入机器人的聊天窗口输入:

1
jav

若不携带番号,机器人返回「请提供番号!可用的子指令有:jew 获取最新影片、jkw 关键词搜索影片」,则说明插件已成功加载。


配置

配置项在 Schema 中分为「基础设置」「获取设置」与「磁链设置」三组。

基础设置

配置项 类型 默认值 取值范围 说明
api string 必填 — API 地址,形如 https://aaa.bbb.ccc
count number 5 1 ~ 30 每次搜索最多获取的影片数量
ifPre boolean false — 是否展示未发行影片(仅影响 jkw 与 jew)
ifForward boolean false — 是否合并转发(仅 onebot 平台)
debug boolean false — 是否输出调试日志

获取设置

配置项 类型 默认值 说明
cover boolean false 是否返回封面图
preview boolean false 是否返回预览截图
magnet boolean true 是否返回磁力链接

磁链设置

仅在 magnet: true 时生效。

配置项 类型 默认值 取值 说明
magnetPriority string default default / cn / size-asc / size-desc 磁链排序方式
magnetCount number 5 -1 或 1 以上 返回的磁链数量,-1 表示全部

配置示例

1
2
3
4
5
6
7
8
9
10
11
12
plugins:
javbus-lizard:
api: 'http://localhost:3000'
count: 5
ifPre: false
ifForward: false
debug: false
cover: true
preview: true
magnet: true
magnetPriority: 'cn'
magnetCount: 3

magnetCount 的合法取值只有 -1 与不小于 1 的整数两种。Schema 中以 Schema.union([Schema.const(-1), Schema.number().min(1)]) 声明,因此不存在 0 的输入方式。


使用流程

父指令为 jav,子指令为 jkw 与 jew。

指令列表

指令 说明 示例
jav <番号> 通过番号查询影片详情 jav ABP-123
jav.jkw <关键词> 关键词搜索影片 jav.jkw 三上悠亚
jav.jew [无码] 获取最新影片 jav.jew / jav.jew 无码

流程一:番号查询

步骤 1:发送番号查询指令

1
jav ABP-123

步骤 2:接收影片详情

机器人返回影片基础信息与磁力链接列表:

1
2
3
4
5
6
7
8
9
10
标题:ABP-123 〇〇〇
发行日期:2024-01-15
影片时长:120分钟
女优:高桥しょう子

磁链[1]大小:2.5GB
magnet:?xt=urn:btih:...

磁链[2]大小:1.8GB
magnet:?xt=urn:btih:...

步骤 3:接收封面与预览

  • cover: true 时,机器人随后发送封面图
  • preview: true 时,机器人随后发送预览截图;开启 ifForward 时以合并转发方式发送预览

步骤 4:异常处理

若番号不存在或影片未发行,机器人返回:

1
番号错误或影片暂未发行

可尝试开启 ifPre: true 后重新查询。


流程二:关键词搜索

步骤 1:发送搜索指令

1
jav.jkw 三上悠亚

步骤 2:接收结果列表

机器人按 count 限制逐条返回影片信息:

1
2
3
4
5
6
标题:SSIS-001 三上悠亚 〇〇
发行日期:2024-02-01
标签:高清, 独占

番号:SSIS-001
[封面图]

开启 ifForward 后,上述结果会合并为一条转发消息发送。

步骤 3:无结果处理

若无匹配结果,机器人返回「未找到相关影片」。


流程三:获取最新影片

步骤 1:发送最新影片指令

获取最新有码影片:

1
jav.jew

获取最新无码影片:

1
jav.jew 无码

若参数为「无码」以外的内容,机器人返回「如需关键词搜索请使用指令 “jkw”,本指令仅支持参数 “无码”」。

步骤 2:接收结果列表

返回格式与关键词搜索一致,逐条展示影片标题、发行日期、标签、番号与封面图。


流程四:合并转发

在 onebot 平台开启 ifForward 后,插件会将多条结果合并为一条转发消息发送。

执行过程

  1. 机器人先发送提示:共 N 条消息合并转发中...
  2. 合并转发完成后,撤回上述提示

若当前平台不是 onebot,机器人发送提示「当前平台(xxx)暂不支持合并转发功能,将顺序发送」,然后逐条顺序发送。


使用场景

场景一:群聊内快速查询

群聊中提及某个番号时,可直接通过 jav <番号> 获取影片详情与磁链,并分享封面与预览。

场景二:按女优或标签检索

通过 jav.jkw <关键词> 检索特定女优或标签的作品,结合 count 与 magnetPriority 控制结果的范围与顺序。

场景三:日常追新

通过 jav.jew 或 jav.jew 无码 查看最新上架影片。若希望包含预告中的未发行影片,可开启 ifPre。


技术实现

技术栈

技术 用途
Koishi 机器人框架
TypeScript 开发语言
javbus-api 后端数据接口
form-data 依赖项(package.json 中声明)

与接口的交互

插件通过 api 配置拼接访问自部署的 javbus-api,涉及的端点为:

端点 用途
/api/movies/{id} 影片详情
/api/magnets/{id}?gid={gid}&uc={uc} 磁力链接列表
/api/movies 最新有码影片
/api/movies?type=uncensored 最新无码影片
/api/movies?magnet=all 最新有码影片(含未发行)
/api/movies?magnet=all&type=uncensored 最新无码影片(含未发行)
/api/movies/search?keyword={keyword} 关键词搜索
/api/movies/search?magnet=all&keyword={keyword} 关键词搜索(含未发行)

ifPre 通过切换 magnet=all 参数来控制是否包含未发行影片。

核心设计

影片详情查询

番号查询分为两步:先请求影片详情,再根据详情中的 gid 与 uc 请求磁力链接列表。

1
2
3
4
5
6
7
8
9
10
async function fetchMovie(number: string): Promise<MovieDetail> {
const movieUrl = `${config.api}${api.movie}${number}`;
const movieData = await ctx.http.get(movieUrl);
// ...
if (config.magnet) {
const magnetUrl = `${config.api}${api.magnet}${id}?gid=${gid}&uc=${uc}`;
const magnetList = await ctx.http.get(magnetUrl);
// ...
}
}

磁链中文字幕识别

插件通过标题中的关键字判断是否为中文字幕资源:

1
2
3
magnetList.forEach((item) => {
item.cn = /(?:ch|C)/i.test(item.title);
});

该正则为不区分大小写地匹配 ch 或 C。因此「中文字幕优先」的实际含义是匹配到上述字符即视为中文字幕资源,并非严格匹配「中文字幕」四个字。

磁链排序与数量限制

排序依据 magnetPriority 执行:

1
2
3
4
5
6
7
if (config.magnetPriority === 'cn') {
magnetList.sort((a, b) => Number(b.cn) - Number(a.cn));
} else if (config.magnetPriority === 'size-asc') {
magnetList.sort((a, b) => a.numberSize - b.numberSize);
} else if (config.magnetPriority === 'size-desc') {
magnetList.sort((a, b) => b.numberSize - a.numberSize);
}

随后按 magnetCount 截取:-1 时取全部,否则取前 N 条。

图片获取与防盗链

封面与预览截图通过 fetchImage 下载,并将 JavBus 详情页地址作为 referer 头,以通过图片服务器的防盗链检查:

1
2
3
4
await ctx.http.get(url, {
headers: { referer },
responseType: 'arraybuffer',
});

图片以 base64 内联方式嵌入消息,避免直接依赖外链可达性。若解析失败,插件返回 null 并记录日志,但不影响文字部分的发送。

合并转发

在 onebot 平台,插件通过构造 forward 类型消息实现合并转发:

1
2
3
4
5
const forwardMessage = h('message', {
forward: true,
children: forwardMessages,
});
await session.send(forwardMessage);

非 onebot 平台会自动降级为逐条顺序发送,并给出对应提示。

错误处理

接口错误在插件内被归纳为三类,并按类型返回统一文案:

匹配规则 返回文案
Not Found 番号错误或影片暂未发行
fetch failed 服务器网络波动,请重试
其他 发生未知错误,请查看日志

上述文案均由插件本地生成,与接口返回的原始错误信息无关。


注意事项

1. 后端 API 依赖

本插件不自带数据源,必须自行部署 javbus-api。部署前需确认:

  • Node.js 环境已就绪
  • 部署环境可访问 JavBus 网站,必要时配置代理
  • API 端口对 Koishi 所在服务器可达

2. 图片下载依赖后端

封面与预览图的下载同样经过后端 API 或 JavBus 图片服务器。若网络不通或图片服务器限制访问,可能出现图片缺失。

3. 磁链有效性

磁力链接的有效性取决于种子资源本身,与插件无关。

4. 合并转发限制

ifForward 仅在 onebot 平台生效。其他平台会自动降级为顺序发送,属于预期行为。

5. 平台选择

请勿将本插件配置于 QQ 或其他国内社交平台。建议部署于自建的、受控的机器人实例中。


常见问题

Q1:提示「番号错误或影片暂未发行」?

可能原因包括:

  • 输入的番号格式不正确
  • 该影片确实未收录于 JavBus
  • 影片处于未发行状态

可尝试开启 ifPre: true 后重新查询。

Q2:提示「服务器网络波动,请重试」?

说明插件在请求过程中遭遇网络异常。可检查:

  • javbus-api 是否正常运行
  • 部署环境能否访问 JavBus 网站
  • Koishi 所在服务器能否访问 api 配置的地址

Q3:图片加载不出来?

封面与预览图依赖 JavBus 图片服务器。若图片服务器出现限制或网络不稳定,可能导致图片缺失。不影响文字内容的返回。

Q4:合并转发没有生效?

请确认当前平台为 onebot,且 ifForward: true。非 onebot 平台会自动降级为顺序发送,并给出「暂不支持合并转发功能」的提示。

Q5:搜索不到结果?

可能原因包括:

  • 关键词与实际内容不匹配
  • 后端 API 暂时不可用
  • 相关资源未收录于 JavBus

Q6:磁链数量与预期不符?

请检查 magnetCount 的取值。合法输入只有 -1(全部)与不小于 1 的整数,0 不被 Schema 接受。

Q7:为什么「中文字幕优先」排序后仍有非中文字幕排在前面?

该排序依据的是标题中是否包含 ch 或 C 字符(不区分大小写),并非严格匹配「中文字幕」四个字。若某资源标题恰好包含上述字符但不含中文字幕,仍会被标记为中文字幕资源。


开发计划

  • 支持更多平台的合并转发
  • 添加影片收藏与订阅功能
  • 支持自定义搜索过滤条件
  • 优化图片缓存机制
  • 支持多 API 负载均衡
  • 添加数据统计功能

获取工具