@eogee-tech/eosearch 0.2.0 → 0.2.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +210 -208
- package/build-cli/cli.js +206 -99
- package/build-cli/updateCheck.js +140 -0
- package/package.json +2 -1
- package/skill/SKILL.md +214 -0
- package/skill/eosearch-video/SKILL.md +119 -0
- package/skill/eosearch-video/helpers/grab.sh +58 -0
package/skill/SKILL.md
ADDED
|
@@ -0,0 +1,214 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: eosearch
|
|
3
|
+
description: EoSearch(eosearch)联网搜索服务接入与使用指南。当用户要求联网搜索、查资料、查最新信息、深度调研某个主题,或提到 EoSearch / eosearch 搜索服务时使用本技能完成服务接入与工具调用。
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
# EoSearch 搜索服务接入与使用
|
|
7
|
+
|
|
8
|
+
EoSearch 是面向 AI Agent 的联网搜索服务:意图路由自动选择搜索引擎,多引擎结果融合去重并给出透明评分(score + 排序理由),支持一步到位的深度检索(搜索 + 正文抓取 + token 预算控制)。
|
|
9
|
+
|
|
10
|
+
本技能即 EoSearch 能力的开通入口:安装本技能并完成一次配置(填入API密钥)后,Agent 即具备完整的联网搜索能力。服务提供两种接口面:CLI 命令行客户端(推荐,`eosearch` 命令)与 MCP(Streamable HTTP),底层为同一个服务端、共用同一份配额,按场景任选其一即可。
|
|
11
|
+
|
|
12
|
+
## 第一步:准备接入信息
|
|
13
|
+
|
|
14
|
+
| 项目 | 说明 |
|
|
15
|
+
|------|------|
|
|
16
|
+
| 服务地址 | `https://eogee.com/search/v1/mcp`(以服务公告为准) |
|
|
17
|
+
| API Key | API密钥,在 eogee.com 个人中心获取 |
|
|
18
|
+
| 接入方式 | CLI 命令行(推荐)或 MCP 客户端 |
|
|
19
|
+
|
|
20
|
+
## 第二步:完成接入(CLI 优先,MCP 备选)
|
|
21
|
+
|
|
22
|
+
若用户尚未提供密钥,先请其到 eogee.com 个人中心「API密钥」申请,把密钥发给你后再完成配置。注册名统一使用小写 `eosearch`,产品展示名写作 EoSearch。
|
|
23
|
+
|
|
24
|
+
### 方式一:CLI 命令行客户端(推荐)
|
|
25
|
+
|
|
26
|
+
适合所有能用 Shell 的环境(WorkBuddy、ZCode、Codex、CI、一次性沙箱等),不依赖任何 MCP 客户端配置,装完即用。
|
|
27
|
+
|
|
28
|
+
1. **安装**:
|
|
29
|
+
|
|
30
|
+
```bash
|
|
31
|
+
npm install -g @eogee-tech/eosearch
|
|
32
|
+
```
|
|
33
|
+
|
|
34
|
+
无法全局安装时可用免安装形式 `npx @eogee-tech/eosearch <子命令>`(每次调用有解包延迟,多轮使用建议全局安装)。
|
|
35
|
+
|
|
36
|
+
2. **技能落位**(推荐,让支持技能发现的客户端在会话中自动触发本指引):
|
|
37
|
+
|
|
38
|
+
```bash
|
|
39
|
+
eosearch skill install
|
|
40
|
+
```
|
|
41
|
+
|
|
42
|
+
把随包分发的技能文档复制到客户端技能目录:默认 `~/.zcode/skills/eosearch/`(ZCode 用户级技能目录),其他客户端用 `--dir <path>` 指定其技能目录;加 `--video` 同时安装 eosearch-video 视频技能。重复执行即把文档升级为与 CLI 同版本。若你正在阅读本文档,说明技能已就位,此步可跳过。
|
|
43
|
+
|
|
44
|
+
3. **配置密钥**(二选一,环境变量优先):
|
|
45
|
+
|
|
46
|
+
```bash
|
|
47
|
+
# bash / zsh
|
|
48
|
+
export EOSEARCH_API_KEY=你的API密钥
|
|
49
|
+
```
|
|
50
|
+
|
|
51
|
+
```powershell
|
|
52
|
+
# Windows PowerShell(当前会话)
|
|
53
|
+
$env:EOSEARCH_API_KEY = "你的API密钥"
|
|
54
|
+
# 永久生效
|
|
55
|
+
setx EOSEARCH_API_KEY "你的API密钥"
|
|
56
|
+
```
|
|
57
|
+
|
|
58
|
+
或在用户目录建配置文件 `~/.eosearchrc`:`{"apiKey":"你的API密钥"}`。密钥只从环境变量或该配置文件读取,CLI 不提供密钥的命令行参数入口,避免密钥进入 Shell 历史与进程列表。
|
|
59
|
+
|
|
60
|
+
4. **自检**:`eosearch whoami`,输出"密钥有效,服务连接正常"即接入完成;401 回到上一步核对密钥。
|
|
61
|
+
|
|
62
|
+
### 方式二:MCP 客户端配置
|
|
63
|
+
|
|
64
|
+
请求头 `X-API-Key` 用于身份认证。把下方示例中的「你的API密钥」替换为真实密钥即可。以下方式任选其一。
|
|
65
|
+
|
|
66
|
+
#### ZCode / Claude Code(命令行注册)
|
|
67
|
+
|
|
68
|
+
```bash
|
|
69
|
+
claude mcp add --transport http eosearch https://eogee.com/search/v1/mcp --header "X-API-Key: 你的API密钥"
|
|
70
|
+
```
|
|
71
|
+
|
|
72
|
+
#### 通用 JSON 配置(Cherry Studio、Cursor、VS Code 等)
|
|
73
|
+
|
|
74
|
+
```json
|
|
75
|
+
{
|
|
76
|
+
"mcpServers": {
|
|
77
|
+
"eosearch": {
|
|
78
|
+
"type": "http",
|
|
79
|
+
"url": "https://eogee.com/search/v1/mcp",
|
|
80
|
+
"headers": {
|
|
81
|
+
"X-API-Key": "你的API密钥"
|
|
82
|
+
}
|
|
83
|
+
}
|
|
84
|
+
}
|
|
85
|
+
}
|
|
86
|
+
```
|
|
87
|
+
|
|
88
|
+
配置完成后重启客户端,确认 `eosearch_search`、`eosearch_batch_search`、`eosearch_fetch`、`eosearch_deep_search` 四个工具已出现。
|
|
89
|
+
|
|
90
|
+
## 第三步:自检(配置完成后立即执行)
|
|
91
|
+
|
|
92
|
+
1. **CLI 接入自检**:`eosearch whoami` 返回"密钥有效"即完成(退出码 0)。
|
|
93
|
+
2. **MCP 接入自检**:确认客户端工具列表已出现四个 `eosearch_*` 工具;或做握手检查(验证服务可达、密钥有效):
|
|
94
|
+
|
|
95
|
+
```bash
|
|
96
|
+
curl -s -o /dev/null -w "%{http_code}" https://eogee.com/search/v1/mcp \
|
|
97
|
+
-H "Content-Type: application/json" \
|
|
98
|
+
-H "Accept: application/json, text/event-stream" \
|
|
99
|
+
-H "X-API-Key: 你的API密钥" \
|
|
100
|
+
-d '{"jsonrpc":"2.0","id":1,"method":"initialize","params":{"protocolVersion":"2025-03-26","capabilities":{},"clientInfo":{"name":"selfcheck","version":"0.0.0"}}}'
|
|
101
|
+
```
|
|
102
|
+
|
|
103
|
+
返回 `200` 即密钥有效、服务正常;`401` 表示密钥无效或请求头拼写有误,回到第二步核对;超时或 5xx 稍后重试。
|
|
104
|
+
|
|
105
|
+
3. **实调检查**:CLI 跑 `eosearch search "hello" --limit 3`,或 MCP 实际调用一次 `eosearch_search`(如 `query: "hello"`),返回带 `score` 的结果列表即接入完成。
|
|
106
|
+
|
|
107
|
+
## 第四步:选择正确的调用方式与工具
|
|
108
|
+
|
|
109
|
+
CLI 接入时按场景直接执行命令(均支持 `--json` 获取机器可读输出):
|
|
110
|
+
|
|
111
|
+
| 场景 | CLI 命令 | 说明 |
|
|
112
|
+
|------|---------|------|
|
|
113
|
+
| 找资料、找来源 | `eosearch search "<关键词>"` | 加 `--freshness week` 做时效过滤、`--limit 5` 控制条数 |
|
|
114
|
+
| 多个独立查询 | `eosearch batch "<q1>" "<q2>"` | 一次并行至多 5 条,配额计 1 次 |
|
|
115
|
+
| 已有网址,读正文 | `eosearch fetch <url>` | 自动适配 CSDN/掘金/知乎/GitHub,`--json` 时输出 `{url, content}` |
|
|
116
|
+
| 要可直接引用的调研结论 | `eosearch deep "<主题>"` | `--top-n` 控制读源数量,任务慢可加 `--timeout 300` |
|
|
117
|
+
| 验证密钥/服务状态 | `eosearch whoami` | 握手不计配额 |
|
|
118
|
+
|
|
119
|
+
CLI 退出码约定:0 成功;1 业务空结果;2 用法错误(参数写错,读 stderr 修正);3 鉴权失败(核对密钥);4 配额限流(稍后重试);5 服务不可用或执行失败。报错固定三段式(错误/原因/下一步),按"下一步"提示修正后重试即可。
|
|
120
|
+
|
|
121
|
+
MCP 接入时按场景选择工具:
|
|
122
|
+
|
|
123
|
+
| 场景 | 使用工具 | 说明 |
|
|
124
|
+
|------|---------|------|
|
|
125
|
+
| 找资料、找来源、看大家都怎么说 | `eosearch_search` | 快,返回链接列表带评分 |
|
|
126
|
+
| 多个独立查询(多意图调研、核查多个说法、横向对比) | `eosearch_batch_search` | 一次调用并行跑多条搜索(至多 5 条),省轮次省 token,配额只计 1 次 |
|
|
127
|
+
| 已有具体网址,要读正文 | `eosearch_fetch` | 自动适配 CSDN/掘金/知乎/GitHub,返回清洗后的正文 |
|
|
128
|
+
| 要直接可用的调研结论/上下文 | `eosearch_deep_search` | 一步完成搜索、选源、抓正文、按预算输出摘录 |
|
|
129
|
+
| 找视频源(后续下载到本机) | `eosearch_search` | "视频"类查询自动走视频意图路由;已验证平台的视频页结果带 `isVideoPage`/`videoPlatform` 标记 |
|
|
130
|
+
|
|
131
|
+
调用原则:
|
|
132
|
+
|
|
133
|
+
1. 需要背景知识或结论时**优先用 `eosearch_deep_search`**,一次调用胜过多次 search + fetch 往返,省时间也省 token。
|
|
134
|
+
2. 有多个独立查询时**合并成一次 `eosearch_batch_search`**(如 `queries: ["量子计算现状", "IBM 股价", "相关ETF"]`),不要拆成多次 search。
|
|
135
|
+
3. 只要链接列表时用 `eosearch_search` 或 `eosearch_batch_search`,配 `format: "markdown"` 更省 token。
|
|
136
|
+
4. 关注时效(新闻、版本发布、近期讨论)时带 `freshness` 参数(`day`/`week`/`month`/`year`);需要限定或排除某些站点时用 `includeDomains` / `excludeDomains`(如 `excludeDomains: ["csdn.net"]`)。
|
|
137
|
+
5. 从 search 结果里挑目标后,用 `eosearch_fetch` 读具体页面。
|
|
138
|
+
|
|
139
|
+
## 保持更新
|
|
140
|
+
|
|
141
|
+
CLI 每次启动会在后台最多每日检查一次 npm 新版本(缓存 `~/.eosearch-update.json`),有更新时在 stderr 提示。看到提示后执行:
|
|
142
|
+
|
|
143
|
+
```bash
|
|
144
|
+
npm i -g @eogee-tech/eosearch
|
|
145
|
+
eosearch skill install # 刷新主技能文档;装了视频技能再加 --video
|
|
146
|
+
```
|
|
147
|
+
|
|
148
|
+
`CI` 或 `NO_UPDATE_NOTIFIER=1` 环境不检查,`--json` 调用不提示;技能文档无需自己再写版本检查。
|
|
149
|
+
|
|
150
|
+
## 结果解读
|
|
151
|
+
|
|
152
|
+
### search 结果字段
|
|
153
|
+
|
|
154
|
+
- `score`:0-100 的综合质量分,排序依据,分数越高越值得先读。
|
|
155
|
+
- `engines`:哪些搜索引擎返回了这条结果。多个引擎同时返回(如 `["csdn", "bing"]`)说明该来源可信度较高。
|
|
156
|
+
- `reasons`:人类可读的排序理由,例如:
|
|
157
|
+
- `#1 on csdn` — 在 csdn 引擎中排名第一
|
|
158
|
+
- `also found by bing` — 同时被 bing 收录(多引擎佐证)
|
|
159
|
+
- `title matches 75% of query terms` — 标题与查询词高度相关
|
|
160
|
+
- `download-page penalty` — 下载站页面被降权(谨慎参考)
|
|
161
|
+
|
|
162
|
+
### deep_search 返回
|
|
163
|
+
|
|
164
|
+
`digest` 是按 token 预算组装好的检索摘录,可直接作为回答依据;`sources` 列出实际读取的来源与得分。引用时注明来源 URL。需要可追溯的结构化信源清单(url/score/adapter/字符数/是否截断)时,带 `format: "json"` 调用,返回体中包含完整 `sources` 数组。
|
|
165
|
+
|
|
166
|
+
## 委派抓取:服务端抓不到时的本地接力
|
|
167
|
+
|
|
168
|
+
部分页面(反爬拦截、需 JS 渲染、非文本内容)服务端无法直接提取正文:`eosearch_fetch` 会返回带 `[委派]` 标记的接力指引,`eosearch_deep_search` 会在摘录末尾标注失败来源及原因。注意:JS 渲染页可能返回成功但只有壳内容(一两百字的公司简介/导航壳,不含目标正文;实测例 stepfun.com/news 资讯页只回简介壳),此时不出现 `[委派]` 标记——`Chars` 异常少且与页面主题不符时,同样按下方接力流程转本机处理,勿把壳内容当正文。收到上述任一信号时,按以下顺序在本机完成读取,再把内容并入原任务:
|
|
169
|
+
|
|
170
|
+
1. **浏览器直读(首选)**:用本地的 Playwright MCP 打开该 URL,渲染成功则直接提取正文,多数页面到此即可;
|
|
171
|
+
2. **PDF 接力**:版面复杂(多栏/表格/论文)时,先滚动到底触发懒加载,再用 Playwright MCP 将页面保存为 PDF,交给 MinerU 免 Key 极速版解析为 Markdown(`mineru-open-api flash-extract <文件>`,未安装先按下方说明安装;单文件 ≤10MB 且 ≤20 页;PDF 为空或过短则改回第 1 步);
|
|
172
|
+
3. **兜底**:只有截图能力时用你的视觉能力读取截图;超过 Flash 限制或需登录的页面,告知用户无法自动读取,请其手动阅读或提供内容。
|
|
173
|
+
|
|
174
|
+
Playwright MCP 未安装时先征得用户同意再装(需 Node.js 18+):客户端 MCP 配置写入 `{"mcpServers":{"playwright":{"command":"npx","args":["@playwright/mcp@latest","--caps=pdf"]}}}`,其中 `--caps=pdf` 用于第 2 步保存 PDF;说明见 https://github.com/microsoft/playwright-mcp。装完重启客户端,工具列表能调到 `browser_navigate` 后,再从第 1 步继续。
|
|
175
|
+
|
|
176
|
+
非文本内容(PDF/图片)不必开浏览器:直接下载文件走 MinerU Flash(免 Key,`mineru-open-api flash-extract <文件>`),图片直接用视觉能力读取。涉及登录态的内容由你在本机读取,动作对用户可见可控。
|
|
177
|
+
|
|
178
|
+
MinerU CLI 未安装时先装再解析:`npm install -g mineru-open-api`(需 Node.js 16+),装完用 `mineru-open-api --version` 自检,能输出版本即就绪;无法全局安装时用 `npx mineru-open-api flash-extract <文件>` 免安装运行;仍不可用时告知用户该文档无法自动解析。
|
|
179
|
+
|
|
180
|
+
## 视频搜索与下载
|
|
181
|
+
|
|
182
|
+
需要"搜视频并下载到本机"时,EoSearch 负责发现、用户本机负责下载,两段配合:
|
|
183
|
+
|
|
184
|
+
1. **发现**:用 `eosearch_search` 搜视频主题(如「XX 教学视频」),视频类查询自动优先 B站垂直引擎(直连站内搜索,返回真实 `/video/` 页链接,描述含 UP主/时长/播放数)。站点定向检索(如"去B站搜")传 `includeDomains: ["bilibili.com"]`,已支持站点自动接入站内引擎。结果中带 `isVideoPage: true` 与 `videoPlatform`(如 `bilibili`、`douyin`)标记的,是已验证下载配方的视频页,优先选择;百度/搜狗的跳转链接已由服务端解包为真实地址,标记不失明。
|
|
185
|
+
2. **下载**:交给「eosearch-video」技能完成——在用户本机用 Playwright MCP 打开视频页拦截流地址,ffmpeg 合成 mp4。下载是点对点直连:视频字节从平台 CDN 直接进用户本机,不经过 EoSearch 服务器,不占服务带宽,也不消耗配额(配额只计工具调用)。
|
|
186
|
+
|
|
187
|
+
「eosearch-video」技能的获取方式:执行 `eosearch skill install --video`(推荐,随 npm 包分发,直接落位到客户端技能目录);或下载 [eosearch-video 技能包](https://eogee.com/downloads/eosearch-video-skill.zip),解压后把 `eosearch-video` 文件夹整体放入客户端技能目录(如 ZCode 的 `.zcode/skills/eosearch-video/`)。技能内含环境检查(ffmpeg 与 Playwright MCP 检测)、缺失时的安装指引与降级方案,未装齐前置条件时不会硬跑。
|
|
188
|
+
|
|
189
|
+
## 常见问题
|
|
190
|
+
|
|
191
|
+
| 现象 | 原因与处理 |
|
|
192
|
+
|------|-----------|
|
|
193
|
+
| `eosearch: command not found` | CLI 未安装或 npm 全局 bin 不在 PATH:重跑 `npm install -g @eogee-tech/eosearch`,或改用 `npx @eogee-tech/eosearch` |
|
|
194
|
+
| 技能文档缺失或版本落后 | 执行 `eosearch skill install` 重新落位(随 CLI 升级保持文档同版本) |
|
|
195
|
+
| CLI 报"未找到 EoSearch API 密钥" | 设置 `EOSEARCH_API_KEY` 环境变量,或在 `~/.eosearchrc` 写入 `{"apiKey":"..."}` |
|
|
196
|
+
| 401 Invalid membership API key | 密钥无效或已过期,到 eogee.com 个人中心核对;确认请求头为 `X-API-Key` |
|
|
197
|
+
| 401 This service requires a membership API key | 请求没带 Key,检查客户端配置的 headers |
|
|
198
|
+
| 429 Daily quota exhausted | 当日配额用完,次日 00:00 UTC 重置;升级会员可提升配额 |
|
|
199
|
+
| 429 Rate limit exceeded | 请求过快,等待数秒后重试 |
|
|
200
|
+
| 搜索结果为空或部分引擎失败 | 服务会自动熔断故障引擎并换道重试;可带 `engines` 参数显式指定其他引擎重试一次 |
|
|
201
|
+
| 返回 `[委派]` 或"无法获取正文" | 页面反爬/需渲染/非文本,按「委派抓取」一节的本地接力流程完成读取 |
|
|
202
|
+
| 只想在某个站内搜(如去B站) | `includeDomains: ["bilibili.com"]`:B站站内引擎自动接入并返回站内直链;未接入站内引擎的站点只有通用结果的后置过滤,产出可能偏少 |
|
|
203
|
+
| Bing 结果异常 | 带 `searchMode: "playwright"` 参数重试一次 |
|
|
204
|
+
|
|
205
|
+
## 配额说明
|
|
206
|
+
|
|
207
|
+
| 档位 | 每日配额 | 每分钟限速 |
|
|
208
|
+
|------|---------|-----------|
|
|
209
|
+
| 极会员(会员 Key) | 不限次数 | 60 次 |
|
|
210
|
+
| 普通用户 Key | 100 次 | 10 次 |
|
|
211
|
+
|
|
212
|
+
服务不提供匿名通道:未携带有效 Key 的请求一律返回 401。
|
|
213
|
+
|
|
214
|
+
工具调用才计费;连接握手与工具列表查询不消耗配额。响应头 `X-Quota-Remaining-Today` 指示当日剩余额度(极会员显示 unlimited)。
|
|
@@ -0,0 +1,119 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: eosearch-video
|
|
3
|
+
description: EoSearch 视频搜索与下载:先用 eosearch_search 找视频源,再在用户本机用浏览器自动化 MCP 拦截视频流、ffmpeg 合成 mp4(点对点直连平台 CDN,不经服务端)。当用户要求"搜视频并下载""下载视频""抓取视频""把视频拿下来""保存这个视频",或从 EoSearch 结果中带 isVideoPage/videoPlatform 标记的链接要求下载时使用。
|
|
4
|
+
argument-hint: "[视频主题或页面URL] [输出文件名]"
|
|
5
|
+
---
|
|
6
|
+
|
|
7
|
+
# EoSearch 视频搜索与下载(eosearch-video)
|
|
8
|
+
|
|
9
|
+
分工明确的两段式:**EoSearch 负责"发现"**(搜到视频页链接),**用户本机负责"下载"**(浏览器自动化 MCP 拦截流地址 + ffmpeg 合成)。下载是点对点直连:视频字节从平台 CDN 直接进用户本机,不经过 EoSearch 服务器——不占服务带宽、不计费,带签名时效的流地址只在用户浏览器里出现,服务端看不到也存不到。
|
|
10
|
+
|
|
11
|
+
## 第 0 步:环境检查(会话内首次用到时执行一次,结果记住)
|
|
12
|
+
|
|
13
|
+
**ffmpeg 检查**:
|
|
14
|
+
|
|
15
|
+
```bash
|
|
16
|
+
ffmpeg -version 2>/dev/null | head -1 || /c/ffmpeg/bin/ffmpeg.exe -version 2>/dev/null | head -1
|
|
17
|
+
```
|
|
18
|
+
|
|
19
|
+
有输出即可用(grab.sh 会自动探测路径,无需额外配置);无输出视为缺失。
|
|
20
|
+
|
|
21
|
+
**Playwright MCP 检查**:查看本会话工具列表,`browser_navigate` 与 `browser_network_requests` 存在即可。
|
|
22
|
+
|
|
23
|
+
**四种组合的走法(任一缺失立即降级,不硬跑)**:
|
|
24
|
+
|
|
25
|
+
| ffmpeg | Playwright MCP | 走法 |
|
|
26
|
+
|--------|----------------|------|
|
|
27
|
+
| 有 | 有 | 全流程 |
|
|
28
|
+
| 无 | 有 | 照常拦截,把直链交付给用户(浏览器打开直链可另存),附下方 ffmpeg 安装指引;装好后只需重跑第 4 步 |
|
|
29
|
+
| 有 | 无 | 降级尝试**一次**:部分平台(网易视频、腾讯新闻)流地址嵌在页面源码里,`eosearch_fetch` 取 HTML 后正则提取直链再 ffmpeg 直下;失败即降级,不恋战;提示按下方指引接入 Playwright MCP 后可全自动 |
|
|
30
|
+
| 无 | 无 | 只交付搜索结果与视频页链接,说明本机缺少自动下载条件,并给出下方 ffmpeg 与 Playwright MCP 的安装指引 |
|
|
31
|
+
|
|
32
|
+
**缺失时的安装指引**(引导用户补齐,装好后从对应步骤继续):
|
|
33
|
+
|
|
34
|
+
- **ffmpeg**:Windows `winget install Gyan.FFmpeg`;macOS `brew install ffmpeg`;Linux `sudo apt install ffmpeg`(或用发行版包管理器)。装完 `ffmpeg -version` 有输出即可,重跑第 4 步。
|
|
35
|
+
- **Playwright MCP**(需 Node.js 18+):客户端 MCP 配置写入 `{"mcpServers":{"playwright":{"command":"npx","args":["@playwright/mcp@latest"]}}}`;需要复用本机 Chrome 的登录态时在 args 末尾追加 `"--browser","chrome"`。说明见 https://github.com/microsoft/playwright-mcp
|
|
36
|
+
- Playwright MCP 装完重启客户端,确认工具列表出现第 2 步表格里的工具,再从第 2 步继续。
|
|
37
|
+
|
|
38
|
+
降级话术必须"给出路":说清缺什么、怎么装、装好后从哪一步继续。
|
|
39
|
+
|
|
40
|
+
CLI 有新版时会在 stderr 提示;升级后执行 `eosearch skill install --video` 刷新技能文档(每日版本检查由 CLI 负责,本技能不重复检查)。
|
|
41
|
+
|
|
42
|
+
## 第 1 步:拿到视频页 URL
|
|
43
|
+
|
|
44
|
+
- 用户给了 URL 直接用,跳到第 2 步。
|
|
45
|
+
- **B站定向检索是首选路径**:`eosearch_search` 带 `includeDomains: ["bilibili.com"]`(对应"去B站搜XX"),自动接入 B站站内搜索引擎,返回真实 `/video/` 页直链(描述含 UP主/时长/播放数/发布日期),全部带 `isVideoPage` 标记。
|
|
46
|
+
- 常规视频搜索:视频类查询自动优先 B站垂直引擎;结果里带 `isVideoPage: true` + `videoPlatform` 标记的是已验证下载配方的视频页,**优先挑这些**。百度/搜狗的跳转链接已由服务端解包为真实域名,标记不会失明。
|
|
47
|
+
- **平台边界(服务端定向刻意不做)**:抖音有登录墙、小红书强反爬+签名,二者的站内搜索不接服务端。通用搜索仍能收录部分抖音视频页(取 `douyin.com/video/{id}` 直链);小红书内容只能走客户端浏览器路线(Playwright MCP 打开其站内搜索,需登录)。
|
|
48
|
+
- 搜索结果里没有具体视频页时:把查询换成具体视频标题/主题关键词再搜一次;或用 Playwright MCP 直接打开平台站内搜索页找目标视频(B站搜索无需登录)。
|
|
49
|
+
|
|
50
|
+
## 第 2 步:浏览器打开视频页并触发播放
|
|
51
|
+
|
|
52
|
+
使用 Playwright MCP 的对应工具:
|
|
53
|
+
|
|
54
|
+
| 能力 | 工具 |
|
|
55
|
+
|------|------|
|
|
56
|
+
| 打开页面 | `browser_navigate` |
|
|
57
|
+
| 找播放按钮并点击 | `browser_snapshot` + `browser_click` |
|
|
58
|
+
| 等待起流 | `browser_wait_for` |
|
|
59
|
+
| 列网络请求 | `browser_network_requests`(filter 填 URL 正则) |
|
|
60
|
+
| 读接口响应体 | `browser_network_request`(`part: "response-body"`) |
|
|
61
|
+
| 页面内取值 | `browser_evaluate` |
|
|
62
|
+
|
|
63
|
+
视频是点击后才加载的,先 snapshot 找到播放按钮 click 触发播放再进第 3 步。
|
|
64
|
+
|
|
65
|
+
## 第 3 步:拦截视频流地址
|
|
66
|
+
|
|
67
|
+
在网络请求列表里找:
|
|
68
|
+
|
|
69
|
+
- `.m3u8` 结尾的地址(首选,HLS 切片流索引)
|
|
70
|
+
- `.mp4` 直链(次选)
|
|
71
|
+
- 找不到时看视频信息 API 的 JSON 响应(如腾讯 `i.news.qq.com/getWebVideo?id=...`),读响应体提取视频地址
|
|
72
|
+
|
|
73
|
+
`video.src` 是 `blob:` 开头说明走 MSE 流式播放,DOM 里拿不到直链:改从网络请求里搜媒体域名(`douyinvod.com`/`upos` 等),或读视频信息 API 响应体。
|
|
74
|
+
|
|
75
|
+
## 第 4 步:ffmpeg 下载合成
|
|
76
|
+
|
|
77
|
+
```bash
|
|
78
|
+
bash <本技能目录>/helpers/grab.sh "<流地址>" 输出.mp4
|
|
79
|
+
```
|
|
80
|
+
|
|
81
|
+
手写命令时的硬规则(grab.sh 已内置处理):
|
|
82
|
+
|
|
83
|
+
- **URL 必须加引号**,内含 `&` 会被 shell 截断;
|
|
84
|
+
- 403 时**来源头与 UA 常缺一不可**(B站实测只带 Referer 仍 403):`-headers "Referer: https://<视频页域名>/" -user_agent "Mozilla/5.0 ... Chrome/131 ..."`;
|
|
85
|
+
- **`-headers`/`-user_agent` 只作用于紧随其后的那一个 `-i`**,音视频分离流(DASH)多输入时每组选项各带一份,否则第二个输入 403;合并用 `-c copy -bsf:a aac_adtstoasc`。
|
|
86
|
+
|
|
87
|
+
## 第 5 步:验证产物
|
|
88
|
+
|
|
89
|
+
```bash
|
|
90
|
+
ffprobe -v error -show_entries format=duration,size -of default=nw=1 输出.mp4
|
|
91
|
+
```
|
|
92
|
+
|
|
93
|
+
时长与页面标注一致即成功;不一致(如明显偏短)多为切片中途断流,重下一次。
|
|
94
|
+
|
|
95
|
+
## 变体与排障
|
|
96
|
+
|
|
97
|
+
| 情况 | 处理 |
|
|
98
|
+
|------|------|
|
|
99
|
+
| 流地址带 token / 签名 | **有时效,拦截到后立刻下载**;过期就刷新页面重新拦截 |
|
|
100
|
+
| 多个清晰度 | URL 路径含 `SD`/`HD` 字样选高清;master m3u8 默认取第一个子流,需指定时把子流 URL 单独喂给 ffmpeg |
|
|
101
|
+
| 音视频分离流(DASH,B站) | grab.sh `--audio <音频流>` 一次合并 |
|
|
102
|
+
| 下载报 403 | 见第 4 步硬规则:Referer + UA 齐上 |
|
|
103
|
+
| 中途断流 | 去掉 `-loglevel error` 看卡在哪个切片;重试一次通常可过(切片 CDN 抖动) |
|
|
104
|
+
| m3u8 在页面里却拦不到 | 视频未开始播放:先触发播放,或页面内取值在 DOM 里搜 `m3u8` |
|
|
105
|
+
| 无头浏览器突然弹登录墙/验证 | 平台指纹检测:改有头模式(`--headless=false`)或指定真 Chrome(`--browser chrome`)重试 |
|
|
106
|
+
| 每次都要重新登录 | Playwright MCP 用了隔离模式(`--isolated`):改用持久化 profile,登录一次目标平台长期有效 |
|
|
107
|
+
|
|
108
|
+
## 已支持平台(2026-10 实测)
|
|
109
|
+
|
|
110
|
+
| 平台 | 页面 URL 模式 | 抓取要点 |
|
|
111
|
+
|------|--------------|---------|
|
|
112
|
+
| B站 | `www.bilibili.com/video/BV*` | DASH 分离流:`*-1-100023.m4s` 视频、`*-1-30216.m4s` 音频,grab.sh `--audio` 合并;**必须同时带 Referer + 浏览器 UA**,缺 UA 即 403;登录前清晰度受限 |
|
|
113
|
+
| 抖音 | `www.douyin.com/video/{id}` | 未登录可播;页面内取值读 `video.currentSrc` 直接得签名 mp4(单文件含音视频);`src` 显示 `blob:` 时改从网络请求搜 `douyinvod.com`;须带 Referer + UA |
|
|
114
|
+
| 腾讯视频 | `v.qq.com/x/cover/*.html` | 播放器走 MSE(`blob:` src),网络请求里直接有 m3u8(`ltshsy.gtimg.com`,与腾讯新闻同体系);带 Referer `https://v.qq.com/` + UA;花絮/预告类短视频无需登录 |
|
|
115
|
+
| 腾讯新闻 | `news.qq.com/rain/a/*` | m3u8 在 `ltshsy.gtimg.com`,带 token,拦截后即时下载 |
|
|
116
|
+
| 网易视频 | `163.com/v/video/*.html` | m3u8 在 `flv3.bn.netease.com`,长签名 URL,无需额外请求头 |
|
|
117
|
+
| YouTube | `youtube.com/watch?v=` / `youtu.be/` | 已识别标记,但下载依赖用户网络环境,不在保证清单内 |
|
|
118
|
+
|
|
119
|
+
清单外的平台不保证可用:照标准流程试一遍,通了就补进本表。
|
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
#!/usr/bin/env bash
|
|
2
|
+
# grab.sh — 从视频流地址(m3u8/mp4)下载合成本地 mp4
|
|
3
|
+
# 用法:
|
|
4
|
+
# bash grab.sh <流地址> <输出.mp4> [选项]
|
|
5
|
+
# 选项:
|
|
6
|
+
# --audio <音频流地址> 音视频分离时同时合并
|
|
7
|
+
# --referer <URL> 403 时加来源头
|
|
8
|
+
# --ua <UA字符串> 自定义 User-Agent
|
|
9
|
+
# --quality <子流URL> master m3u8 里选定清晰度的子流(等价于直接把子流当第1参数)
|
|
10
|
+
|
|
11
|
+
set -uo pipefail
|
|
12
|
+
|
|
13
|
+
# ffmpeg 路径探测:先 PATH,再常见安装位置;找不到时给出安装指引
|
|
14
|
+
FFMPEG="$(command -v ffmpeg 2>/dev/null || true)"
|
|
15
|
+
[ -z "$FFMPEG" ] && [ -x /c/ffmpeg/bin/ffmpeg.exe ] && FFMPEG="/c/ffmpeg/bin/ffmpeg.exe"
|
|
16
|
+
[ -z "$FFMPEG" ] && { echo "错误: 未找到 ffmpeg。安装: winget install Gyan.FFmpeg(或从 ffmpeg.org 下载解压后加入 PATH),装好后只需重跑本脚本" >&2; exit 1; }
|
|
17
|
+
FFPROBE="$(command -v ffprobe 2>/dev/null || true)"
|
|
18
|
+
[ -z "$FFPROBE" ] && FFPROBE="$(dirname "$FFMPEG")/ffprobe"
|
|
19
|
+
|
|
20
|
+
usage() { grep '^#' "$0" | sed 's/^# \{0,1\}//'; }
|
|
21
|
+
|
|
22
|
+
[ $# -lt 2 ] && { usage; exit 1; }
|
|
23
|
+
|
|
24
|
+
URL="$1"; OUT="$2"; shift 2
|
|
25
|
+
AUDIO=""; REF=""; UA=""; EXTRA=()
|
|
26
|
+
|
|
27
|
+
while [ $# -gt 0 ]; do
|
|
28
|
+
case "$1" in
|
|
29
|
+
--audio) AUDIO="$2"; shift 2 ;;
|
|
30
|
+
--referer) REF="$2"; shift 2 ;;
|
|
31
|
+
--ua) UA="$2"; shift 2 ;;
|
|
32
|
+
--quality) URL="$2"; shift 2 ;;
|
|
33
|
+
*) echo "未知参数: $1" >&2; exit 1 ;;
|
|
34
|
+
esac
|
|
35
|
+
done
|
|
36
|
+
|
|
37
|
+
# 流地址含 & ? 等字符,必须整体作为单个参数传入,此处不再拆分
|
|
38
|
+
[ -n "$REF" ] && EXTRA+=(-headers "Referer: $REF")
|
|
39
|
+
[ -n "$UA" ] && EXTRA+=(-user_agent "$UA")
|
|
40
|
+
|
|
41
|
+
echo "[grab] 输入: $URL"
|
|
42
|
+
[ -n "$AUDIO" ] && echo "[grab] 音频流: $AUDIO"
|
|
43
|
+
echo "[grab] 输出: $OUT"
|
|
44
|
+
|
|
45
|
+
# -headers/-user_agent 只作用于紧随其后的那一个 -i,多输入时每组选项必须各带一份
|
|
46
|
+
if [ -n "$AUDIO" ]; then
|
|
47
|
+
"$FFMPEG" -y -loglevel error "${EXTRA[@]}" -i "$URL" "${EXTRA[@]}" -i "$AUDIO" \
|
|
48
|
+
-c copy -bsf:a aac_adtstoasc "$OUT"
|
|
49
|
+
else
|
|
50
|
+
"$FFMPEG" -y -loglevel error "${EXTRA[@]}" -i "$URL" \
|
|
51
|
+
-c copy -bsf:a aac_adtstoasc "$OUT"
|
|
52
|
+
fi
|
|
53
|
+
RC=$?
|
|
54
|
+
|
|
55
|
+
[ $RC -ne 0 ] && { echo "[grab] ffmpeg 退出码 $RC(token 过期就刷新页面重新拦截;403 就补 Referer+UA)" >&2; exit $RC; }
|
|
56
|
+
|
|
57
|
+
echo "[grab] 校验产物:"
|
|
58
|
+
"$FFPROBE" -v error -show_entries format=duration,size -of default=nw=1 "$OUT"
|