Compare commits
4 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| 26be7fc28f | |||
| fd6756d1af | |||
| 11cd9d14ad | |||
| f94458bba3 |
@@ -47,7 +47,7 @@ jobs:
|
||||
fail-fast: false
|
||||
matrix:
|
||||
os: ${{ (github.event_name == 'push' || github.event_name == 'schedule' || github.event_name == 'workflow_dispatch') && fromJSON('["ubuntu-latest","macos-latest","windows-latest"]') || fromJSON('["ubuntu-latest"]') }}
|
||||
node-version: ${{ (github.event_name == 'push' || github.event_name == 'schedule' || github.event_name == 'workflow_dispatch') && fromJSON('["20","22"]') || fromJSON('["22"]') }}
|
||||
node-version: ${{ (github.event_name == 'push' || github.event_name == 'schedule' || github.event_name == 'workflow_dispatch') && fromJSON('["22"]') || fromJSON('["22"]') }}
|
||||
shard: [1, 2]
|
||||
steps:
|
||||
- uses: actions/checkout@v6
|
||||
|
||||
+3
-3
@@ -30,7 +30,7 @@ All adapters use TypeScript. Use the pipeline API for data-fetching commands, an
|
||||
|
||||
### Pipeline Adapter (Recommended for data-fetching commands)
|
||||
|
||||
Create a file like `clis/<site>/<command>.ts`:
|
||||
Create a file like `clis/<site>/<command>.js`:
|
||||
|
||||
```typescript
|
||||
import { cli, Strategy } from '@jackwener/opencli/registry';
|
||||
@@ -60,11 +60,11 @@ cli({
|
||||
});
|
||||
```
|
||||
|
||||
See [`hackernews/top.ts`](clis/hackernews/top.ts) for a real example.
|
||||
See [`hackernews/top.js`](clis/hackernews/top.js) for a real example.
|
||||
|
||||
### func() Adapter (For complex browser interactions)
|
||||
|
||||
Create a file like `clis/<site>/<command>.ts`:
|
||||
Create a file like `clis/<site>/<command>.js`:
|
||||
|
||||
```typescript
|
||||
import { cli, Strategy } from '@jackwener/opencli/registry';
|
||||
|
||||
@@ -30,10 +30,10 @@ It also works as a **CLI hub** for local tools such as `gh`, `docker`, and other
|
||||
- **AI Agent ready** — `explore` discovers APIs, `synthesize` generates adapters, `cascade` finds auth strategies, `browser` controls the browser directly.
|
||||
- **External CLI Hub** — Discover, auto-install, and passthrough commands to any external CLI (gh, obsidian, docker, etc). Zero setup.
|
||||
- **Self-healing setup** — `opencli doctor` diagnoses and auto-starts the daemon, extension, and live browser connectivity.
|
||||
- **Dynamic Loader** — Simply drop `.ts` adapters into the `clis/` folder for auto-registration.
|
||||
- **Dynamic Loader** — Simply drop `.js` adapters into the `clis/` folder for auto-registration.
|
||||
- **Zero LLM cost** — No tokens consumed at runtime. Run 10,000 times and pay nothing.
|
||||
- **Deterministic** — Same command, same output schema, every time. Pipeable, scriptable, CI-friendly.
|
||||
- **Broad coverage** — 79+ sites across global and Chinese platforms (Bilibili, Zhihu, Xiaohongshu, Reddit, HackerNews, and more), plus desktop Electron apps via CDP.
|
||||
- **Broad coverage** — 87+ sites across global and Chinese platforms (Bilibili, Zhihu, Xiaohongshu, Reddit, HackerNews, and more), plus desktop Electron apps via CDP.
|
||||
|
||||
---
|
||||
|
||||
@@ -136,7 +136,7 @@ OpenCLI is not only for websites. It can also:
|
||||
|
||||
## Prerequisites
|
||||
|
||||
- **Node.js**: >= 20.0.0 (or **Bun** >= 1.0)
|
||||
- **Node.js**: >= 21.0.0 (or **Bun** >= 1.0)
|
||||
- **Chrome or Chromium** running and logged into the target site for browser-backed commands
|
||||
|
||||
> **Important**: Browser-backed commands reuse your Chrome/Chromium login session. If you get empty data or permission-like failures, first confirm the site is already open and authenticated in Chrome/Chromium.
|
||||
@@ -212,7 +212,7 @@ To load the source Browser Bridge extension:
|
||||
| **xiaoe** | `courses` `detail` `catalog` `play-url` `content` |
|
||||
| **quark** | `ls` `mkdir` `mv` `rename` `rm` `save` `share-tree` |
|
||||
|
||||
79+ adapters in total — **[→ see all supported sites & commands](./docs/adapters/index.md)**
|
||||
87+ adapters in total — **[→ see all supported sites & commands](./docs/adapters/index.md)**
|
||||
|
||||
## CLI Hub
|
||||
|
||||
@@ -349,7 +349,7 @@ See **[TESTING.md](./TESTING.md)** for how to run and write tests.
|
||||
- **"Extension not connected"** — Ensure the Browser Bridge extension is installed and **enabled** in `chrome://extensions` in Chrome or Chromium.
|
||||
- **"attach failed: Cannot access a chrome-extension:// URL"** — Another extension may be interfering. Try disabling other extensions temporarily.
|
||||
- **Empty data or 'Unauthorized' error** — Your Chrome/Chromium login session may have expired. Navigate to the target site and log in again.
|
||||
- **Node API errors** — Ensure Node.js >= 20. Some dependencies require modern Node APIs.
|
||||
- **Node API errors** — Ensure Node.js >= 21. Some features require `node:util` styleText (stable in Node 21+).
|
||||
- **Daemon issues** — Check status: `curl localhost:19825/status` · View logs: `curl localhost:19825/logs`
|
||||
|
||||
## Star History
|
||||
|
||||
+5
-5
@@ -10,7 +10,7 @@
|
||||
|
||||
OpenCLI 可以用同一套 CLI 做三类事情:
|
||||
|
||||
- **直接使用现成适配器**:B站、知乎、小红书、Twitter/X、Reddit、HackerNews 等 [79+ 站点](#内置命令) 开箱即用。
|
||||
- **直接使用现成适配器**:B站、知乎、小红书、Twitter/X、Reddit、HackerNews 等 [87+ 站点](#内置命令) 开箱即用。
|
||||
- **直接驱动浏览器**:用 `opencli browser` 让 AI Agent 实时点击、输入、提取、截图、检查页面状态。
|
||||
- **把新网站生成成 CLI**:通过 `explore`、`synthesize`、`generate`、`cascade` 从真实页面行为推导出新的适配器。
|
||||
|
||||
@@ -23,7 +23,7 @@ OpenCLI 可以用同一套 CLI 做三类事情:
|
||||
- **输出稳定**:适配器命令返回固定结构,适合 shell、脚本、CI 和 AI Agent 工具调用。
|
||||
- **面向 AI Agent**:`browser` 负责实时操作,`explore` 负责探索接口,`synthesize` 负责生成适配器,`cascade` 负责探测认证路径。
|
||||
- **运行成本低**:已有命令运行时不消耗模型 token。
|
||||
- **天然可扩展**:既能用内置能力,也能注册本地 CLI,或直接往 `clis/` 丢 `.ts` 适配器。
|
||||
- **天然可扩展**:既能用内置能力,也能注册本地 CLI,或直接往 `clis/` 丢 `.js` 适配器。
|
||||
|
||||
## 快速开始
|
||||
|
||||
@@ -124,7 +124,7 @@ OpenCLI 不只是网站 CLI,还可以:
|
||||
|
||||
## 前置要求
|
||||
|
||||
- **Node.js**: >= 20.0.0
|
||||
- **Node.js**: >= 21.0.0
|
||||
- 浏览器型命令需要 Chrome 或 Chromium 处于运行中,并已登录目标网站
|
||||
|
||||
> **重要**:浏览器型命令直接复用你的 Chrome/Chromium 登录态。如果拿到空数据或出现权限类失败,先确认目标站点已经在浏览器里打开并完成登录。
|
||||
@@ -262,7 +262,7 @@ npm link
|
||||
| **douyin** | `videos` `publish` `drafts` `draft` `delete` `stats` `profile` `update` `hashtag` `location` `activities` `collections` | 浏览器 |
|
||||
| **yuanbao** | `new` `ask` | 浏览器 |
|
||||
|
||||
79+ 适配器 — **[→ 查看完整命令列表](./docs/adapters/index.md)**
|
||||
87+ 适配器 — **[→ 查看完整命令列表](./docs/adapters/index.md)**
|
||||
|
||||
### 外部 CLI 枢纽
|
||||
|
||||
@@ -460,7 +460,7 @@ opencli cascade https://api.example.com/data
|
||||
- **返回空数据,或者报错 "Unauthorized"**
|
||||
- Chrome/Chromium 里的登录态可能已经过期。请打开当前页面,在新标签页重新手工登录或刷新该页面。
|
||||
- **Node API 错误 (如 parseArgs, fs 等)**
|
||||
- 确保 Node.js 版本 `>= 20`。
|
||||
- 确保 Node.js 版本 `>= 21`(`node:util` 的 `styleText` 需要 Node 21+)。
|
||||
- **Daemon 问题**
|
||||
- 检查 daemon 状态:`curl localhost:19825/status`
|
||||
- 查看扩展日志:`curl localhost:19825/logs`
|
||||
|
||||
+2
-2
@@ -205,12 +205,12 @@ E2E 与 smoke 都使用 `./.github/actions/setup-chrome` 准备真实 Chrome,
|
||||
|
||||
### Sharding
|
||||
|
||||
单元测试使用 vitest 内置 shard,并在 Node `20` / `22` 两个版本上运行:
|
||||
单元测试使用 vitest 内置 shard,并在 Node `22` 上运行(项目要求 Node >= 21):
|
||||
|
||||
```yaml
|
||||
strategy:
|
||||
matrix:
|
||||
node-version: ['20', '22']
|
||||
node-version: ['22']
|
||||
shard: [1, 2]
|
||||
steps:
|
||||
- run: npx vitest run src/ --reporter=verbose --shard=${{ matrix.shard }}/2
|
||||
|
||||
@@ -15,7 +15,7 @@ OpenCLI turns **any website** or **Electron app** into a command-line interface
|
||||
- **Account-safe** — Reuses Chrome's logged-in state; your credentials never leave the browser.
|
||||
- **AI Agent ready** — `explore` discovers APIs, `synthesize` generates adapters, `cascade` finds auth strategies.
|
||||
- **Self-healing setup** — `opencli doctor` auto-starts the daemon and diagnoses extension + live browser connectivity.
|
||||
- **Dynamic Loader** — Simply drop `.ts` adapters into the `clis/` folder for auto-registration.
|
||||
- **Dynamic Loader** — Simply drop `.js` adapters into the `clis/` folder for auto-registration.
|
||||
- **Dual-Engine Architecture** — Supports both declarative pipeline adapters and robust browser runtime TypeScript injections.
|
||||
|
||||
## Quick Start
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
|
||||
## Requirements
|
||||
|
||||
- **Node.js**: >= 20.0.0
|
||||
- **Node.js**: >= 21.0.0
|
||||
- **Chrome** running and logged into the target site (for browser commands)
|
||||
|
||||
## Install via npm (Recommended)
|
||||
|
||||
@@ -25,7 +25,7 @@ OPENCLI_CDP_TARGET=detail.1688.com opencli 1688 item 841141931191 -f json
|
||||
|
||||
### Node API errors
|
||||
|
||||
- Make sure you are using **Node.js >= 20**. Some dependencies require modern Node APIs.
|
||||
- Make sure you are using **Node.js >= 21**. Some features require `node:util` styleText (stable in Node 21+).
|
||||
- Run `node --version` to verify.
|
||||
|
||||
### Daemon issues
|
||||
|
||||
+1
-1
@@ -31,5 +31,5 @@ features:
|
||||
details: "opencli doctor auto-starts the daemon and diagnoses extension + live browser connectivity."
|
||||
- icon: 📦
|
||||
title: Dynamic Loader
|
||||
details: Simply drop .ts adapters into the clis/ folder for auto-registration. Zero boilerplate.
|
||||
details: Simply drop .js adapters into the clis/ folder for auto-registration. Zero boilerplate.
|
||||
---
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
|
||||
## 系统要求
|
||||
|
||||
- **Node.js**: >= 20.0.0
|
||||
- **Node.js**: >= 21.0.0
|
||||
- **Chrome** 已运行并登录目标网站(浏览器命令需要)
|
||||
|
||||
## 通过 npm 安装(推荐)
|
||||
|
||||
+1
-2
@@ -47,10 +47,9 @@
|
||||
"copy-yaml": "node scripts/copy-yaml.cjs",
|
||||
"start": "node dist/src/main.js",
|
||||
"start:bun": "bun dist/src/main.js",
|
||||
"preuninstall": "node -e \"fetch('http://127.0.0.1:19825/shutdown',{method:'POST',headers:{'X-OpenCLI':'1'},signal:AbortSignal.timeout(3000)}).catch(()=>{})\" || true",
|
||||
"preuninstall": "node -e \"fetch('http://127.0.0.1:'+(process.env.OPENCLI_DAEMON_PORT||'19825')+'/shutdown',{method:'POST',headers:{'X-OpenCLI':'1'},signal:AbortSignal.timeout(3000)}).catch(()=>{})\" || true",
|
||||
"postinstall": "node scripts/postinstall.js || true; node scripts/fetch-adapters.js || true",
|
||||
"typecheck": "tsc --noEmit",
|
||||
"lint": "tsc --noEmit",
|
||||
"prepare": "[ -d src ] && npm run build || true",
|
||||
"prepublishOnly": "npm run build",
|
||||
"test": "vitest run --project unit --project extension",
|
||||
|
||||
@@ -168,6 +168,7 @@ function main() {
|
||||
console.log('');
|
||||
console.log(' Then run \x1b[36mopencli doctor\x1b[0m to verify.');
|
||||
console.log('');
|
||||
|
||||
}
|
||||
|
||||
main();
|
||||
|
||||
@@ -215,15 +215,15 @@ OpenCLI autofix repaired this adapter locally, and the retry passed.
|
||||
## Original failure
|
||||
- Error code: `<error_code>`
|
||||
|
||||
\```text
|
||||
~~~
|
||||
<error_message>
|
||||
\```
|
||||
~~~
|
||||
|
||||
## Local fix summary
|
||||
|
||||
\```text
|
||||
~~~
|
||||
<1-2 sentence description of what you changed and why>
|
||||
\```
|
||||
~~~
|
||||
|
||||
_Issue filed by OpenCLI autofix after a verified local repair._
|
||||
```
|
||||
|
||||
@@ -72,7 +72,7 @@ opencli browser click 7 # all three together
|
||||
4. **Wait** (if needed): `opencli browser wait selector ".loaded"` or `wait text "Success"`
|
||||
5. **Verify**: `opencli browser state` or `opencli browser get value <N>`
|
||||
6. **Repeat**: browser stays open between commands
|
||||
7. **Save**: write a TS adapter to `~/.opencli/clis/<site>/<command>.ts`
|
||||
7. **Save**: write a JS adapter to `~/.opencli/clis/<site>/<command>.js`
|
||||
|
||||
## Commands
|
||||
|
||||
@@ -159,7 +159,7 @@ opencli browser network --all # Include static resources
|
||||
### Sedimentation (Save as CLI)
|
||||
|
||||
```bash
|
||||
opencli browser init hn/top # Generate adapter scaffold at ~/.opencli/clis/hn/top.ts
|
||||
opencli browser init hn/top # Generate adapter scaffold at ~/.opencli/clis/hn/top.js
|
||||
opencli browser verify hn/top # Test the adapter (adds --limit 3 only if `limit` arg is defined)
|
||||
```
|
||||
|
||||
@@ -207,7 +207,7 @@ opencli browser network # See captured API requests
|
||||
opencli browser network --detail 0 # Inspect response body
|
||||
|
||||
# 3. Generate scaffold
|
||||
opencli browser init hn/top # Creates ~/.opencli/clis/hn/top.ts
|
||||
opencli browser init hn/top # Creates ~/.opencli/clis/hn/top.js
|
||||
|
||||
# 4. Edit the adapter (fill in func logic)
|
||||
# - If API found: use fetch() directly (Strategy.PUBLIC or COOKIE)
|
||||
@@ -224,7 +224,7 @@ opencli browser close
|
||||
### Example adapter:
|
||||
|
||||
```typescript
|
||||
// ~/.opencli/clis/hn/top.ts
|
||||
// ~/.opencli/clis/hn/top.js
|
||||
import { cli, Strategy } from '@jackwener/opencli/registry';
|
||||
|
||||
cli({
|
||||
@@ -250,7 +250,7 @@ cli({
|
||||
});
|
||||
```
|
||||
|
||||
Save to `~/.opencli/clis/<site>/<command>.ts` → immediately available as `opencli <site> <command>`.
|
||||
Save to `~/.opencli/clis/<site>/<command>.js` → immediately available as `opencli <site> <command>`.
|
||||
|
||||
### Strategy Guide
|
||||
|
||||
|
||||
@@ -151,12 +151,12 @@ fetch(url) 直接能拿到?
|
||||
|
||||
```bash
|
||||
ls clis/<site>/ # 看同站点已有什么
|
||||
cat clis/<site>/feed.ts # 读最相似的那个
|
||||
cat clis/<site>/feed.js # 读最相似的那个
|
||||
```
|
||||
|
||||
改 3 处即可:`name`、API URL、字段映射。
|
||||
|
||||
**Bilibili 平台 SDK**(`clis/bilibili/utils.ts`):
|
||||
**Bilibili 平台 SDK**(`clis/bilibili/utils.js`):
|
||||
- `fetchJson(page, url)` → 普通 Cookie-tier API
|
||||
- `apiGet(page, path, {signed, params})` → URL 含 `/wbi/` 的接口(自动签名)
|
||||
- `getSelfUid(page)` / `resolveUid(page, input)` → 用户 UID 处理
|
||||
@@ -165,7 +165,7 @@ cat clis/<site>/feed.ts # 读最相似的那个
|
||||
|
||||
## Step 3: 编写适配器
|
||||
|
||||
所有适配器统一使用 TypeScript `cli()` API,放入 `clis/<site>/<name>.ts` 即自动注册。
|
||||
所有适配器统一使用 `cli()` API,放入 `clis/<site>/<name>.js` 即自动注册。
|
||||
|
||||
完整模板(Tier 1~4)、分页模式、错误处理规范(`throw CliError` + YAML envelope)→ **[adapter-templates.md](references/adapter-templates.md)**
|
||||
|
||||
@@ -209,8 +209,8 @@ cli({
|
||||
|
||||
<!-- keep in sync with oneshot SKILL.md §测试 -->
|
||||
**两种开发场景**:
|
||||
- **Repo 贡献**:文件放 `clis/<site>/<name>.ts`,`npm run build` 后自动注册
|
||||
- **私人 adapter**(本地使用,无需提 PR):文件放 `~/.opencli/clis/<site>/<name>.ts`,无需 build
|
||||
- **Repo 贡献**:文件放 `clis/<site>/<name>.js`,`npm run build` 后自动注册
|
||||
- **私人 adapter**(本地使用,无需提 PR):文件放 `~/.opencli/clis/<site>/<name>.js`,无需 build
|
||||
|
||||
```bash
|
||||
# Repo 贡献:build 后直接运行
|
||||
|
||||
Reference in New Issue
Block a user