@simonyea/holysheep-cli 1.1.3 → 1.1.5

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 CHANGED
@@ -41,7 +41,7 @@ Instead of manually editing config files and environment variables for each tool
41
41
  | [Aider](https://aider.chat) | `pip install aider-install && aider-install` | `~/.aider.conf.yml` | ✅ Auto |
42
42
  | [Continue.dev](https://continue.dev) | VS Code marketplace | `~/.continue/config.yaml` | ✅ Auto |
43
43
  | [OpenCode](https://opencode.ai) | `brew install anomalyco/tap/opencode` | `~/.config/opencode/opencode.json` | ✅ Auto |
44
- | [OpenClaw](https://github.com/iOfficeAI/AionUi) | Download from website | `~/.openclaw/settings.json` | ✅ Auto |
44
+ | [OpenClaw](https://github.com/openclaw/openclaw) | `npm i -g openclaw@latest` | `~/.openclaw/openclaw.json` | ✅ Auto |
45
45
  | [Cursor](https://cursor.sh) | Download from website | GUI only (encrypted storage) | ⚠️ Manual |
46
46
  | [Gemini CLI](https://github.com/google-gemini/gemini-cli) | `npm i -g @google/gemini-cli` | Google protocol only | ❌ Not supported |
47
47
 
@@ -135,7 +135,7 @@ HolySheep 是面向中国开发者的 Claude/GPT/Gemini 官方 API 中转服务
135
135
  | [Aider](https://aider.chat) | `pip install aider-install && aider-install` | `~/.aider.conf.yml` | ✅ 自动 |
136
136
  | [Continue.dev](https://continue.dev) | VS Code 插件市场 | `~/.continue/config.yaml` | ✅ 自动 |
137
137
  | [OpenCode](https://opencode.ai) | `brew install anomalyco/tap/opencode` | `~/.config/opencode/opencode.json` | ✅ 自动 |
138
- | [OpenClaw](https://github.com/iOfficeAI/AionUi) | 官网下载 | `~/.openclaw/settings.json` | ✅ 自动 |
138
+ | [OpenClaw](https://github.com/openclaw/openclaw) | `npm i -g openclaw@latest` | `~/.openclaw/openclaw.json` | ✅ 自动 |
139
139
  | [Cursor](https://cursor.sh) | 官网下载 | GUI 手动配置(加密存储) | ⚠️ 手动 |
140
140
  | [Gemini CLI](https://github.com/google-gemini/gemini-cli) | `npm i -g @google/gemini-cli` | 仅支持 Google 官方协议 | ❌ 不支持 |
141
141
 
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@simonyea/holysheep-cli",
3
- "version": "1.1.3",
3
+ "version": "1.1.5",
4
4
  "description": "一键配置所有 AI 编程工具接入 HolySheep API — Claude Code / Codex / Gemini CLI / OpenCode / OpenClaw / Aider / Cursor",
5
5
  "keywords": [
6
6
  "claude",
@@ -15,6 +15,7 @@ const AUTO_INSTALL = {
15
15
  'codex': { cmd: 'npm install -g @openai/codex', mgr: 'npm' },
16
16
  'gemini-cli': { cmd: 'npm install -g @google/gemini-cli', mgr: 'npm' },
17
17
  'opencode': { cmd: 'npm install -g opencode-ai', mgr: 'npm' },
18
+ 'openclaw': { cmd: 'npm install -g openclaw@latest', mgr: 'npm' },
18
19
  'aider': { cmd: 'pip install aider-chat', mgr: 'pip' },
19
20
  }
20
21
 
@@ -44,19 +45,13 @@ async function tryAutoInstall(tool) {
44
45
  spinner.fail(`安装失败,请手动运行: ${chalk.cyan(info.cmd)}`)
45
46
  return false
46
47
  }
47
- // Windows PATH 在当前进程内不会刷新,安装成功即认为可用
48
- if (process.platform === 'win32') {
49
- spinner.succeed(`${tool.name} 安装完成(请重新开一个终端窗口后运行 hs setup 完成配置)`)
50
- return false // 返回 false 跳过配置,让用户重开终端再来
51
- }
52
- // 安装后重新检测
53
- if (tool.checkInstalled()) {
54
- spinner.succeed(`${tool.name} 安装成功`)
55
- return true
56
- } else {
57
- spinner.fail(`${tool.name} 安装后仍未检测到,请手动安装: ${chalk.cyan(info.cmd)}`)
58
- return false
48
+ spinner.succeed(`${tool.name} 安装成功`)
49
+ // Windows PATH 在当前进程内不会刷新,但安装已成功,直接继续配置
50
+ // Windows 再额外做一次检测
51
+ if (process.platform !== 'win32' && !tool.checkInstalled()) {
52
+ console.log(chalk.yellow(` ⚠ 安装后未检测到命令,尝试直接配置...`))
59
53
  }
54
+ return true // 安装成功就视为可配置
60
55
  } catch (e) {
61
56
  spinner.fail(`安装失败: ${e.message}`)
62
57
  return false
@@ -137,6 +132,7 @@ async function setup(options) {
137
132
  const selectedTools = TOOLS.filter(t => toolIds.includes(t.id))
138
133
  const needInstall = selectedTools.filter(t => !t.checkInstalled() && canAutoInstall(t.id))
139
134
  const cantInstall = selectedTools.filter(t => !t.checkInstalled() && !canAutoInstall(t.id))
135
+ const justInstalled = new Set() // 记录本次刚安装成功的工具 id
140
136
 
141
137
  // 提示不能自动安装的工具
142
138
  if (cantInstall.length) {
@@ -156,16 +152,17 @@ async function setup(options) {
156
152
 
157
153
  if (doInstall) {
158
154
  for (const tool of needInstall) {
159
- await tryAutoInstall(tool)
155
+ const ok = await tryAutoInstall(tool)
156
+ if (ok) justInstalled.add(tool.id)
160
157
  }
161
158
  console.log()
162
159
  }
163
160
  }
164
161
 
165
- // Step 4: 配置每个已安装的工具
162
+ // Step 4: 配置每个已安装的工具(包含刚刚安装成功的)
166
163
  const envVarsToWrite = {}
167
164
  const results = []
168
- const toConfigureTools = selectedTools.filter(t => t.checkInstalled())
165
+ const toConfigureTools = selectedTools.filter(t => t.checkInstalled() || justInstalled.has(t.id))
169
166
 
170
167
  if (toConfigureTools.length === 0) {
171
168
  console.log(chalk.yellow('没有可配置的工具(请先安装),退出。'))
@@ -1,43 +1,37 @@
1
1
  /**
2
- * OpenClaw 适配器
3
- * OpenClaw 是基于 Claude Code 架构的开源 AI 编程助手
4
- * 配置方式与 Claude Code 几乎相同,使用 Anthropic API 格式
2
+ * OpenClaw 适配器 (github.com/openclaw/openclaw)
5
3
  *
6
- * 配置文件: ~/.openclaw/settings.json (或 ~/.claude/settings.json 共享)
7
- * 环境变量: ANTHROPIC_API_KEY, ANTHROPIC_BASE_URL
4
+ * OpenClaw 是个人 AI 助手 + 多渠道消息网关
5
+ * 支持 WhatsApp/Telegram/Signal/Discord/iMessage 等 20+ 渠道
8
6
  *
9
- * OpenClaw 也支持通过 AGENTS.md 自定义 agent 行为
7
+ * 安装方式: npm install -g openclaw@latest
8
+ * 配置文件: ~/.openclaw/openclaw.json (JSON5 格式)
9
+ * 文档: https://docs.openclaw.ai
10
+ *
11
+ * HolySheep 接入方式:通过 env.ANTHROPIC_API_KEY + env.ANTHROPIC_BASE_URL
12
+ * 设置 Anthropic provider 自定义 base URL 指向 HolySheep 中继
10
13
  */
11
- const fs = require('fs')
14
+ const fs = require('fs')
12
15
  const path = require('path')
13
- const os = require('os')
16
+ const os = require('os')
14
17
 
15
- function getSettingsFile() {
16
- // OpenClaw 可能用独立配置,也可能共享 Claude 配置
17
- const openclaw = path.join(os.homedir(), '.openclaw', 'settings.json')
18
- const claude = path.join(os.homedir(), '.claude', 'settings.json')
19
- if (fs.existsSync(openclaw)) return openclaw
20
- // 检查是否安装了 openclaw
21
- try {
22
- require('child_process').execSync('which openclaw', { stdio: 'ignore' })
23
- return openclaw
24
- } catch {
25
- return openclaw // 默认路径
26
- }
27
- }
18
+ const OPENCLAW_DIR = path.join(os.homedir(), '.openclaw')
19
+ const CONFIG_FILE = path.join(OPENCLAW_DIR, 'openclaw.json')
28
20
 
29
- function readSettings(file) {
21
+ function readConfig() {
30
22
  try {
31
- if (fs.existsSync(file)) {
32
- return JSON.parse(fs.readFileSync(file, 'utf8').replace(/[\x00-\x1F\x7F]/g, ' '))
23
+ if (fs.existsSync(CONFIG_FILE)) {
24
+ // openclaw.json JSON5 格式,先去掉注释再 parse
25
+ const raw = fs.readFileSync(CONFIG_FILE, 'utf8')
26
+ return JSON.parse(raw.replace(/\/\/[^\n]*/g, '').replace(/\/\*[\s\S]*?\*\//g, ''))
33
27
  }
34
28
  } catch {}
35
29
  return {}
36
30
  }
37
31
 
38
- function writeSettings(file, data) {
39
- fs.mkdirSync(path.dirname(file), { recursive: true })
40
- fs.writeFileSync(file, JSON.stringify(data, null, 2), 'utf8')
32
+ function writeConfig(data) {
33
+ fs.mkdirSync(OPENCLAW_DIR, { recursive: true })
34
+ fs.writeFileSync(CONFIG_FILE, JSON.stringify(data, null, 2), 'utf8')
41
35
  }
42
36
 
43
37
  module.exports = {
@@ -47,30 +41,63 @@ module.exports = {
47
41
  return require('../utils/which').commandExists('openclaw')
48
42
  },
49
43
  isConfigured() {
50
- const file = getSettingsFile()
51
- const s = readSettings(file)
52
- return !!(s.env?.ANTHROPIC_API_KEY || s.env?.ANTHROPIC_AUTH_TOKEN)
44
+ const c = readConfig()
45
+ return !!(
46
+ c.env?.ANTHROPIC_BASE_URL?.includes('holysheep') ||
47
+ c.models?.providers?.holysheep
48
+ )
53
49
  },
54
- configure(apiKey, baseUrlAnthropicNoV1) {
55
- const file = getSettingsFile()
56
- const settings = readSettings(file)
57
- if (!settings.env) settings.env = {}
58
- settings.env.ANTHROPIC_API_KEY = apiKey
59
- settings.env.ANTHROPIC_BASE_URL = baseUrlAnthropicNoV1
60
- writeSettings(file, settings)
61
- return { file, hot: true }
50
+ configure(apiKey, baseUrlAnthropicNoV1, baseUrlOpenAI) {
51
+ const config = readConfig()
52
+
53
+ // 设置环境变量 Anthropic provider 使用 ANTHROPIC_BASE_URL 覆盖默认地址
54
+ if (!config.env) config.env = {}
55
+ config.env.ANTHROPIC_API_KEY = apiKey
56
+ config.env.ANTHROPIC_BASE_URL = baseUrlAnthropicNoV1 // https://api.holysheep.ai
57
+
58
+ // 设置默认模型(如果未配置)
59
+ if (!config.agents) config.agents = {}
60
+ if (!config.agents.defaults) config.agents.defaults = {}
61
+ if (!config.agents.defaults.model) {
62
+ config.agents.defaults.model = { primary: 'anthropic/claude-sonnet-4-5' }
63
+ }
64
+
65
+ // 同时注册一个 holysheep 自定义 provider(支持所有模型)
66
+ if (!config.models) config.models = {}
67
+ config.models.mode = 'merge'
68
+ if (!config.models.providers) config.models.providers = {}
69
+ config.models.providers.holysheep = {
70
+ baseUrl: baseUrlOpenAI, // https://api.holysheep.ai/v1
71
+ apiKey,
72
+ api: 'openai-completions',
73
+ models: [
74
+ { id: 'claude-sonnet-4-5', name: 'Claude Sonnet 4.5 (HolySheep)' },
75
+ { id: 'claude-opus-4-5', name: 'Claude Opus 4.5 (HolySheep)' },
76
+ { id: 'gpt-5.4', name: 'GPT-5.4 (HolySheep)' },
77
+ { id: 'gpt-5', name: 'GPT-5 (HolySheep)' },
78
+ ],
79
+ }
80
+
81
+ writeConfig(config)
82
+ return { file: CONFIG_FILE, hot: false }
62
83
  },
63
84
  reset() {
64
- const file = getSettingsFile()
65
- const settings = readSettings(file)
66
- if (settings.env) {
67
- delete settings.env.ANTHROPIC_API_KEY
68
- delete settings.env.ANTHROPIC_BASE_URL
85
+ const config = readConfig()
86
+ if (config.env) {
87
+ delete config.env.ANTHROPIC_API_KEY
88
+ delete config.env.ANTHROPIC_BASE_URL
89
+ }
90
+ if (config.models?.providers) {
91
+ delete config.models.providers.holysheep
92
+ }
93
+ // 如果默认模型是 anthropic/xxx,清掉
94
+ if (config.agents?.defaults?.model?.primary?.startsWith('anthropic/')) {
95
+ delete config.agents.defaults.model
69
96
  }
70
- writeSettings(file, settings)
97
+ writeConfig(config)
71
98
  },
72
- getConfigPath() { return getSettingsFile() },
73
- hint: '配置方式同 Claude Code,支持热切换',
74
- installCmd: '请访问 openclaw 官网下载安装',
75
- docsUrl: 'https://github.com/iOfficeAI/AionUi',
99
+ getConfigPath() { return CONFIG_FILE },
100
+ hint: '切换后重启 OpenClaw 生效;支持 /model 命令切换模型',
101
+ installCmd: 'npm install -g openclaw@latest',
102
+ docsUrl: 'https://docs.openclaw.ai',
76
103
  }