@aiyiran/myclaw 1.1.114 → 1.1.118
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/injects/inject-minimax.js +135 -58
- package/injects/inject-zai.js +156 -121
- package/package.json +1 -1
- package/skills/minimax-inject/scripts/inject.js +53 -6
|
@@ -5,16 +5,11 @@
|
|
|
5
5
|
*
|
|
6
6
|
* 注入 MiniMax 模型配置到 openclaw.json,并为所有 agent 写入 API Key。
|
|
7
7
|
*
|
|
8
|
-
*
|
|
9
|
-
*
|
|
10
|
-
*
|
|
11
|
-
*
|
|
12
|
-
*
|
|
13
|
-
* 5. 为所有 agent 写入 API Key (auth-profiles.json,不存在则创建)
|
|
14
|
-
*
|
|
15
|
-
* 不触碰: 图片模型、其他 provider、onboard 流程
|
|
16
|
-
*
|
|
17
|
-
* 入口: myclaw inject-minimax [--key sk-xxx]
|
|
8
|
+
* 用法:
|
|
9
|
+
* myclaw inject-minimax # 仅追加 minimax provider,不改默认,副作用最小
|
|
10
|
+
* myclaw inject-minimax --default # 追加 + 设为默认 + 全部对话迁移到 MiniMax-M3
|
|
11
|
+
* myclaw inject-minimax --only # 追加 + 设为默认 + 全部对话迁移 + 清掉所有其他 provider
|
|
12
|
+
* myclaw inject-minimax --key sk-xxx # 使用指定 API Key
|
|
18
13
|
*/
|
|
19
14
|
|
|
20
15
|
const fs = require('fs');
|
|
@@ -24,25 +19,33 @@ const { readConfig, writeConfig } = require('../find-config');
|
|
|
24
19
|
|
|
25
20
|
const DEFAULT_MINIMAX_KEY = "sk-cp-DC5lWd2Stt9CBFzLIT2awP4K-ZEn5AkYwjl3Cdj-mIBmgjxod518F2LaVF2L9c35Wv5-Eox0F1ctJD5vXtB9p3OmxoWLd9ge9zIUIMrCVuqBYdL_s6kb8Qs";
|
|
26
21
|
|
|
22
|
+
const PROVIDER_ID = "minimax";
|
|
23
|
+
const DEFAULT_MODEL = "minimax/MiniMax-M3";
|
|
24
|
+
|
|
27
25
|
function run(cliArgs) {
|
|
28
|
-
// 解析参数
|
|
26
|
+
// ── 解析参数 ──
|
|
29
27
|
let apiKey = null;
|
|
30
|
-
let
|
|
28
|
+
let setDefault = false;
|
|
29
|
+
let onlyMode = false;
|
|
30
|
+
|
|
31
31
|
for (let i = 0; i < cliArgs.length; i++) {
|
|
32
32
|
if (cliArgs[i] === '--key' && cliArgs[i + 1]) {
|
|
33
33
|
apiKey = cliArgs[i + 1];
|
|
34
34
|
i++;
|
|
35
|
-
} else if (cliArgs[i] === '--
|
|
36
|
-
|
|
35
|
+
} else if (cliArgs[i] === '--default') {
|
|
36
|
+
setDefault = true;
|
|
37
|
+
} else if (cliArgs[i] === '--only') {
|
|
38
|
+
onlyMode = true;
|
|
39
|
+
setDefault = true; // --only 隐含 --default
|
|
37
40
|
}
|
|
38
41
|
}
|
|
39
42
|
|
|
40
43
|
if (!apiKey) {
|
|
41
44
|
apiKey = DEFAULT_MINIMAX_KEY;
|
|
42
|
-
console.log('💡 未传入 --key
|
|
45
|
+
console.log('💡 未传入 --key,使用默认 API Key');
|
|
43
46
|
}
|
|
44
47
|
|
|
45
|
-
// 读取配置
|
|
48
|
+
// ── 读取配置 ──
|
|
46
49
|
let config, configPath;
|
|
47
50
|
try {
|
|
48
51
|
({ config, configPath } = readConfig());
|
|
@@ -52,16 +55,47 @@ function run(cliArgs) {
|
|
|
52
55
|
}
|
|
53
56
|
|
|
54
57
|
console.log('📍 找到配置: ' + configPath);
|
|
58
|
+
console.log('📌 模式: ' + (onlyMode ? '--only (独占)' : setDefault ? '--default (设默认)' : '追加'));
|
|
59
|
+
|
|
60
|
+
// ── Step 1:--only 清掉所有其他 provider ──
|
|
61
|
+
if (onlyMode) {
|
|
62
|
+
console.log('');
|
|
63
|
+
console.log('🧹 [--only] 清理其他所有 provider...');
|
|
64
|
+
|
|
65
|
+
if (config.models?.providers) {
|
|
66
|
+
for (const key of Object.keys(config.models.providers)) {
|
|
67
|
+
if (key !== PROVIDER_ID) {
|
|
68
|
+
delete config.models.providers[key];
|
|
69
|
+
console.log(' ✓ 删除 provider: ' + key);
|
|
70
|
+
}
|
|
71
|
+
}
|
|
72
|
+
}
|
|
73
|
+
if (config.auth?.profiles) {
|
|
74
|
+
for (const key of Object.keys(config.auth.profiles)) {
|
|
75
|
+
if (!key.startsWith(PROVIDER_ID + ':')) {
|
|
76
|
+
delete config.auth.profiles[key];
|
|
77
|
+
console.log(' ✓ 删除 auth profile: ' + key);
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
}
|
|
81
|
+
if (config.agents?.defaults?.models) {
|
|
82
|
+
for (const key of Object.keys(config.agents.defaults.models)) {
|
|
83
|
+
if (!key.startsWith(PROVIDER_ID + '/')) {
|
|
84
|
+
delete config.agents.defaults.models[key];
|
|
85
|
+
console.log(' ✓ 删除白名单: ' + key);
|
|
86
|
+
}
|
|
87
|
+
}
|
|
88
|
+
}
|
|
89
|
+
}
|
|
90
|
+
|
|
91
|
+
// ── Step 2:注入 minimax provider 配置 ──
|
|
92
|
+
console.log('');
|
|
93
|
+
console.log('📝 [Step 2] 注入 MiniMax 配置...');
|
|
55
94
|
|
|
56
|
-
// ─── 1. auth profile ───
|
|
57
95
|
if (!config.auth) config.auth = {};
|
|
58
96
|
if (!config.auth.profiles) config.auth.profiles = {};
|
|
59
|
-
config.auth.profiles["minimax:cn"] = {
|
|
60
|
-
provider: "minimax",
|
|
61
|
-
mode: "api_key"
|
|
62
|
-
};
|
|
97
|
+
config.auth.profiles["minimax:cn"] = { provider: "minimax", mode: "api_key" };
|
|
63
98
|
|
|
64
|
-
// ─── 2. minimax provider + 模型定义 ───
|
|
65
99
|
if (!config.models) config.models = {};
|
|
66
100
|
if (!config.models.mode) config.models.mode = "merge";
|
|
67
101
|
if (!config.models.providers) config.models.providers = {};
|
|
@@ -76,74 +110,82 @@ function run(cliArgs) {
|
|
|
76
110
|
name: "MiniMax M3",
|
|
77
111
|
reasoning: true,
|
|
78
112
|
input: ["text"],
|
|
79
|
-
cost: {
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
113
|
+
cost: { input: 0.3, output: 1.2, cacheRead: 0.06, cacheWrite: 0.375 },
|
|
114
|
+
contextWindow: 204800,
|
|
115
|
+
maxTokens: 131072
|
|
116
|
+
},
|
|
117
|
+
{
|
|
118
|
+
id: "MiniMax-M2.7-highspeed",
|
|
119
|
+
name: "MiniMax M2.7 Highspeed",
|
|
120
|
+
reasoning: true,
|
|
121
|
+
input: ["text"],
|
|
122
|
+
cost: { input: 0.3, output: 1.2, cacheRead: 0.06, cacheWrite: 0.375 },
|
|
85
123
|
contextWindow: 204800,
|
|
86
124
|
maxTokens: 131072
|
|
87
125
|
}
|
|
88
126
|
]
|
|
89
127
|
};
|
|
90
128
|
|
|
91
|
-
// ─── 3. 默认聊天模型 ───
|
|
92
129
|
if (!config.agents) config.agents = {};
|
|
93
130
|
if (!config.agents.defaults) config.agents.defaults = {};
|
|
94
|
-
if (
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
131
|
+
if (!config.agents.defaults.models) config.agents.defaults.models = {};
|
|
132
|
+
|
|
133
|
+
// 清理 onboard 残留的无 -highspeed 版本
|
|
134
|
+
delete config.agents.defaults.models["minimax/MiniMax-M2.7"];
|
|
135
|
+
// 白名单:M3 + M2.7-highspeed
|
|
136
|
+
config.agents.defaults.models["minimax/MiniMax-M3"] = {};
|
|
137
|
+
config.agents.defaults.models["minimax/MiniMax-M2.7-highspeed"] = {};
|
|
138
|
+
|
|
139
|
+
// ── Step 3:--default 设默认模型 ──
|
|
140
|
+
if (setDefault) {
|
|
141
|
+
config.agents.defaults.model = { primary: DEFAULT_MODEL };
|
|
142
|
+
console.log('⚡ 默认模型 → ' + DEFAULT_MODEL);
|
|
99
143
|
} else {
|
|
100
|
-
console.log('⊘
|
|
144
|
+
console.log('⊘ 未传 --default,保留现有默认模型');
|
|
101
145
|
}
|
|
102
146
|
|
|
103
|
-
//
|
|
104
|
-
if (
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
147
|
+
// ── --only 额外清除 per-agent 覆盖 ──
|
|
148
|
+
if (onlyMode) {
|
|
149
|
+
let overrideCount = 0;
|
|
150
|
+
for (const agent of (config.agents.list || [])) {
|
|
151
|
+
if (agent.model && agent.model !== DEFAULT_MODEL) {
|
|
152
|
+
delete agent.model;
|
|
153
|
+
overrideCount++;
|
|
154
|
+
}
|
|
155
|
+
}
|
|
156
|
+
if (overrideCount > 0) console.log('🧹 --only: 已清除 ' + overrideCount + ' 个 agent 的独立 model 覆盖');
|
|
157
|
+
}
|
|
108
158
|
|
|
109
|
-
// ─── 写入 openclaw.json ───
|
|
110
159
|
writeConfig(config, configPath);
|
|
111
160
|
console.log('✅ openclaw.json 已更新');
|
|
112
161
|
|
|
113
|
-
//
|
|
114
|
-
|
|
162
|
+
// ── Step 4:为所有 agent 写入 API Key ──
|
|
163
|
+
console.log('');
|
|
164
|
+
console.log('🔑 [Step 4] 写入 API Key 到所有 agent...');
|
|
165
|
+
|
|
115
166
|
const DEFAULT_MAIN_DIR = path.join(os.homedir(), '.openclaw', 'agents', 'main', 'agent');
|
|
116
167
|
const agentList = (config.agents && config.agents.list) || [];
|
|
117
168
|
|
|
118
|
-
// 构建去重的 agentDir 列表,main 默认路径始终存在
|
|
119
169
|
const agentDirs = new Map();
|
|
120
170
|
agentDirs.set(DEFAULT_MAIN_DIR, 'main');
|
|
121
171
|
for (const agent of agentList) {
|
|
122
172
|
if (agent.agentDir) agentDirs.set(agent.agentDir, agent.id);
|
|
123
173
|
}
|
|
124
174
|
|
|
125
|
-
let okCount = 0;
|
|
126
|
-
let skipCount = 0;
|
|
175
|
+
let okCount = 0, skipCount = 0;
|
|
127
176
|
|
|
128
177
|
for (const [agentDir, agentId] of agentDirs) {
|
|
129
178
|
const profilesPath = path.join(agentDir, 'auth-profiles.json');
|
|
130
|
-
|
|
131
|
-
// 读取现有文件,不存在则初始化骨架
|
|
132
179
|
let profiles = { version: 1, profiles: {}, lastGood: {} };
|
|
133
180
|
if (fs.existsSync(profilesPath)) {
|
|
134
181
|
try {
|
|
135
182
|
const parsed = JSON.parse(fs.readFileSync(profilesPath, 'utf8'));
|
|
136
183
|
if (parsed.profiles) profiles = parsed;
|
|
137
184
|
if (!profiles.lastGood) profiles.lastGood = {};
|
|
138
|
-
} catch { /*
|
|
185
|
+
} catch { /* 解析失败用空骨架 */ }
|
|
139
186
|
}
|
|
140
187
|
|
|
141
|
-
|
|
142
|
-
profiles.profiles["minimax:cn"] = {
|
|
143
|
-
type: "api_key",
|
|
144
|
-
provider: "minimax",
|
|
145
|
-
key: apiKey
|
|
146
|
-
};
|
|
188
|
+
profiles.profiles["minimax:cn"] = { type: "api_key", provider: "minimax", key: apiKey };
|
|
147
189
|
profiles.lastGood["minimax"] = "minimax:cn";
|
|
148
190
|
|
|
149
191
|
try {
|
|
@@ -157,11 +199,46 @@ function run(cliArgs) {
|
|
|
157
199
|
}
|
|
158
200
|
}
|
|
159
201
|
|
|
202
|
+
// ── Step 5:--default / --only 迁移全部对话 ──
|
|
203
|
+
if (setDefault) {
|
|
204
|
+
console.log('');
|
|
205
|
+
console.log('🔄 [Step 5] 迁移全部对话 → ' + DEFAULT_MODEL + ' ...');
|
|
206
|
+
let sessionOk = 0, sessionSkip = 0, sessionChanged = 0;
|
|
207
|
+
|
|
208
|
+
for (const [agentDir] of agentDirs) {
|
|
209
|
+
const sessionsPath = path.join(agentDir, '..', 'sessions', 'sessions.json');
|
|
210
|
+
if (!fs.existsSync(sessionsPath)) continue;
|
|
211
|
+
try {
|
|
212
|
+
const sessions = JSON.parse(fs.readFileSync(sessionsPath, 'utf8'));
|
|
213
|
+
let changed = 0;
|
|
214
|
+
for (const key of Object.keys(sessions)) {
|
|
215
|
+
const m = sessions[key]?.model;
|
|
216
|
+
if (!m) continue;
|
|
217
|
+
// 修复无前缀的旧格式残留
|
|
218
|
+
if (m === 'MiniMax-M2.7-highspeed') { sessions[key].model = 'minimax/MiniMax-M3'; changed++; continue; }
|
|
219
|
+
if (m === 'glm-5.1') { sessions[key].model = 'zai/glm-5.1'; changed++; continue; }
|
|
220
|
+
// 统一迁移到新默认
|
|
221
|
+
if (m !== DEFAULT_MODEL) { sessions[key].model = DEFAULT_MODEL; changed++; }
|
|
222
|
+
}
|
|
223
|
+
if (changed > 0) {
|
|
224
|
+
fs.writeFileSync(sessionsPath, JSON.stringify(sessions, null, 2) + '\n', 'utf8');
|
|
225
|
+
sessionChanged += changed;
|
|
226
|
+
}
|
|
227
|
+
sessionOk++;
|
|
228
|
+
} catch {
|
|
229
|
+
sessionSkip++;
|
|
230
|
+
}
|
|
231
|
+
}
|
|
232
|
+
console.log(' 对话迁移: ' + sessionChanged + ' 条,文件: ' + sessionOk + ' 个,跳过: ' + sessionSkip + ' 个');
|
|
233
|
+
}
|
|
234
|
+
|
|
235
|
+
// ── 汇总 ──
|
|
160
236
|
console.log('');
|
|
161
237
|
console.log('✅ MiniMax 注入完成');
|
|
162
|
-
console.log('
|
|
163
|
-
console.log('
|
|
164
|
-
console.log(' Agent:
|
|
238
|
+
console.log(' 默认模型: ' + (setDefault ? DEFAULT_MODEL : '(未修改)'));
|
|
239
|
+
console.log(' 备选模型: minimax/MiniMax-M2.7-highspeed');
|
|
240
|
+
console.log(' Agent: ' + okCount + ' 个写入,' + skipCount + ' 个跳过');
|
|
241
|
+
if (onlyMode) console.log(' 其他 provider 已清除');
|
|
165
242
|
console.log('');
|
|
166
243
|
}
|
|
167
244
|
|
package/injects/inject-zai.js
CHANGED
|
@@ -3,14 +3,13 @@
|
|
|
3
3
|
/**
|
|
4
4
|
* inject-zai.js
|
|
5
5
|
*
|
|
6
|
-
*
|
|
7
|
-
* 同时写入 API Key 到 auth-profiles.json。
|
|
6
|
+
* 注入智谱 GLM 模型配置到 openclaw.json,并为所有 agent 写入 API Key。
|
|
8
7
|
*
|
|
9
|
-
*
|
|
10
|
-
*
|
|
11
|
-
*
|
|
12
|
-
*
|
|
13
|
-
*
|
|
8
|
+
* 用法:
|
|
9
|
+
* myclaw inject-zai # 仅追加 zai provider,不改默认,副作用最小
|
|
10
|
+
* myclaw inject-zai --default # 追加 + 设为默认 + 全部对话迁移到 glm-5.1
|
|
11
|
+
* myclaw inject-zai --only # 追加 + 设为默认 + 全部对话迁移 + 清掉所有其他 provider
|
|
12
|
+
* myclaw inject-zai --key xxx # 使用指定 API Key
|
|
14
13
|
*/
|
|
15
14
|
|
|
16
15
|
const { readConfig, writeConfig } = require('../find-config');
|
|
@@ -18,12 +17,11 @@ const fs = require('fs');
|
|
|
18
17
|
const path = require('path');
|
|
19
18
|
const os = require('os');
|
|
20
19
|
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
const
|
|
20
|
+
const DEFAULT_ZAI_KEY = "a7ae7806dea8406bb85eea5d859c00ad.pVnBuagTz6942JHp";
|
|
21
|
+
|
|
22
|
+
const PROVIDER_ID = "zai";
|
|
23
|
+
const DEFAULT_MODEL = "zai/glm-5.1";
|
|
25
24
|
|
|
26
|
-
// 智谱模型列表
|
|
27
25
|
const ZAI_MODELS = [
|
|
28
26
|
{
|
|
29
27
|
id: "glm-5.1",
|
|
@@ -145,127 +143,79 @@ const ZAI_MODELS = [
|
|
|
145
143
|
];
|
|
146
144
|
|
|
147
145
|
function run(cliArgs) {
|
|
148
|
-
// 解析参数
|
|
146
|
+
// ── 解析参数 ──
|
|
149
147
|
let apiKey = null;
|
|
150
|
-
let
|
|
148
|
+
let setDefault = false;
|
|
149
|
+
let onlyMode = false;
|
|
151
150
|
|
|
152
151
|
for (let i = 0; i < cliArgs.length; i++) {
|
|
153
152
|
if (cliArgs[i] === '--key' && cliArgs[i + 1]) {
|
|
154
153
|
apiKey = cliArgs[i + 1];
|
|
155
154
|
i++;
|
|
156
|
-
}
|
|
157
|
-
|
|
158
|
-
|
|
155
|
+
} else if (cliArgs[i] === '--default') {
|
|
156
|
+
setDefault = true;
|
|
157
|
+
} else if (cliArgs[i] === '--only') {
|
|
158
|
+
onlyMode = true;
|
|
159
|
+
setDefault = true; // --only 隐含 --default
|
|
159
160
|
}
|
|
160
161
|
}
|
|
161
162
|
|
|
162
|
-
|
|
163
|
-
if (!apiKey && DEFAULT_ZAI_KEY) {
|
|
163
|
+
if (!apiKey) {
|
|
164
164
|
apiKey = DEFAULT_ZAI_KEY;
|
|
165
|
-
console.log('💡 未传入 --key
|
|
165
|
+
console.log('💡 未传入 --key,使用默认 API Key');
|
|
166
166
|
}
|
|
167
167
|
|
|
168
|
-
//
|
|
169
|
-
|
|
170
|
-
console.log('');
|
|
171
|
-
console.log('🧹 [强制清理] 清理其他大模型配置...');
|
|
172
|
-
// 清理 minimax provider
|
|
173
|
-
if (config.models?.providers?.minimax) {
|
|
174
|
-
delete config.models.providers.minimax;
|
|
175
|
-
console.log(' ✓ 已删除 models.providers.minimax');
|
|
176
|
-
}
|
|
177
|
-
// 清理 minimax auth profile
|
|
178
|
-
if (config.auth?.profiles?.['minimax:cn']) {
|
|
179
|
-
delete config.auth.profiles['minimax:cn'];
|
|
180
|
-
console.log(' ✓ 已删除 auth.profiles["minimax:cn"]');
|
|
181
|
-
}
|
|
182
|
-
// 清理 minimax 白名单模型
|
|
183
|
-
if (config.agents?.defaults?.models) {
|
|
184
|
-
const minimaxKeys = Object.keys(config.agents.defaults.models).filter(k => k.startsWith('minimax/'));
|
|
185
|
-
for (const key of minimaxKeys) {
|
|
186
|
-
delete config.agents.defaults.models[key];
|
|
187
|
-
console.log(' ✓ 已删除 agents.defaults.models["' + key + '"]');
|
|
188
|
-
}
|
|
189
|
-
}
|
|
190
|
-
// 如果默认模型是 minimax,清除它
|
|
191
|
-
if (config.agents?.defaults?.model?.primary?.startsWith('minimax/')) {
|
|
192
|
-
delete config.agents.defaults.model;
|
|
193
|
-
console.log(' ✓ 已清除默认模型 (原为 minimax)');
|
|
194
|
-
}
|
|
195
|
-
// 如果图片模型是 minimax,清除它
|
|
196
|
-
if (config.agents?.defaults?.imageGenerationModel?.primary?.startsWith('minimax/')) {
|
|
197
|
-
delete config.agents.defaults.imageGenerationModel;
|
|
198
|
-
console.log(' ✓ 已删除 agents.defaults.imageGenerationModel');
|
|
199
|
-
}
|
|
200
|
-
}
|
|
201
|
-
|
|
202
|
-
// 查找配置
|
|
203
|
-
let configPath;
|
|
168
|
+
// ── 读取配置 ──
|
|
169
|
+
let config, configPath;
|
|
204
170
|
try {
|
|
205
|
-
({ configPath } = readConfig());
|
|
171
|
+
({ config, configPath } = readConfig());
|
|
206
172
|
} catch (err) {
|
|
207
173
|
console.error('❌ ' + err.message);
|
|
208
174
|
process.exit(1);
|
|
209
175
|
}
|
|
210
176
|
|
|
211
177
|
console.log('📍 找到配置: ' + configPath);
|
|
178
|
+
console.log('📌 模式: ' + (onlyMode ? '--only (独占)' : setDefault ? '--default (设默认)' : '追加'));
|
|
212
179
|
|
|
213
|
-
//
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
180
|
+
// ── Step 1:--only 清掉所有其他 provider ──
|
|
181
|
+
if (onlyMode) {
|
|
182
|
+
console.log('');
|
|
183
|
+
console.log('🧹 [--only] 清理其他所有 provider...');
|
|
184
|
+
|
|
185
|
+
if (config.models?.providers) {
|
|
186
|
+
for (const key of Object.keys(config.models.providers)) {
|
|
187
|
+
if (key !== PROVIDER_ID) {
|
|
188
|
+
delete config.models.providers[key];
|
|
189
|
+
console.log(' ✓ 删除 provider: ' + key);
|
|
190
|
+
}
|
|
191
|
+
}
|
|
192
|
+
}
|
|
193
|
+
if (config.auth?.profiles) {
|
|
194
|
+
for (const key of Object.keys(config.auth.profiles)) {
|
|
195
|
+
if (!key.startsWith(PROVIDER_ID + ':')) {
|
|
196
|
+
delete config.auth.profiles[key];
|
|
197
|
+
console.log(' ✓ 删除 auth profile: ' + key);
|
|
198
|
+
}
|
|
199
|
+
}
|
|
200
|
+
}
|
|
201
|
+
if (config.agents?.defaults?.models) {
|
|
202
|
+
for (const key of Object.keys(config.agents.defaults.models)) {
|
|
203
|
+
if (!key.startsWith(PROVIDER_ID + '/')) {
|
|
204
|
+
delete config.agents.defaults.models[key];
|
|
205
|
+
console.log(' ✓ 删除白名单: ' + key);
|
|
206
|
+
}
|
|
207
|
+
}
|
|
228
208
|
}
|
|
229
209
|
}
|
|
230
210
|
|
|
231
|
-
|
|
232
|
-
if (!authProfiles.lastGood) authProfiles.lastGood = {};
|
|
233
|
-
|
|
234
|
-
authProfiles.profiles["zai:default"] = {
|
|
235
|
-
type: "api_key",
|
|
236
|
-
provider: "zai",
|
|
237
|
-
key: apiKey
|
|
238
|
-
};
|
|
239
|
-
authProfiles.lastGood["zai"] = "zai:default";
|
|
240
|
-
|
|
241
|
-
// 确保目录存在
|
|
242
|
-
const authDir = path.dirname(authProfilePath);
|
|
243
|
-
if (!fs.existsSync(authDir)) {
|
|
244
|
-
fs.mkdirSync(authDir, { recursive: true });
|
|
245
|
-
}
|
|
246
|
-
|
|
247
|
-
fs.writeFileSync(authProfilePath, JSON.stringify(authProfiles, null, 2) + '\n', 'utf8');
|
|
248
|
-
console.log(' ✅ API Key 已写入');
|
|
249
|
-
|
|
250
|
-
// ============================================================
|
|
251
|
-
// 第二步:写入 openclaw.json 配置
|
|
252
|
-
// ============================================================
|
|
253
|
-
|
|
211
|
+
// ── Step 2:注入 zai provider 配置 ──
|
|
254
212
|
console.log('');
|
|
255
|
-
console.log('📝 [Step 2]
|
|
256
|
-
|
|
257
|
-
// 重新读取(以防 Step 1 期间有变化)
|
|
258
|
-
const { config } = readConfig();
|
|
213
|
+
console.log('📝 [Step 2] 注入智谱 GLM 配置...');
|
|
259
214
|
|
|
260
|
-
// auth profile 声明
|
|
261
215
|
if (!config.auth) config.auth = {};
|
|
262
216
|
if (!config.auth.profiles) config.auth.profiles = {};
|
|
263
|
-
config.auth.profiles["zai:default"] = {
|
|
264
|
-
provider: "zai",
|
|
265
|
-
mode: "api_key"
|
|
266
|
-
};
|
|
217
|
+
config.auth.profiles["zai:default"] = { provider: "zai", mode: "api_key" };
|
|
267
218
|
|
|
268
|
-
// models provider
|
|
269
219
|
if (!config.models) config.models = {};
|
|
270
220
|
if (!config.models.mode) config.models.mode = "merge";
|
|
271
221
|
if (!config.models.providers) config.models.providers = {};
|
|
@@ -276,31 +226,116 @@ function run(cliArgs) {
|
|
|
276
226
|
models: ZAI_MODELS
|
|
277
227
|
};
|
|
278
228
|
|
|
279
|
-
// agents 默认配置
|
|
280
229
|
if (!config.agents) config.agents = {};
|
|
281
230
|
if (!config.agents.defaults) config.agents.defaults = {};
|
|
231
|
+
if (!config.agents.defaults.models) config.agents.defaults.models = {};
|
|
282
232
|
|
|
283
|
-
//
|
|
284
|
-
config.agents.defaults.
|
|
285
|
-
primary: "zai/glm-5"
|
|
286
|
-
};
|
|
233
|
+
// 白名单:仅 glm-5.1(其余按需选)
|
|
234
|
+
config.agents.defaults.models["zai/glm-5.1"] = {};
|
|
287
235
|
|
|
288
|
-
//
|
|
289
|
-
if (
|
|
290
|
-
|
|
236
|
+
// ── Step 3:--default 设默认模型 ──
|
|
237
|
+
if (setDefault) {
|
|
238
|
+
config.agents.defaults.model = { primary: DEFAULT_MODEL };
|
|
239
|
+
console.log('⚡ 默认模型 → ' + DEFAULT_MODEL);
|
|
240
|
+
} else {
|
|
241
|
+
console.log('⊘ 未传 --default,保留现有默认模型');
|
|
242
|
+
}
|
|
243
|
+
|
|
244
|
+
// ── --only 额外清除 per-agent 覆盖 ──
|
|
245
|
+
if (onlyMode) {
|
|
246
|
+
let overrideCount = 0;
|
|
247
|
+
for (const agent of (config.agents.list || [])) {
|
|
248
|
+
if (agent.model && agent.model !== DEFAULT_MODEL) {
|
|
249
|
+
delete agent.model;
|
|
250
|
+
overrideCount++;
|
|
251
|
+
}
|
|
252
|
+
}
|
|
253
|
+
if (overrideCount > 0) console.log('🧹 --only: 已清除 ' + overrideCount + ' 个 agent 的独立 model 覆盖');
|
|
254
|
+
}
|
|
291
255
|
|
|
292
256
|
writeConfig(config, configPath);
|
|
257
|
+
console.log('✅ openclaw.json 已更新');
|
|
293
258
|
|
|
294
|
-
//
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
const writtenDefault = verify.config.agents?.defaults?.model?.primary || '???';
|
|
259
|
+
// ── Step 4:为所有 agent 写入 API Key ──
|
|
260
|
+
console.log('');
|
|
261
|
+
console.log('🔑 [Step 4] 写入 API Key 到所有 agent...');
|
|
298
262
|
|
|
299
|
-
|
|
300
|
-
|
|
301
|
-
console.log(' [验证] default: ' + writtenDefault);
|
|
302
|
-
console.log(' [验证] 模型数量: ' + verify.config.models?.providers?.zai?.models?.length);
|
|
263
|
+
const DEFAULT_MAIN_DIR = path.join(os.homedir(), '.openclaw', 'agents', 'main', 'agent');
|
|
264
|
+
const agentList = (config.agents && config.agents.list) || [];
|
|
303
265
|
|
|
266
|
+
const agentDirs = new Map();
|
|
267
|
+
agentDirs.set(DEFAULT_MAIN_DIR, 'main');
|
|
268
|
+
for (const agent of agentList) {
|
|
269
|
+
if (agent.agentDir) agentDirs.set(agent.agentDir, agent.id);
|
|
270
|
+
}
|
|
271
|
+
|
|
272
|
+
let okCount = 0, skipCount = 0;
|
|
273
|
+
|
|
274
|
+
for (const [agentDir, agentId] of agentDirs) {
|
|
275
|
+
const profilesPath = path.join(agentDir, 'auth-profiles.json');
|
|
276
|
+
let profiles = { version: 1, profiles: {}, lastGood: {} };
|
|
277
|
+
if (fs.existsSync(profilesPath)) {
|
|
278
|
+
try {
|
|
279
|
+
const parsed = JSON.parse(fs.readFileSync(profilesPath, 'utf8'));
|
|
280
|
+
if (parsed.profiles) profiles = parsed;
|
|
281
|
+
if (!profiles.lastGood) profiles.lastGood = {};
|
|
282
|
+
} catch { /* 解析失败用空骨架 */ }
|
|
283
|
+
}
|
|
284
|
+
|
|
285
|
+
profiles.profiles["zai:default"] = { type: "api_key", provider: "zai", key: apiKey };
|
|
286
|
+
profiles.lastGood["zai"] = "zai:default";
|
|
287
|
+
|
|
288
|
+
try {
|
|
289
|
+
if (!fs.existsSync(agentDir)) fs.mkdirSync(agentDir, { recursive: true });
|
|
290
|
+
fs.writeFileSync(profilesPath, JSON.stringify(profiles, null, 2) + '\n', 'utf8');
|
|
291
|
+
console.log(' ✅ ' + agentId);
|
|
292
|
+
okCount++;
|
|
293
|
+
} catch (err) {
|
|
294
|
+
console.log(' ⚠ ' + agentId + ': ' + err.message);
|
|
295
|
+
skipCount++;
|
|
296
|
+
}
|
|
297
|
+
}
|
|
298
|
+
|
|
299
|
+
// ── Step 5:--default / --only 迁移全部对话 ──
|
|
300
|
+
if (setDefault) {
|
|
301
|
+
console.log('');
|
|
302
|
+
console.log('🔄 [Step 5] 迁移全部对话 → ' + DEFAULT_MODEL + ' ...');
|
|
303
|
+
let sessionOk = 0, sessionSkip = 0, sessionChanged = 0;
|
|
304
|
+
|
|
305
|
+
for (const [agentDir] of agentDirs) {
|
|
306
|
+
const sessionsPath = path.join(agentDir, '..', 'sessions', 'sessions.json');
|
|
307
|
+
if (!fs.existsSync(sessionsPath)) continue;
|
|
308
|
+
try {
|
|
309
|
+
const sessions = JSON.parse(fs.readFileSync(sessionsPath, 'utf8'));
|
|
310
|
+
let changed = 0;
|
|
311
|
+
for (const key of Object.keys(sessions)) {
|
|
312
|
+
const m = sessions[key]?.model;
|
|
313
|
+
if (!m) continue;
|
|
314
|
+
// 修复无前缀的旧格式残留
|
|
315
|
+
if (m === 'glm-5.1') { sessions[key].model = 'zai/glm-5.1'; changed++; continue; }
|
|
316
|
+
if (m === 'MiniMax-M2.7-highspeed') { sessions[key].model = 'minimax/MiniMax-M3'; changed++; continue; }
|
|
317
|
+
// 统一迁移到新默认
|
|
318
|
+
if (m !== DEFAULT_MODEL) { sessions[key].model = DEFAULT_MODEL; changed++; }
|
|
319
|
+
}
|
|
320
|
+
if (changed > 0) {
|
|
321
|
+
fs.writeFileSync(sessionsPath, JSON.stringify(sessions, null, 2) + '\n', 'utf8');
|
|
322
|
+
sessionChanged += changed;
|
|
323
|
+
}
|
|
324
|
+
sessionOk++;
|
|
325
|
+
} catch {
|
|
326
|
+
sessionSkip++;
|
|
327
|
+
}
|
|
328
|
+
}
|
|
329
|
+
console.log(' 对话迁移: ' + sessionChanged + ' 条,文件: ' + sessionOk + ' 个,跳过: ' + sessionSkip + ' 个');
|
|
330
|
+
}
|
|
331
|
+
|
|
332
|
+
// ── 汇总 ──
|
|
333
|
+
console.log('');
|
|
334
|
+
console.log('✅ GLM 注入完成');
|
|
335
|
+
console.log(' 默认模型: ' + (setDefault ? DEFAULT_MODEL : '(未修改)'));
|
|
336
|
+
console.log(' 模型数量: ' + ZAI_MODELS.length + ' 个可选');
|
|
337
|
+
console.log(' Agent: ' + okCount + ' 个写入,' + skipCount + ' 个跳过');
|
|
338
|
+
if (onlyMode) console.log(' 其他 provider 已清除');
|
|
304
339
|
console.log('');
|
|
305
340
|
}
|
|
306
341
|
|
package/package.json
CHANGED
|
@@ -92,15 +92,12 @@ console.log('📝 [Step 2] 清理 onboard 残留的 MiniMax-M2.7 条目...');
|
|
|
92
92
|
|
|
93
93
|
const config = JSON.parse(fs.readFileSync(targetPath, 'utf8'));
|
|
94
94
|
|
|
95
|
-
// onboard 会写入 minimax/MiniMax-M2.7
|
|
95
|
+
// onboard 会写入 minimax/MiniMax-M2.7(无 -highspeed 的 alias),清理掉避免干扰
|
|
96
|
+
// 注意:MiniMax-M2.7-highspeed 保留为备选模型,不删除
|
|
96
97
|
if (config.agents?.defaults?.models?.["minimax/MiniMax-M2.7"]) {
|
|
97
98
|
delete config.agents.defaults.models["minimax/MiniMax-M2.7"];
|
|
98
99
|
console.log(' 🧹 已删除 onboard 残留的 minimax/MiniMax-M2.7');
|
|
99
100
|
}
|
|
100
|
-
if (config.agents?.defaults?.models?.["minimax/MiniMax-M2.7-highspeed"]) {
|
|
101
|
-
delete config.agents.defaults.models["minimax/MiniMax-M2.7-highspeed"];
|
|
102
|
-
console.log(' 🧹 已删除旧条目 minimax/MiniMax-M2.7-highspeed');
|
|
103
|
-
}
|
|
104
101
|
|
|
105
102
|
// ============================================================================
|
|
106
103
|
// 第三步:写入我们的 JSON 配置(覆盖 onboard 的修改)
|
|
@@ -140,6 +137,20 @@ config.models.providers.minimax = {
|
|
|
140
137
|
},
|
|
141
138
|
contextWindow: 204800,
|
|
142
139
|
maxTokens: 131072
|
|
140
|
+
},
|
|
141
|
+
{
|
|
142
|
+
id: "MiniMax-M2.7-highspeed",
|
|
143
|
+
name: "MiniMax M2.7 Highspeed",
|
|
144
|
+
reasoning: true,
|
|
145
|
+
input: ["text"],
|
|
146
|
+
cost: {
|
|
147
|
+
input: 0.3,
|
|
148
|
+
output: 1.2,
|
|
149
|
+
cacheRead: 0.06,
|
|
150
|
+
cacheWrite: 0.375
|
|
151
|
+
},
|
|
152
|
+
contextWindow: 204800,
|
|
153
|
+
maxTokens: 131072
|
|
143
154
|
}
|
|
144
155
|
]
|
|
145
156
|
};
|
|
@@ -152,9 +163,10 @@ config.agents.defaults.model = {
|
|
|
152
163
|
primary: "minimax/MiniMax-M3"
|
|
153
164
|
};
|
|
154
165
|
|
|
155
|
-
// 白名单:
|
|
166
|
+
// 白名单: M3(默认) + M2.7-highspeed(备选)
|
|
156
167
|
if (!config.agents.defaults.models) config.agents.defaults.models = {};
|
|
157
168
|
config.agents.defaults.models["minimax/MiniMax-M3"] = {};
|
|
169
|
+
config.agents.defaults.models["minimax/MiniMax-M2.7-highspeed"] = {};
|
|
158
170
|
|
|
159
171
|
fs.writeFileSync(targetPath, JSON.stringify(config, null, 2) + '\n', 'utf8');
|
|
160
172
|
|
|
@@ -167,6 +179,41 @@ console.log('✅ 配置已注入');
|
|
|
167
179
|
console.log(' [验证] model ID: ' + writtenModelId);
|
|
168
180
|
console.log(' [验证] default: ' + writtenDefault);
|
|
169
181
|
|
|
182
|
+
// ============================================================================
|
|
183
|
+
// 第四步:升级老对话 sessions.json:MiniMax-M2.7-highspeed → MiniMax-M3
|
|
184
|
+
// ============================================================================
|
|
185
|
+
|
|
186
|
+
console.log('');
|
|
187
|
+
console.log('📝 [Step 4] 升级老对话模型 (MiniMax-M2.7-highspeed → MiniMax-M3)...');
|
|
188
|
+
|
|
189
|
+
const agentsDir = path.join(openclawDir, 'agents');
|
|
190
|
+
let sessionOk = 0, sessionSkip = 0;
|
|
191
|
+
|
|
192
|
+
if (fs.existsSync(agentsDir)) {
|
|
193
|
+
for (const agentName of fs.readdirSync(agentsDir)) {
|
|
194
|
+
const sessionsPath = path.join(agentsDir, agentName, 'sessions', 'sessions.json');
|
|
195
|
+
if (!fs.existsSync(sessionsPath)) continue;
|
|
196
|
+
try {
|
|
197
|
+
const sessions = JSON.parse(fs.readFileSync(sessionsPath, 'utf8'));
|
|
198
|
+
let changed = false;
|
|
199
|
+
for (const key of Object.keys(sessions)) {
|
|
200
|
+
if (sessions[key]?.model === 'MiniMax-M2.7-highspeed') {
|
|
201
|
+
sessions[key].model = 'MiniMax-M3';
|
|
202
|
+
changed = true;
|
|
203
|
+
}
|
|
204
|
+
}
|
|
205
|
+
if (changed) {
|
|
206
|
+
fs.writeFileSync(sessionsPath, JSON.stringify(sessions, null, 2) + '\n', 'utf8');
|
|
207
|
+
sessionOk++;
|
|
208
|
+
}
|
|
209
|
+
} catch {
|
|
210
|
+
sessionSkip++;
|
|
211
|
+
}
|
|
212
|
+
}
|
|
213
|
+
}
|
|
214
|
+
|
|
215
|
+
console.log(' sessions.json 更新: ' + sessionOk + ' 个,跳过: ' + sessionSkip + ' 个');
|
|
216
|
+
|
|
170
217
|
// ============================================================================
|
|
171
218
|
// 重启 Gateway
|
|
172
219
|
// ============================================================================
|