@jackwener/opencli 1.0.5 → 1.1.0
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/CHANGELOG.md +8 -0
- package/README.md +36 -10
- package/README.zh-CN.md +3 -0
- package/SKILL.md +7 -2
- package/dist/bilibili.js +4 -2
- package/dist/cli-manifest.json +506 -6
- package/dist/cli.js +51 -1
- package/dist/clis/antigravity/serve.js +296 -47
- package/dist/clis/arxiv/paper.d.ts +1 -0
- package/dist/clis/arxiv/paper.js +21 -0
- package/dist/clis/arxiv/search.d.ts +1 -0
- package/dist/clis/arxiv/search.js +24 -0
- package/dist/clis/arxiv/utils.d.ts +18 -0
- package/dist/clis/arxiv/utils.js +49 -0
- package/dist/clis/boss/batchgreet.d.ts +1 -0
- package/dist/clis/boss/batchgreet.js +147 -0
- package/dist/clis/boss/exchange.d.ts +1 -0
- package/dist/clis/boss/exchange.js +111 -0
- package/dist/clis/boss/greet.d.ts +1 -0
- package/dist/clis/boss/greet.js +175 -0
- package/dist/clis/boss/invite.d.ts +1 -0
- package/dist/clis/boss/invite.js +158 -0
- package/dist/clis/boss/joblist.d.ts +1 -0
- package/dist/clis/boss/joblist.js +55 -0
- package/dist/clis/boss/mark.d.ts +1 -0
- package/dist/clis/boss/mark.js +141 -0
- package/dist/clis/boss/recommend.d.ts +1 -0
- package/dist/clis/boss/recommend.js +83 -0
- package/dist/clis/boss/stats.d.ts +1 -0
- package/dist/clis/boss/stats.js +116 -0
- package/dist/clis/sinafinance/news.d.ts +7 -0
- package/dist/clis/sinafinance/news.js +61 -0
- package/dist/clis/wikipedia/search.d.ts +1 -0
- package/dist/clis/wikipedia/search.js +30 -0
- package/dist/clis/wikipedia/summary.d.ts +1 -0
- package/dist/clis/wikipedia/summary.js +28 -0
- package/dist/clis/wikipedia/utils.d.ts +8 -0
- package/dist/clis/wikipedia/utils.js +18 -0
- package/dist/clis/xiaohongshu/creator-note-detail.d.ts +64 -5
- package/dist/clis/xiaohongshu/creator-note-detail.js +258 -69
- package/dist/clis/xiaohongshu/creator-note-detail.test.d.ts +1 -0
- package/dist/clis/xiaohongshu/creator-note-detail.test.js +211 -0
- package/dist/clis/xiaohongshu/creator-notes-summary.d.ts +28 -0
- package/dist/clis/xiaohongshu/creator-notes-summary.js +92 -0
- package/dist/clis/xiaohongshu/creator-notes-summary.test.d.ts +1 -0
- package/dist/clis/xiaohongshu/creator-notes-summary.test.js +49 -0
- package/dist/clis/xiaohongshu/creator-notes.d.ts +18 -5
- package/dist/clis/xiaohongshu/creator-notes.js +159 -71
- package/dist/clis/xiaohongshu/creator-notes.test.d.ts +1 -0
- package/dist/clis/xiaohongshu/creator-notes.test.js +162 -0
- package/dist/external.d.ts +20 -0
- package/dist/external.js +159 -0
- package/docs/.vitepress/config.mts +1 -0
- package/docs/public/CNAME +1 -0
- package/package.json +1 -1
- package/src/bilibili.ts +4 -2
- package/src/browser/cdp.ts +3 -3
- package/src/cli.ts +56 -1
- package/src/clis/antigravity/README.md +3 -46
- package/src/clis/antigravity/serve.ts +323 -50
- package/src/clis/arxiv/paper.ts +21 -0
- package/src/clis/arxiv/search.ts +24 -0
- package/src/clis/arxiv/utils.ts +63 -0
- package/src/clis/boss/batchgreet.ts +167 -0
- package/src/clis/boss/exchange.ts +126 -0
- package/src/clis/boss/greet.ts +198 -0
- package/src/clis/boss/invite.ts +177 -0
- package/src/clis/boss/joblist.ts +63 -0
- package/src/clis/boss/mark.ts +155 -0
- package/src/clis/boss/recommend.ts +94 -0
- package/src/clis/boss/stats.ts +130 -0
- package/src/clis/chaoxing/README.md +2 -24
- package/src/clis/chatgpt/README.md +3 -42
- package/src/clis/chatwise/README.md +3 -36
- package/src/clis/codex/README.md +3 -32
- package/src/clis/cursor/README.md +3 -31
- package/src/clis/discord-app/README.md +2 -25
- package/src/clis/feishu/README.md +2 -17
- package/src/clis/neteasemusic/README.md +3 -29
- package/src/clis/notion/README.md +2 -26
- package/src/clis/sinafinance/news.ts +76 -0
- package/src/clis/wechat/README.md +2 -25
- package/src/clis/wikipedia/search.ts +32 -0
- package/src/clis/wikipedia/summary.ts +28 -0
- package/src/clis/wikipedia/utils.ts +20 -0
- package/src/clis/xiaohongshu/creator-note-detail.test.ts +223 -0
- package/src/clis/xiaohongshu/creator-note-detail.ts +340 -72
- package/src/clis/xiaohongshu/creator-notes-summary.test.ts +54 -0
- package/src/clis/xiaohongshu/creator-notes-summary.ts +120 -0
- package/src/clis/xiaohongshu/creator-notes.test.ts +178 -0
- package/src/clis/xiaohongshu/creator-notes.ts +215 -75
- package/src/daemon.ts +3 -3
- package/src/external-clis.yaml +39 -0
- package/src/external.ts +182 -0
- package/CDP.md +0 -103
- package/CDP.zh-CN.md +0 -103
- package/CLI-ELECTRON.md +0 -125
|
@@ -1,44 +1,5 @@
|
|
|
1
|
-
# ChatGPT
|
|
1
|
+
# ChatGPT Adapter
|
|
2
2
|
|
|
3
|
-
Control the **ChatGPT macOS Desktop App**
|
|
3
|
+
Control the **ChatGPT macOS Desktop App** from the terminal via AppleScript or CDP.
|
|
4
4
|
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
The current built-in commands use native AppleScript automation — no extra launch flags needed.
|
|
8
|
-
|
|
9
|
-
### Prerequisites
|
|
10
|
-
1. Install the official [ChatGPT Desktop App](https://openai.com/chatgpt/mac/) from OpenAI.
|
|
11
|
-
2. Grant **Accessibility permissions** to your terminal app (Terminal / iTerm / Warp) in **System Settings → Privacy & Security → Accessibility**. This is required for System Events keystroke simulation.
|
|
12
|
-
|
|
13
|
-
### Commands
|
|
14
|
-
- `opencli chatgpt status`: Check if the ChatGPT app is currently running.
|
|
15
|
-
- `opencli chatgpt new`: Activate ChatGPT and press `Cmd+N` to start a new conversation.
|
|
16
|
-
- `opencli chatgpt send "message"`: Copy your message to clipboard, activate ChatGPT, paste, and submit.
|
|
17
|
-
- `opencli chatgpt read`: Copy the last AI response via `Cmd+Shift+C` and return it as text.
|
|
18
|
-
|
|
19
|
-
## Approach 2: CDP (Advanced, Electron Debug Mode)
|
|
20
|
-
|
|
21
|
-
ChatGPT Desktop is also an Electron app and can be launched with a remote debugging port for deeper automation via CDP:
|
|
22
|
-
|
|
23
|
-
```bash
|
|
24
|
-
/Applications/ChatGPT.app/Contents/MacOS/ChatGPT \
|
|
25
|
-
--remote-debugging-port=9224
|
|
26
|
-
```
|
|
27
|
-
|
|
28
|
-
Then set the endpoint:
|
|
29
|
-
```bash
|
|
30
|
-
export OPENCLI_CDP_ENDPOINT="http://127.0.0.1:9224"
|
|
31
|
-
```
|
|
32
|
-
|
|
33
|
-
> **Note**: The CDP approach enables future advanced commands like DOM inspection, model switching, and code extraction — similar to the Cursor and Codex adapters.
|
|
34
|
-
|
|
35
|
-
## How It Works
|
|
36
|
-
|
|
37
|
-
- **AppleScript mode**: Uses `osascript` and `pbcopy`/`pbpaste` for clipboard-based text transfer. No remote debugging port needed.
|
|
38
|
-
- **CDP mode**: Connects via Chrome DevTools Protocol to the Electron renderer process for direct DOM manipulation.
|
|
39
|
-
|
|
40
|
-
## Limitations
|
|
41
|
-
|
|
42
|
-
- macOS only (AppleScript dependency)
|
|
43
|
-
- AppleScript mode requires Accessibility permissions
|
|
44
|
-
- `read` command copies the last response — earlier messages need manual scroll
|
|
5
|
+
📖 **Full documentation**: [docs/adapters/desktop/chatgpt](../../../docs/adapters/desktop/chatgpt.md)
|
|
@@ -1,38 +1,5 @@
|
|
|
1
|
-
# ChatWise Adapter
|
|
1
|
+
# ChatWise Adapter
|
|
2
2
|
|
|
3
|
-
Control the **ChatWise Desktop App**
|
|
3
|
+
Control the **ChatWise Desktop App** (multi-LLM client) from the terminal via CDP.
|
|
4
4
|
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
1. Install [ChatWise](https://chatwise.app/).
|
|
8
|
-
2. Launch with remote debugging port:
|
|
9
|
-
```bash
|
|
10
|
-
/Applications/ChatWise.app/Contents/MacOS/ChatWise \
|
|
11
|
-
--remote-debugging-port=9228
|
|
12
|
-
```
|
|
13
|
-
|
|
14
|
-
## Setup
|
|
15
|
-
|
|
16
|
-
```bash
|
|
17
|
-
export OPENCLI_CDP_ENDPOINT="http://127.0.0.1:9228"
|
|
18
|
-
```
|
|
19
|
-
|
|
20
|
-
## Commands
|
|
21
|
-
|
|
22
|
-
### Diagnostics
|
|
23
|
-
- `opencli chatwise status`: Check CDP connection status.
|
|
24
|
-
- `opencli chatwise screenshot`: Export DOM + accessibility snapshot.
|
|
25
|
-
|
|
26
|
-
### Chat
|
|
27
|
-
- `opencli chatwise new`: Start a new conversation (`Cmd+N`).
|
|
28
|
-
- `opencli chatwise send "message"`: Send a message to the active chat.
|
|
29
|
-
- `opencli chatwise read`: Read the current conversation.
|
|
30
|
-
- `opencli chatwise ask "prompt"`: Send + wait for response + return it (one-shot).
|
|
31
|
-
|
|
32
|
-
### AI Features
|
|
33
|
-
- `opencli chatwise model`: Get the current AI model.
|
|
34
|
-
- `opencli chatwise model gpt-4`: Switch to a different model.
|
|
35
|
-
|
|
36
|
-
### Organization
|
|
37
|
-
- `opencli chatwise history`: List conversations from the sidebar.
|
|
38
|
-
- `opencli chatwise export`: Export conversation as Markdown.
|
|
5
|
+
📖 **Full documentation**: [docs/adapters/desktop/chatwise](../../../docs/adapters/desktop/chatwise.md)
|
package/src/clis/codex/README.md
CHANGED
|
@@ -1,34 +1,5 @@
|
|
|
1
|
-
#
|
|
1
|
+
# Codex Adapter
|
|
2
2
|
|
|
3
|
-
Control the **OpenAI Codex Desktop App**
|
|
4
|
-
Because Codex is built on Electron, OpenCLI can directly drive its internal UI, automate slash commands, and manipulate its AI agent threads.
|
|
3
|
+
Control the **OpenAI Codex Desktop App** via Chrome DevTools Protocol (CDP).
|
|
5
4
|
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
1. You must have the official OpenAI Codex app installed.
|
|
9
|
-
2. Launch it via the terminal and expose the remote debugging port:
|
|
10
|
-
```bash
|
|
11
|
-
# macOS
|
|
12
|
-
/Applications/Codex.app/Contents/MacOS/Codex --remote-debugging-port=9222
|
|
13
|
-
```
|
|
14
|
-
|
|
15
|
-
## Setup
|
|
16
|
-
|
|
17
|
-
Export the CDP endpoint in your shell:
|
|
18
|
-
```bash
|
|
19
|
-
export OPENCLI_CODEX_CDP_ENDPOINT="http://127.0.0.1:9222"
|
|
20
|
-
```
|
|
21
|
-
|
|
22
|
-
## Commands
|
|
23
|
-
|
|
24
|
-
### Diagnostics
|
|
25
|
-
- `opencli codex status`: Checks connection and reads the current active window URL/title.
|
|
26
|
-
- `opencli codex dump`: Dumps the full UI DOM and Accessibility tree into `/tmp` (ideal for building AI automation tools on top of it).
|
|
27
|
-
|
|
28
|
-
### Agent Manipulation
|
|
29
|
-
- `opencli codex new`: Simulates `Cmd+N` to start a completely fresh and isolated Git Worktree thread context.
|
|
30
|
-
- `opencli codex send "message"`: Robustly finds the active Thread Composer and injects your text.
|
|
31
|
-
- *Pro-tip*: You can trigger internal shortcuts by sending them, e.g., `opencli codex send "/review"` or `opencli codex send "$imagegen draw a cat"`.
|
|
32
|
-
- `opencli codex read`: Extracts the entire current thread history and AI reasoning logs into readable text.
|
|
33
|
-
- `opencli codex extract-diff`: Automatically scrapes any visual Patch chunks and Code Diffs the AI generated inside the review UI.
|
|
34
|
-
- `opencli codex model`: Get the currently active AI model.
|
|
5
|
+
📖 **Full documentation**: [docs/adapters/desktop/codex](../../../docs/adapters/desktop/codex.md)
|
|
@@ -1,33 +1,5 @@
|
|
|
1
|
-
# Cursor Adapter
|
|
1
|
+
# Cursor Adapter
|
|
2
2
|
|
|
3
|
-
Control the **Cursor IDE** from the terminal via Chrome DevTools Protocol (CDP).
|
|
3
|
+
Control the **Cursor IDE** from the terminal via Chrome DevTools Protocol (CDP).
|
|
4
4
|
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
1. Install [Cursor](https://cursor.sh/).
|
|
8
|
-
2. Launch it with the remote debugging port:
|
|
9
|
-
```bash
|
|
10
|
-
/Applications/Cursor.app/Contents/MacOS/Cursor --remote-debugging-port=9226
|
|
11
|
-
```
|
|
12
|
-
|
|
13
|
-
## Setup
|
|
14
|
-
|
|
15
|
-
```bash
|
|
16
|
-
export OPENCLI_CDP_ENDPOINT="http://127.0.0.1:9226"
|
|
17
|
-
```
|
|
18
|
-
|
|
19
|
-
## Commands
|
|
20
|
-
|
|
21
|
-
### Diagnostics
|
|
22
|
-
- `opencli cursor status`: Check CDP connection status.
|
|
23
|
-
- `opencli cursor dump`: Dump the full DOM and Accessibility snapshot to `/tmp/cursor-dom.html` and `/tmp/cursor-snapshot.json`.
|
|
24
|
-
|
|
25
|
-
### Chat Manipulation
|
|
26
|
-
- `opencli cursor new`: Press `Cmd+N` to start a new file/tab.
|
|
27
|
-
- `opencli cursor send "message"`: Inject text into the active Composer/Chat input and submit.
|
|
28
|
-
- `opencli cursor read`: Extract the full conversation history from the active chat panel.
|
|
29
|
-
|
|
30
|
-
### AI Features
|
|
31
|
-
- `opencli cursor composer "prompt"`: Open the Composer panel (`Cmd+I`) and send a prompt for inline AI editing.
|
|
32
|
-
- `opencli cursor model`: Get the currently active AI model (e.g., `claude-4.5-sonnet`).
|
|
33
|
-
- `opencli cursor extract-code`: Extract all code blocks from the current conversation.
|
|
5
|
+
📖 **Full documentation**: [docs/adapters/desktop/cursor](../../../docs/adapters/desktop/cursor.md)
|
|
@@ -1,28 +1,5 @@
|
|
|
1
|
-
# Discord
|
|
1
|
+
# Discord Adapter
|
|
2
2
|
|
|
3
3
|
Control the **Discord Desktop App** from the terminal via Chrome DevTools Protocol (CDP).
|
|
4
4
|
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
Launch with remote debugging port:
|
|
8
|
-
```bash
|
|
9
|
-
/Applications/Discord.app/Contents/MacOS/Discord --remote-debugging-port=9232
|
|
10
|
-
```
|
|
11
|
-
|
|
12
|
-
## Setup
|
|
13
|
-
|
|
14
|
-
```bash
|
|
15
|
-
export OPENCLI_CDP_ENDPOINT="http://127.0.0.1:9232"
|
|
16
|
-
```
|
|
17
|
-
|
|
18
|
-
## Commands
|
|
19
|
-
|
|
20
|
-
| Command | Description |
|
|
21
|
-
|---------|-------------|
|
|
22
|
-
| `discord status` | Check CDP connection |
|
|
23
|
-
| `discord send "message"` | Send a message in the active channel |
|
|
24
|
-
| `discord read` | Read recent messages |
|
|
25
|
-
| `discord channels` | List channels in the current server |
|
|
26
|
-
| `discord servers` | List all joined servers |
|
|
27
|
-
| `discord search "query"` | Search messages (Cmd+F) |
|
|
28
|
-
| `discord members` | List online members |
|
|
5
|
+
📖 **Full documentation**: [docs/adapters/desktop/discord](../../../docs/adapters/desktop/discord.md)
|
|
@@ -1,20 +1,5 @@
|
|
|
1
|
-
# Feishu (飞书/Lark)
|
|
1
|
+
# Feishu (飞书/Lark) Adapter
|
|
2
2
|
|
|
3
3
|
Control **Feishu/Lark Desktop** from the terminal via AppleScript.
|
|
4
4
|
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
## Prerequisites
|
|
8
|
-
|
|
9
|
-
1. Feishu/Lark must be running and logged in
|
|
10
|
-
2. Terminal must have **Accessibility permission**
|
|
11
|
-
|
|
12
|
-
## Commands
|
|
13
|
-
|
|
14
|
-
| Command | Description |
|
|
15
|
-
|---------|-------------|
|
|
16
|
-
| `feishu status` | Check if Feishu/Lark is running |
|
|
17
|
-
| `feishu send "msg"` | Send message in active chat (paste + Enter) |
|
|
18
|
-
| `feishu read` | Read current chat (Cmd+A → Cmd+C) |
|
|
19
|
-
| `feishu search "query"` | Global search (Cmd+K) |
|
|
20
|
-
| `feishu new` | New message/document (Cmd+N) |
|
|
5
|
+
📖 **Full documentation**: [docs/adapters/desktop/feishu](../../../docs/adapters/desktop/feishu.md)
|
|
@@ -1,31 +1,5 @@
|
|
|
1
|
-
# NeteaseMusic
|
|
1
|
+
# NeteaseMusic (网易云音乐) Adapter
|
|
2
2
|
|
|
3
|
-
Control **NeteaseMusic**
|
|
3
|
+
Control **NeteaseMusic** from the terminal via Chrome DevTools Protocol (CDP/CEF).
|
|
4
4
|
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
Launch with remote debugging port:
|
|
8
|
-
```bash
|
|
9
|
-
/Applications/NeteaseMusic.app/Contents/MacOS/NeteaseMusic --remote-debugging-port=9234
|
|
10
|
-
```
|
|
11
|
-
|
|
12
|
-
## Setup
|
|
13
|
-
|
|
14
|
-
```bash
|
|
15
|
-
export OPENCLI_CDP_ENDPOINT="http://127.0.0.1:9234"
|
|
16
|
-
```
|
|
17
|
-
|
|
18
|
-
## Commands
|
|
19
|
-
|
|
20
|
-
| Command | Description |
|
|
21
|
-
|---------|-------------|
|
|
22
|
-
| `neteasemusic status` | Check CDP connection |
|
|
23
|
-
| `neteasemusic playing` | Current song info (title, artist, album) |
|
|
24
|
-
| `neteasemusic play` | Play / Pause toggle |
|
|
25
|
-
| `neteasemusic next` | Skip to next song |
|
|
26
|
-
| `neteasemusic prev` | Go to previous song |
|
|
27
|
-
| `neteasemusic search "query"` | Search songs, artists |
|
|
28
|
-
| `neteasemusic playlist` | Show current playback queue |
|
|
29
|
-
| `neteasemusic like` | Like / unlike current song |
|
|
30
|
-
| `neteasemusic lyrics` | Get lyrics of current song |
|
|
31
|
-
| `neteasemusic volume [0-100]` | Get or set volume |
|
|
5
|
+
📖 **Full documentation**: [docs/adapters/desktop/neteasemusic](../../../docs/adapters/desktop/neteasemusic.md)
|
|
@@ -1,29 +1,5 @@
|
|
|
1
|
-
# Notion
|
|
1
|
+
# Notion Adapter
|
|
2
2
|
|
|
3
3
|
Control the **Notion Desktop App** from the terminal via Chrome DevTools Protocol (CDP).
|
|
4
4
|
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
Launch with remote debugging port:
|
|
8
|
-
```bash
|
|
9
|
-
/Applications/Notion.app/Contents/MacOS/Notion --remote-debugging-port=9230
|
|
10
|
-
```
|
|
11
|
-
|
|
12
|
-
## Setup
|
|
13
|
-
|
|
14
|
-
```bash
|
|
15
|
-
export OPENCLI_CDP_ENDPOINT="http://127.0.0.1:9230"
|
|
16
|
-
```
|
|
17
|
-
|
|
18
|
-
## Commands
|
|
19
|
-
|
|
20
|
-
| Command | Description |
|
|
21
|
-
|---------|-------------|
|
|
22
|
-
| `notion status` | Check CDP connection |
|
|
23
|
-
| `notion search "query"` | Quick Find search (Cmd+P) |
|
|
24
|
-
| `notion read` | Read the current page content |
|
|
25
|
-
| `notion new "title"` | Create a new page (Cmd+N) |
|
|
26
|
-
| `notion write "text"` | Append text to the current page |
|
|
27
|
-
| `notion sidebar` | List pages from the sidebar |
|
|
28
|
-
| `notion favorites` | List pages from the Favorites section |
|
|
29
|
-
| `notion export` | Export page as Markdown |
|
|
5
|
+
📖 **Full documentation**: [docs/adapters/desktop/notion](../../../docs/adapters/desktop/notion.md)
|
|
@@ -0,0 +1,76 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Sina Finance 7x24 live news feed.
|
|
3
|
+
*
|
|
4
|
+
* Uses the public CJ API — no key or browser required.
|
|
5
|
+
* https://app.cj.sina.com.cn/api/news/pc
|
|
6
|
+
*/
|
|
7
|
+
|
|
8
|
+
import { cli, Strategy } from '../../registry.js';
|
|
9
|
+
import { CliError } from '../../errors.js';
|
|
10
|
+
|
|
11
|
+
// User-facing type (0-9) → Sina API tag ID
|
|
12
|
+
const TYPE_MAP = [
|
|
13
|
+
0, // 0: 全部
|
|
14
|
+
10, // 1: A股
|
|
15
|
+
1, // 2: 宏观
|
|
16
|
+
3, // 3: 公司
|
|
17
|
+
4, // 4: 数据
|
|
18
|
+
5, // 5: 市场
|
|
19
|
+
102, // 6: 国际
|
|
20
|
+
6, // 7: 观点
|
|
21
|
+
6, // 8: 央行
|
|
22
|
+
8, // 9: 其它
|
|
23
|
+
] as const;
|
|
24
|
+
|
|
25
|
+
interface SinaNewsItem {
|
|
26
|
+
id?: string;
|
|
27
|
+
create_time?: string;
|
|
28
|
+
rich_text?: string;
|
|
29
|
+
view_num?: number;
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
function stripHtml(html: string): string {
|
|
33
|
+
return html.replace(/<[^>]+>/g, '').trim();
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
cli({
|
|
37
|
+
site: 'sinafinance',
|
|
38
|
+
name: 'news',
|
|
39
|
+
description: '新浪财经 7x24 小时实时快讯',
|
|
40
|
+
domain: 'app.cj.sina.com.cn',
|
|
41
|
+
strategy: Strategy.PUBLIC,
|
|
42
|
+
browser: false,
|
|
43
|
+
args: [
|
|
44
|
+
{ name: 'limit', type: 'int', default: 20, help: 'Max results (max 50)' },
|
|
45
|
+
{ name: 'type', type: 'int', default: 0, help: 'News type: 0=全部 1=A股 2=宏观 3=公司 4=数据 5=市场 6=国际 7=观点 8=央行 9=其它' },
|
|
46
|
+
],
|
|
47
|
+
columns: ['id', 'time', 'content', 'views'],
|
|
48
|
+
func: async (_page, args) => {
|
|
49
|
+
const limit = Math.max(1, Math.min(Number(args.limit), 50));
|
|
50
|
+
const apiTag = TYPE_MAP[args.type as number] ?? 0;
|
|
51
|
+
|
|
52
|
+
const params = new URLSearchParams({
|
|
53
|
+
page: '1',
|
|
54
|
+
size: String(limit),
|
|
55
|
+
tag: String(apiTag),
|
|
56
|
+
});
|
|
57
|
+
|
|
58
|
+
const res = await fetch(`https://app.cj.sina.com.cn/api/news/pc?${params}`);
|
|
59
|
+
if (!res.ok) {
|
|
60
|
+
throw new CliError('FETCH_ERROR', `Sina Finance API HTTP ${res.status}`, 'Check your network connection');
|
|
61
|
+
}
|
|
62
|
+
const json = await res.json() as { result?: { data?: { feed?: { list?: SinaNewsItem[] } } } };
|
|
63
|
+
const list = json?.result?.data?.feed?.list ?? [];
|
|
64
|
+
|
|
65
|
+
if (!list.length) {
|
|
66
|
+
throw new CliError('NOT_FOUND', 'No news found', 'Try a different type or increase limit');
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
return list.map((item) => ({
|
|
70
|
+
id: item.id ?? '',
|
|
71
|
+
time: item.create_time ?? '',
|
|
72
|
+
content: stripHtml(item.rich_text ?? ''),
|
|
73
|
+
views: item.view_num ?? 0,
|
|
74
|
+
}));
|
|
75
|
+
},
|
|
76
|
+
});
|
|
@@ -1,28 +1,5 @@
|
|
|
1
|
-
# WeChat (微信)
|
|
1
|
+
# WeChat (微信) Adapter
|
|
2
2
|
|
|
3
3
|
Control **WeChat Mac Desktop** from the terminal via AppleScript + Accessibility API.
|
|
4
4
|
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
## Prerequisites
|
|
8
|
-
|
|
9
|
-
1. WeChat must be running and logged in
|
|
10
|
-
2. Terminal must have **Accessibility permission** (System Settings → Privacy & Security → Accessibility)
|
|
11
|
-
|
|
12
|
-
## Commands
|
|
13
|
-
|
|
14
|
-
| Command | Description |
|
|
15
|
-
|---------|-------------|
|
|
16
|
-
| `wechat status` | Check if WeChat is running |
|
|
17
|
-
| `wechat send "msg"` | Send message in the active chat (clipboard paste + Enter) |
|
|
18
|
-
| `wechat read` | Read current chat content (Cmd+A → Cmd+C) |
|
|
19
|
-
| `wechat search "keyword"` | Open search and type a query (Cmd+F) |
|
|
20
|
-
| `wechat chats` | Switch to Chats tab (Cmd+1) |
|
|
21
|
-
| `wechat contacts` | Switch to Contacts tab (Cmd+2) |
|
|
22
|
-
|
|
23
|
-
## Limitations
|
|
24
|
-
|
|
25
|
-
- **No CDP support** — WeChat is native Cocoa, not Electron
|
|
26
|
-
- `send` requires the correct conversation to be already open
|
|
27
|
-
- `read` captures whatever is visible via select-all + copy
|
|
28
|
-
- `search` types the query but cannot programmatically click results
|
|
5
|
+
📖 **Full documentation**: [docs/adapters/desktop/wechat](../../../docs/adapters/desktop/wechat.md)
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
import { cli, Strategy } from '../../registry.js';
|
|
2
|
+
import { CliError } from '../../errors.js';
|
|
3
|
+
import { wikiFetch } from './utils.js';
|
|
4
|
+
|
|
5
|
+
interface WikiSearchResult { title: string; snippet: string; }
|
|
6
|
+
|
|
7
|
+
cli({
|
|
8
|
+
site: 'wikipedia',
|
|
9
|
+
name: 'search',
|
|
10
|
+
description: 'Search Wikipedia articles',
|
|
11
|
+
strategy: Strategy.PUBLIC,
|
|
12
|
+
browser: false,
|
|
13
|
+
args: [
|
|
14
|
+
{ name: 'keyword', positional: true, required: true, help: 'Search keyword' },
|
|
15
|
+
{ name: 'limit', type: 'int', default: 10, help: 'Max results' },
|
|
16
|
+
{ name: 'lang', default: 'en', help: 'Language code (e.g. en, zh, ja)' },
|
|
17
|
+
],
|
|
18
|
+
columns: ['title', 'snippet', 'url'],
|
|
19
|
+
func: async (_page, args) => {
|
|
20
|
+
const limit = Math.max(1, Math.min(Number(args.limit), 50));
|
|
21
|
+
const lang = args.lang || 'en';
|
|
22
|
+
const q = encodeURIComponent(args.keyword);
|
|
23
|
+
const data = await wikiFetch(lang, `/w/api.php?action=query&list=search&srsearch=${q}&srlimit=${limit}&format=json&utf8=1`) as { query?: { search?: WikiSearchResult[] } };
|
|
24
|
+
const results = data?.query?.search;
|
|
25
|
+
if (!results?.length) throw new CliError('NOT_FOUND', 'No articles found', 'Try a different keyword');
|
|
26
|
+
return results.map((r) => ({
|
|
27
|
+
title: r.title,
|
|
28
|
+
snippet: r.snippet.replace(/<[^>]+>/g, '').slice(0, 120),
|
|
29
|
+
url: `https://${lang}.wikipedia.org/wiki/${encodeURIComponent(r.title.replace(/ /g, '_'))}`,
|
|
30
|
+
}));
|
|
31
|
+
},
|
|
32
|
+
});
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
import { cli, Strategy } from '../../registry.js';
|
|
2
|
+
import { CliError } from '../../errors.js';
|
|
3
|
+
import { wikiFetch } from './utils.js';
|
|
4
|
+
|
|
5
|
+
cli({
|
|
6
|
+
site: 'wikipedia',
|
|
7
|
+
name: 'summary',
|
|
8
|
+
description: 'Get Wikipedia article summary',
|
|
9
|
+
strategy: Strategy.PUBLIC,
|
|
10
|
+
browser: false,
|
|
11
|
+
args: [
|
|
12
|
+
{ name: 'title', positional: true, required: true, help: 'Article title (e.g. "Transformer (machine learning model)")' },
|
|
13
|
+
{ name: 'lang', default: 'en', help: 'Language code (e.g. en, zh, ja)' },
|
|
14
|
+
],
|
|
15
|
+
columns: ['title', 'description', 'extract', 'url'],
|
|
16
|
+
func: async (_page, args) => {
|
|
17
|
+
const lang = args.lang || 'en';
|
|
18
|
+
const title = encodeURIComponent(args.title.replace(/ /g, '_'));
|
|
19
|
+
const data = await wikiFetch(lang, `/api/rest_v1/page/summary/${title}`) as { title?: string; description?: string; extract?: string; content_urls?: { desktop?: { page?: string } } };
|
|
20
|
+
if (!data?.title) throw new CliError('NOT_FOUND', `Article "${args.title}" not found`, 'Try searching first: opencli wikipedia search <keyword>');
|
|
21
|
+
return [{
|
|
22
|
+
title: data.title,
|
|
23
|
+
description: data.description ?? '-',
|
|
24
|
+
extract: (data.extract ?? '').slice(0, 300),
|
|
25
|
+
url: data.content_urls?.desktop?.page ?? `https://${lang}.wikipedia.org/wiki/${title}`,
|
|
26
|
+
}];
|
|
27
|
+
},
|
|
28
|
+
});
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Wikipedia adapter utilities.
|
|
3
|
+
*
|
|
4
|
+
* Uses the public MediaWiki REST API and Action API — no key required.
|
|
5
|
+
* REST API: https://en.wikipedia.org/api/rest_v1/
|
|
6
|
+
* Action API: https://en.wikipedia.org/w/api.php
|
|
7
|
+
*/
|
|
8
|
+
|
|
9
|
+
import { CliError } from '../../errors.js';
|
|
10
|
+
|
|
11
|
+
export async function wikiFetch(lang: string, path: string): Promise<unknown> {
|
|
12
|
+
const url = `https://${lang}.wikipedia.org${path}`;
|
|
13
|
+
const resp = await fetch(url, {
|
|
14
|
+
headers: { 'User-Agent': 'opencli/1.0 (https://github.com/jackwener/opencli)' },
|
|
15
|
+
});
|
|
16
|
+
if (!resp.ok) {
|
|
17
|
+
throw new CliError('FETCH_ERROR', `Wikipedia API HTTP ${resp.status}`, `Check your title or search term`);
|
|
18
|
+
}
|
|
19
|
+
return resp.json();
|
|
20
|
+
}
|