pumpkinai-config 1.0.16 → 1.0.17
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/claude-api.js +123 -67
- package/claude-setup.js +113 -200
- package/package.json +1 -1
package/claude-api.js
CHANGED
|
@@ -134,78 +134,130 @@ function installClaude() {
|
|
|
134
134
|
}
|
|
135
135
|
}
|
|
136
136
|
|
|
137
|
-
//
|
|
138
|
-
function
|
|
139
|
-
log('\n[配置]
|
|
137
|
+
// 设置系统用户环境变量
|
|
138
|
+
function setupEnvironmentVariables(apiKey) {
|
|
139
|
+
log('\n[配置] 设置系统用户环境变量...', 'cyan');
|
|
140
140
|
|
|
141
|
-
|
|
141
|
+
const osType = getOS();
|
|
142
142
|
let homeDir;
|
|
143
143
|
if (process.platform !== 'win32' && process.env.SUDO_USER) {
|
|
144
|
-
// Linux/Mac 使用 sudo 时,获取实际用户的 home 目录
|
|
145
144
|
const actualUser = process.env.SUDO_USER;
|
|
146
145
|
homeDir = process.platform === 'darwin' ? `/Users/${actualUser}` : `/home/${actualUser}`;
|
|
147
146
|
} else {
|
|
148
147
|
homeDir = os.homedir();
|
|
149
148
|
}
|
|
150
149
|
|
|
151
|
-
|
|
152
|
-
const
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
150
|
+
// 需要设置的环境变量
|
|
151
|
+
const envVars = {
|
|
152
|
+
ANTHROPIC_AUTH_TOKEN: apiKey,
|
|
153
|
+
ANTHROPIC_BASE_URL: "https://new.aicode.us.com",
|
|
154
|
+
CLAUDE_CODE_DISABLE_EXPERIMENTAL_BETAS:"1"
|
|
155
|
+
};
|
|
156
156
|
|
|
157
157
|
try {
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
158
|
+
if (osType === 'windows') {
|
|
159
|
+
// Windows: 使用 setx 设置用户环境变量(永久生效)
|
|
160
|
+
for (const [key, value] of Object.entries(envVars)) {
|
|
161
|
+
try {
|
|
162
|
+
execSync(`setx ${key} "${value}"`, { stdio: 'pipe' });
|
|
163
|
+
log(`[成功] 设置环境变量: ${key}`, 'green');
|
|
164
|
+
} catch (error) {
|
|
165
|
+
log(`[错误] 设置环境变量 ${key} 失败: ${error.message}`, 'red');
|
|
166
|
+
return false;
|
|
167
|
+
}
|
|
168
|
+
}
|
|
169
|
+
log('[提示] 请重新打开终端使环境变量生效', 'yellow');
|
|
170
|
+
return true;
|
|
171
|
+
|
|
172
|
+
} else if (osType === 'mac') {
|
|
173
|
+
// macOS: 写入 ~/.zshrc
|
|
174
|
+
const zshrcPath = path.join(homeDir, '.zshrc');
|
|
175
|
+
let zshrcContent = '';
|
|
176
|
+
if (fs.existsSync(zshrcPath)) {
|
|
177
|
+
zshrcContent = fs.readFileSync(zshrcPath, 'utf8');
|
|
178
|
+
}
|
|
179
|
+
|
|
180
|
+
// 构建环境变量行
|
|
181
|
+
let envLines = '\n# Claude Code 环境变量 (pumpkinai)\n';
|
|
182
|
+
for (const [key, value] of Object.entries(envVars)) {
|
|
183
|
+
const envLine = `export ${key}="${value}"`;
|
|
184
|
+
if (!zshrcContent.includes(`export ${key}=`)) {
|
|
185
|
+
envLines += envLine + '\n';
|
|
186
|
+
log(`[成功] 添加环境变量: ${key}`, 'green');
|
|
187
|
+
} else {
|
|
188
|
+
// 替换已存在的环境变量
|
|
189
|
+
const regex = new RegExp(`export ${key}=.*`, 'g');
|
|
190
|
+
zshrcContent = zshrcContent.replace(regex, envLine);
|
|
191
|
+
log(`[更新] 更新环境变量: ${key}`, 'yellow');
|
|
192
|
+
}
|
|
193
|
+
}
|
|
194
|
+
|
|
195
|
+
// 写入文件
|
|
196
|
+
if (envLines !== '\n# Claude Code 环境变量 (pumpkinai)\n') {
|
|
197
|
+
const newContent = zshrcContent + envLines;
|
|
198
|
+
fs.writeFileSync(zshrcPath, newContent, 'utf8');
|
|
199
|
+
} else {
|
|
200
|
+
fs.writeFileSync(zshrcPath, zshrcContent, 'utf8');
|
|
201
|
+
}
|
|
202
|
+
|
|
203
|
+
// 修改文件所有者
|
|
204
|
+
if (process.env.SUDO_USER) {
|
|
205
|
+
const actualUser = process.env.SUDO_USER;
|
|
206
|
+
try {
|
|
207
|
+
execSync(`chown ${actualUser}:staff ${zshrcPath}`);
|
|
208
|
+
} catch (error) {}
|
|
209
|
+
}
|
|
210
|
+
|
|
211
|
+
log(`[成功] 环境变量已写入: ${zshrcPath}`, 'green');
|
|
212
|
+
log('[提示] 请重新打开终端或运行: source ~/.zshrc', 'yellow');
|
|
213
|
+
return true;
|
|
165
214
|
|
|
166
|
-
// 创建 .claude 目录
|
|
167
|
-
if (!fs.existsSync(claudeDir)) {
|
|
168
|
-
fs.mkdirSync(claudeDir, { recursive: true });
|
|
169
|
-
log(`[成功] 创建目录: ${claudeDir}`, 'green');
|
|
170
215
|
} else {
|
|
171
|
-
|
|
172
|
-
|
|
216
|
+
// Linux: 写入 ~/.bashrc
|
|
217
|
+
const bashrcPath = path.join(homeDir, '.bashrc');
|
|
218
|
+
let bashrcContent = '';
|
|
219
|
+
if (fs.existsSync(bashrcPath)) {
|
|
220
|
+
bashrcContent = fs.readFileSync(bashrcPath, 'utf8');
|
|
221
|
+
}
|
|
222
|
+
|
|
223
|
+
// 构建环境变量行
|
|
224
|
+
let envLines = '\n# Claude Code 环境变量 (pumpkinai)\n';
|
|
225
|
+
for (const [key, value] of Object.entries(envVars)) {
|
|
226
|
+
const envLine = `export ${key}="${value}"`;
|
|
227
|
+
if (!bashrcContent.includes(`export ${key}=`)) {
|
|
228
|
+
envLines += envLine + '\n';
|
|
229
|
+
log(`[成功] 添加环境变量: ${key}`, 'green');
|
|
230
|
+
} else {
|
|
231
|
+
// 替换已存在的环境变量
|
|
232
|
+
const regex = new RegExp(`export ${key}=.*`, 'g');
|
|
233
|
+
bashrcContent = bashrcContent.replace(regex, envLine);
|
|
234
|
+
log(`[更新] 更新环境变量: ${key}`, 'yellow');
|
|
235
|
+
}
|
|
236
|
+
}
|
|
173
237
|
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
238
|
+
// 写入文件
|
|
239
|
+
if (envLines !== '\n# Claude Code 环境变量 (pumpkinai)\n') {
|
|
240
|
+
const newContent = bashrcContent + envLines;
|
|
241
|
+
fs.writeFileSync(bashrcPath, newContent, 'utf8');
|
|
242
|
+
} else {
|
|
243
|
+
fs.writeFileSync(bashrcPath, bashrcContent, 'utf8');
|
|
180
244
|
}
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
primaryApiKey: "1"
|
|
189
|
-
};
|
|
190
|
-
|
|
191
|
-
fs.writeFileSync(configPath, JSON.stringify(config, null, 2), 'utf8');
|
|
192
|
-
log(`[成功] 创建配置文件: ${configPath}`, 'green');
|
|
193
|
-
|
|
194
|
-
// 如果是通过 sudo 运行的,修改文件所有者
|
|
195
|
-
if (process.platform !== 'win32' && process.env.SUDO_USER) {
|
|
196
|
-
const actualUser = process.env.SUDO_USER;
|
|
197
|
-
const group = process.platform === 'darwin' ? 'staff' : actualUser;
|
|
198
|
-
try {
|
|
199
|
-
execSync(`chown -R ${actualUser}:${group} ${claudeDir}`);
|
|
200
|
-
log(`[成功] 设置文件所有者为: ${actualUser}`, 'green');
|
|
201
|
-
} catch (error) {
|
|
202
|
-
log(`[警告] 无法设置文件所有者: ${error.message}`, 'yellow');
|
|
245
|
+
|
|
246
|
+
// 修改文件所有者
|
|
247
|
+
if (process.env.SUDO_USER) {
|
|
248
|
+
const actualUser = process.env.SUDO_USER;
|
|
249
|
+
try {
|
|
250
|
+
execSync(`chown ${actualUser}:${actualUser} ${bashrcPath}`);
|
|
251
|
+
} catch (error) {}
|
|
203
252
|
}
|
|
253
|
+
|
|
254
|
+
log(`[成功] 环境变量已写入: ${bashrcPath}`, 'green');
|
|
255
|
+
log('[提示] 请重新打开终端或运行: source ~/.bashrc', 'yellow');
|
|
256
|
+
return true;
|
|
204
257
|
}
|
|
205
258
|
|
|
206
|
-
return true;
|
|
207
259
|
} catch (error) {
|
|
208
|
-
log(`[错误]
|
|
260
|
+
log(`[错误] 设置环境变量失败: ${error.message}`, 'red');
|
|
209
261
|
return false;
|
|
210
262
|
}
|
|
211
263
|
}
|
|
@@ -228,14 +280,14 @@ async function configureEnvironment() {
|
|
|
228
280
|
return false;
|
|
229
281
|
}
|
|
230
282
|
|
|
231
|
-
return
|
|
283
|
+
return setupEnvironmentVariables(apiKey);
|
|
232
284
|
}
|
|
233
285
|
|
|
234
286
|
// 显示完成信息
|
|
235
287
|
function showCompletionInfo() {
|
|
236
288
|
const osType = getOS();
|
|
237
289
|
|
|
238
|
-
//
|
|
290
|
+
// 获取 home 目录
|
|
239
291
|
let homeDir;
|
|
240
292
|
if (process.platform !== 'win32' && process.env.SUDO_USER) {
|
|
241
293
|
const actualUser = process.env.SUDO_USER;
|
|
@@ -243,9 +295,6 @@ function showCompletionInfo() {
|
|
|
243
295
|
} else {
|
|
244
296
|
homeDir = os.homedir();
|
|
245
297
|
}
|
|
246
|
-
const claudeDir = path.join(homeDir, '.claude');
|
|
247
|
-
const settingsPath = path.join(claudeDir, 'settings.json');
|
|
248
|
-
const configPath = path.join(claudeDir, 'config.json');
|
|
249
298
|
|
|
250
299
|
log('\n', 'reset');
|
|
251
300
|
log('=' + '='.repeat(68) + '=', 'yellow');
|
|
@@ -254,15 +303,21 @@ function showCompletionInfo() {
|
|
|
254
303
|
|
|
255
304
|
log('\n[已完成操作]', 'cyan');
|
|
256
305
|
log(' * 安装 @anthropic-ai/claude-code', 'green');
|
|
257
|
-
log(' *
|
|
258
|
-
log(' *
|
|
306
|
+
log(' * 设置用户环境变量 ANTHROPIC_AUTH_TOKEN', 'green');
|
|
307
|
+
log(' * 设置用户环境变量 ANTHROPIC_BASE_URL', 'green');
|
|
308
|
+
log(' * 设置用户环境变量 ANTHROPIC_SMALL_FAST_MODEL', 'green');
|
|
259
309
|
|
|
260
|
-
log('\n[
|
|
261
|
-
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
|
|
310
|
+
log('\n[环境变量配置]', 'cyan');
|
|
311
|
+
if (osType === 'windows') {
|
|
312
|
+
log(' 环境变量已通过 setx 设置到用户环境变量', 'reset');
|
|
313
|
+
log(' 可在 系统属性 -> 高级 -> 环境变量 中查看', 'yellow');
|
|
314
|
+
} else if (osType === 'mac') {
|
|
315
|
+
log(' 环境变量已写入: ~/.zshrc', 'reset');
|
|
316
|
+
log(` ${path.join(homeDir, '.zshrc')}`, 'yellow');
|
|
317
|
+
} else {
|
|
318
|
+
log(' 环境变量已写入: ~/.bashrc', 'reset');
|
|
319
|
+
log(` ${path.join(homeDir, '.bashrc')}`, 'yellow');
|
|
320
|
+
}
|
|
266
321
|
|
|
267
322
|
log('\n[启动方式]', 'cyan');
|
|
268
323
|
|
|
@@ -331,5 +386,6 @@ if (require.main === module) {
|
|
|
331
386
|
module.exports = {
|
|
332
387
|
main,
|
|
333
388
|
installClaude,
|
|
334
|
-
configureEnvironment
|
|
389
|
+
configureEnvironment,
|
|
390
|
+
setupEnvironmentVariables
|
|
335
391
|
};
|
package/claude-setup.js
CHANGED
|
@@ -134,106 +134,9 @@ function installClaude() {
|
|
|
134
134
|
}
|
|
135
135
|
}
|
|
136
136
|
|
|
137
|
-
//
|
|
138
|
-
function
|
|
139
|
-
log('\n[配置]
|
|
140
|
-
|
|
141
|
-
// 获取实际用户的 home 目录
|
|
142
|
-
let homeDir;
|
|
143
|
-
if (process.platform !== 'win32' && process.env.SUDO_USER) {
|
|
144
|
-
// Linux/Mac 使用 sudo 时,获取实际用户的 home 目录
|
|
145
|
-
const actualUser = process.env.SUDO_USER;
|
|
146
|
-
homeDir = process.platform === 'darwin' ? `/Users/${actualUser}` : `/home/${actualUser}`;
|
|
147
|
-
} else {
|
|
148
|
-
homeDir = os.homedir();
|
|
149
|
-
}
|
|
150
|
-
|
|
151
|
-
const claudeDir = path.join(homeDir, '.claude');
|
|
152
|
-
const settingsPath = path.join(claudeDir, 'settings.json');
|
|
153
|
-
const configPath = path.join(claudeDir, 'config.json');
|
|
154
|
-
const oldConfigPath = path.join(homeDir, '.claude.json');
|
|
155
|
-
const oldConfigBackupPath = path.join(homeDir, '.claude.json.backup');
|
|
156
|
-
|
|
157
|
-
try {
|
|
158
|
-
// 删除旧的配置文件(不提示用户)
|
|
159
|
-
if (fs.existsSync(oldConfigPath)) {
|
|
160
|
-
fs.unlinkSync(oldConfigPath);
|
|
161
|
-
}
|
|
162
|
-
if (fs.existsSync(oldConfigBackupPath)) {
|
|
163
|
-
fs.unlinkSync(oldConfigBackupPath);
|
|
164
|
-
}
|
|
165
|
-
|
|
166
|
-
// 创建 .claude 目录
|
|
167
|
-
if (!fs.existsSync(claudeDir)) {
|
|
168
|
-
fs.mkdirSync(claudeDir, { recursive: true });
|
|
169
|
-
log(`[成功] 创建目录: ${claudeDir}`, 'green');
|
|
170
|
-
} else {
|
|
171
|
-
log(`[提示] 目录已存在: ${claudeDir}`, 'yellow');
|
|
172
|
-
}
|
|
173
|
-
|
|
174
|
-
// 创建 settings.json 配置
|
|
175
|
-
const settings = {
|
|
176
|
-
env: {
|
|
177
|
-
ANTHROPIC_AUTH_TOKEN: apiKey,
|
|
178
|
-
ANTHROPIC_BASE_URL: "https://code.ppchat.vip",
|
|
179
|
-
ANTHROPIC_SMALL_FAST_MODEL: "claude-3-5-haiku-20241022"
|
|
180
|
-
}
|
|
181
|
-
};
|
|
182
|
-
|
|
183
|
-
fs.writeFileSync(settingsPath, JSON.stringify(settings, null, 2), 'utf8');
|
|
184
|
-
log(`[成功] 创建配置文件: ${settingsPath}`, 'green');
|
|
185
|
-
|
|
186
|
-
// 创建 config.json 配置
|
|
187
|
-
const config = {
|
|
188
|
-
primaryApiKey: "1"
|
|
189
|
-
};
|
|
190
|
-
|
|
191
|
-
fs.writeFileSync(configPath, JSON.stringify(config, null, 2), 'utf8');
|
|
192
|
-
log(`[成功] 创建配置文件: ${configPath}`, 'green');
|
|
193
|
-
|
|
194
|
-
// 如果是通过 sudo 运行的,修改文件所有者
|
|
195
|
-
if (process.platform !== 'win32' && process.env.SUDO_USER) {
|
|
196
|
-
const actualUser = process.env.SUDO_USER;
|
|
197
|
-
const group = process.platform === 'darwin' ? 'staff' : actualUser;
|
|
198
|
-
try {
|
|
199
|
-
execSync(`chown -R ${actualUser}:${group} ${claudeDir}`);
|
|
200
|
-
log(`[成功] 设置文件所有者为: ${actualUser}`, 'green');
|
|
201
|
-
} catch (error) {
|
|
202
|
-
log(`[警告] 无法设置文件所有者: ${error.message}`, 'yellow');
|
|
203
|
-
}
|
|
204
|
-
}
|
|
205
|
-
|
|
206
|
-
return true;
|
|
207
|
-
} catch (error) {
|
|
208
|
-
log(`[错误] 创建配置文件失败: ${error.message}`, 'red');
|
|
209
|
-
return false;
|
|
210
|
-
}
|
|
211
|
-
}
|
|
212
|
-
|
|
213
|
-
// 配置 Claude
|
|
214
|
-
async function configureEnvironment() {
|
|
215
|
-
log('\n[配置] 配置 API Key...', 'cyan');
|
|
216
|
-
|
|
217
|
-
// 显示粘贴提示
|
|
218
|
-
if (process.platform === 'win32') {
|
|
219
|
-
log('[提示] Windows 粘贴方式:', 'yellow');
|
|
220
|
-
log(' • CMD/PowerShell: 鼠标右键 或 Shift+Insert', 'yellow');
|
|
221
|
-
|
|
222
|
-
}
|
|
223
|
-
|
|
224
|
-
const apiKey = await getUserInput('请输入你的 Claude API Key (sk-xxx): ');
|
|
225
|
-
|
|
226
|
-
if (!apiKey || !apiKey.startsWith('sk-')) {
|
|
227
|
-
log('[错误] API Key 格式不正确,应该以 sk- 开头', 'red');
|
|
228
|
-
return false;
|
|
229
|
-
}
|
|
230
|
-
|
|
231
|
-
return createClaudeConfig(apiKey);
|
|
232
|
-
}
|
|
233
|
-
|
|
234
|
-
// 配置环境变量到系统
|
|
235
|
-
function setupEnvironmentVariable() {
|
|
236
|
-
log('\n[配置] 设置系统环境变量...', 'cyan');
|
|
137
|
+
// 设置系统用户环境变量
|
|
138
|
+
function setupEnvironmentVariables(apiKey) {
|
|
139
|
+
log('\n[配置] 设置系统用户环境变量...', 'cyan');
|
|
237
140
|
|
|
238
141
|
const osType = getOS();
|
|
239
142
|
let homeDir;
|
|
@@ -244,122 +147,112 @@ function setupEnvironmentVariable() {
|
|
|
244
147
|
homeDir = os.homedir();
|
|
245
148
|
}
|
|
246
149
|
|
|
247
|
-
|
|
150
|
+
// 需要设置的环境变量
|
|
151
|
+
const envVars = {
|
|
152
|
+
ANTHROPIC_AUTH_TOKEN: apiKey,
|
|
153
|
+
ANTHROPIC_BASE_URL: "https://code.ppchat.vip",
|
|
154
|
+
CLAUDE_CODE_DISABLE_EXPERIMENTAL_BETAS:"1"
|
|
155
|
+
};
|
|
248
156
|
|
|
249
157
|
try {
|
|
250
158
|
if (osType === 'windows') {
|
|
251
159
|
// Windows: 使用 setx 设置用户环境变量(永久生效)
|
|
252
|
-
|
|
253
|
-
execSync('setx CLAUDE_CODE_DISABLE_EXPERIMENTAL_BETAS "1"', { stdio: 'pipe' });
|
|
254
|
-
log('[成功] 已设置 Windows 用户环境变量', 'green');
|
|
255
|
-
log('[提示] 请重新打开终端使环境变量生效', 'yellow');
|
|
256
|
-
return true;
|
|
257
|
-
} catch (error) {
|
|
258
|
-
log('[警告] 无法使用 setx 设置环境变量', 'yellow');
|
|
259
|
-
|
|
260
|
-
// 创建 PowerShell Profile 配置
|
|
160
|
+
for (const [key, value] of Object.entries(envVars)) {
|
|
261
161
|
try {
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
const profileDir = path.dirname(profilePath);
|
|
267
|
-
if (!fs.existsSync(profileDir)) {
|
|
268
|
-
fs.mkdirSync(profileDir, { recursive: true });
|
|
269
|
-
}
|
|
270
|
-
|
|
271
|
-
// 读取现有 Profile 内容
|
|
272
|
-
let profileContent = '';
|
|
273
|
-
if (fs.existsSync(profilePath)) {
|
|
274
|
-
profileContent = fs.readFileSync(profilePath, 'utf8');
|
|
275
|
-
}
|
|
276
|
-
|
|
277
|
-
// 检查是否已存在该环境变量配置
|
|
278
|
-
const psEnvLine = '$env:CLAUDE_CODE_DISABLE_EXPERIMENTAL_BETAS = "1"';
|
|
279
|
-
if (!profileContent.includes('CLAUDE_CODE_DISABLE_EXPERIMENTAL_BETAS')) {
|
|
280
|
-
// 追加环境变量到 Profile
|
|
281
|
-
const newContent = profileContent + (profileContent ? '\n' : '') +
|
|
282
|
-
'# Claude Code 环境变量\n' + psEnvLine + '\n';
|
|
283
|
-
fs.writeFileSync(profilePath, newContent, 'utf8');
|
|
284
|
-
log(`[成功] 已添加环境变量到 PowerShell Profile: ${profilePath}`, 'green');
|
|
285
|
-
log('[提示] 请重新打开 PowerShell 使环境变量生效', 'yellow');
|
|
286
|
-
} else {
|
|
287
|
-
log('[提示] PowerShell Profile 中已存在该环境变量', 'yellow');
|
|
288
|
-
}
|
|
289
|
-
return true;
|
|
290
|
-
} catch (psError) {
|
|
291
|
-
log(`[警告] PowerShell Profile 配置失败: ${psError.message}`, 'yellow');
|
|
292
|
-
log('[提示] 请联系淘宝或者技术客服解决', 'yellow');
|
|
162
|
+
execSync(`setx ${key} "${value}"`, { stdio: 'pipe' });
|
|
163
|
+
log(`[成功] 设置环境变量: ${key}`, 'green');
|
|
164
|
+
} catch (error) {
|
|
165
|
+
log(`[错误] 设置环境变量 ${key} 失败: ${error.message}`, 'red');
|
|
293
166
|
return false;
|
|
294
167
|
}
|
|
295
168
|
}
|
|
169
|
+
log('[提示] 请重新打开终端使环境变量生效', 'yellow');
|
|
170
|
+
return true;
|
|
296
171
|
|
|
297
172
|
} else if (osType === 'mac') {
|
|
298
173
|
// macOS: 写入 ~/.zshrc
|
|
299
174
|
const zshrcPath = path.join(homeDir, '.zshrc');
|
|
300
|
-
|
|
301
|
-
// 读取现有内容
|
|
302
175
|
let zshrcContent = '';
|
|
303
176
|
if (fs.existsSync(zshrcPath)) {
|
|
304
177
|
zshrcContent = fs.readFileSync(zshrcPath, 'utf8');
|
|
305
178
|
}
|
|
306
179
|
|
|
307
|
-
//
|
|
308
|
-
|
|
309
|
-
|
|
310
|
-
const
|
|
311
|
-
|
|
312
|
-
|
|
313
|
-
|
|
314
|
-
|
|
315
|
-
|
|
316
|
-
|
|
317
|
-
|
|
318
|
-
|
|
319
|
-
execSync(`chown ${actualUser}:staff ${zshrcPath}`);
|
|
320
|
-
} catch (error) {
|
|
321
|
-
}
|
|
180
|
+
// 构建环境变量行
|
|
181
|
+
let envLines = '\n# Claude Code 环境变量 (pumpkinai)\n';
|
|
182
|
+
for (const [key, value] of Object.entries(envVars)) {
|
|
183
|
+
const envLine = `export ${key}="${value}"`;
|
|
184
|
+
if (!zshrcContent.includes(`export ${key}=`)) {
|
|
185
|
+
envLines += envLine + '\n';
|
|
186
|
+
log(`[成功] 添加环境变量: ${key}`, 'green');
|
|
187
|
+
} else {
|
|
188
|
+
// 替换已存在的环境变量
|
|
189
|
+
const regex = new RegExp(`export ${key}=.*`, 'g');
|
|
190
|
+
zshrcContent = zshrcContent.replace(regex, envLine);
|
|
191
|
+
log(`[更新] 更新环境变量: ${key}`, 'yellow');
|
|
322
192
|
}
|
|
193
|
+
}
|
|
323
194
|
|
|
324
|
-
|
|
325
|
-
|
|
195
|
+
// 写入文件
|
|
196
|
+
if (envLines !== '\n# Claude Code 环境变量 (pumpkinai)\n') {
|
|
197
|
+
const newContent = zshrcContent + envLines;
|
|
198
|
+
fs.writeFileSync(zshrcPath, newContent, 'utf8');
|
|
326
199
|
} else {
|
|
327
|
-
|
|
200
|
+
fs.writeFileSync(zshrcPath, zshrcContent, 'utf8');
|
|
201
|
+
}
|
|
202
|
+
|
|
203
|
+
// 修改文件所有者
|
|
204
|
+
if (process.env.SUDO_USER) {
|
|
205
|
+
const actualUser = process.env.SUDO_USER;
|
|
206
|
+
try {
|
|
207
|
+
execSync(`chown ${actualUser}:staff ${zshrcPath}`);
|
|
208
|
+
} catch (error) {}
|
|
328
209
|
}
|
|
210
|
+
|
|
211
|
+
log(`[成功] 环境变量已写入: ${zshrcPath}`, 'green');
|
|
212
|
+
log('[提示] 请重新打开终端或运行: source ~/.zshrc', 'yellow');
|
|
329
213
|
return true;
|
|
330
214
|
|
|
331
215
|
} else {
|
|
332
216
|
// Linux: 写入 ~/.bashrc
|
|
333
217
|
const bashrcPath = path.join(homeDir, '.bashrc');
|
|
334
|
-
|
|
335
|
-
// 读取现有内容
|
|
336
218
|
let bashrcContent = '';
|
|
337
219
|
if (fs.existsSync(bashrcPath)) {
|
|
338
220
|
bashrcContent = fs.readFileSync(bashrcPath, 'utf8');
|
|
339
221
|
}
|
|
340
222
|
|
|
341
|
-
//
|
|
342
|
-
|
|
343
|
-
|
|
344
|
-
const
|
|
345
|
-
|
|
346
|
-
|
|
347
|
-
|
|
348
|
-
|
|
349
|
-
|
|
350
|
-
|
|
351
|
-
|
|
352
|
-
|
|
353
|
-
execSync(`chown ${actualUser}:${actualUser} ${bashrcPath}`);
|
|
354
|
-
} catch (error) {
|
|
355
|
-
}
|
|
223
|
+
// 构建环境变量行
|
|
224
|
+
let envLines = '\n# Claude Code 环境变量 (pumpkinai)\n';
|
|
225
|
+
for (const [key, value] of Object.entries(envVars)) {
|
|
226
|
+
const envLine = `export ${key}="${value}"`;
|
|
227
|
+
if (!bashrcContent.includes(`export ${key}=`)) {
|
|
228
|
+
envLines += envLine + '\n';
|
|
229
|
+
log(`[成功] 添加环境变量: ${key}`, 'green');
|
|
230
|
+
} else {
|
|
231
|
+
// 替换已存在的环境变量
|
|
232
|
+
const regex = new RegExp(`export ${key}=.*`, 'g');
|
|
233
|
+
bashrcContent = bashrcContent.replace(regex, envLine);
|
|
234
|
+
log(`[更新] 更新环境变量: ${key}`, 'yellow');
|
|
356
235
|
}
|
|
236
|
+
}
|
|
357
237
|
|
|
358
|
-
|
|
359
|
-
|
|
238
|
+
// 写入文件
|
|
239
|
+
if (envLines !== '\n# Claude Code 环境变量 (pumpkinai)\n') {
|
|
240
|
+
const newContent = bashrcContent + envLines;
|
|
241
|
+
fs.writeFileSync(bashrcPath, newContent, 'utf8');
|
|
360
242
|
} else {
|
|
361
|
-
|
|
243
|
+
fs.writeFileSync(bashrcPath, bashrcContent, 'utf8');
|
|
244
|
+
}
|
|
245
|
+
|
|
246
|
+
// 修改文件所有者
|
|
247
|
+
if (process.env.SUDO_USER) {
|
|
248
|
+
const actualUser = process.env.SUDO_USER;
|
|
249
|
+
try {
|
|
250
|
+
execSync(`chown ${actualUser}:${actualUser} ${bashrcPath}`);
|
|
251
|
+
} catch (error) {}
|
|
362
252
|
}
|
|
253
|
+
|
|
254
|
+
log(`[成功] 环境变量已写入: ${bashrcPath}`, 'green');
|
|
255
|
+
log('[提示] 请重新打开终端或运行: source ~/.bashrc', 'yellow');
|
|
363
256
|
return true;
|
|
364
257
|
}
|
|
365
258
|
|
|
@@ -369,11 +262,32 @@ function setupEnvironmentVariable() {
|
|
|
369
262
|
}
|
|
370
263
|
}
|
|
371
264
|
|
|
265
|
+
// 配置 Claude
|
|
266
|
+
async function configureEnvironment() {
|
|
267
|
+
log('\n[配置] 配置 API Key...', 'cyan');
|
|
268
|
+
|
|
269
|
+
// 显示粘贴提示
|
|
270
|
+
if (process.platform === 'win32') {
|
|
271
|
+
log('[提示] Windows 粘贴方式:', 'yellow');
|
|
272
|
+
log(' • CMD/PowerShell: 鼠标右键 或 Shift+Insert', 'yellow');
|
|
273
|
+
|
|
274
|
+
}
|
|
275
|
+
|
|
276
|
+
const apiKey = await getUserInput('请输入你的 Claude API Key (sk-xxx): ');
|
|
277
|
+
|
|
278
|
+
if (!apiKey || !apiKey.startsWith('sk-')) {
|
|
279
|
+
log('[错误] API Key 格式不正确,应该以 sk- 开头', 'red');
|
|
280
|
+
return false;
|
|
281
|
+
}
|
|
282
|
+
|
|
283
|
+
return setupEnvironmentVariables(apiKey);
|
|
284
|
+
}
|
|
285
|
+
|
|
372
286
|
// 显示完成信息
|
|
373
287
|
function showCompletionInfo() {
|
|
374
288
|
const osType = getOS();
|
|
375
289
|
|
|
376
|
-
//
|
|
290
|
+
// 获取 home 目录
|
|
377
291
|
let homeDir;
|
|
378
292
|
if (process.platform !== 'win32' && process.env.SUDO_USER) {
|
|
379
293
|
const actualUser = process.env.SUDO_USER;
|
|
@@ -381,9 +295,6 @@ function showCompletionInfo() {
|
|
|
381
295
|
} else {
|
|
382
296
|
homeDir = os.homedir();
|
|
383
297
|
}
|
|
384
|
-
const claudeDir = path.join(homeDir, '.claude');
|
|
385
|
-
const settingsPath = path.join(claudeDir, 'settings.json');
|
|
386
|
-
const configPath = path.join(claudeDir, 'config.json');
|
|
387
298
|
|
|
388
299
|
log('\n', 'reset');
|
|
389
300
|
log('=' + '='.repeat(68) + '=', 'yellow');
|
|
@@ -392,16 +303,21 @@ function showCompletionInfo() {
|
|
|
392
303
|
|
|
393
304
|
log('\n[已完成操作]', 'cyan');
|
|
394
305
|
log(' * 安装 @anthropic-ai/claude-code', 'green');
|
|
395
|
-
log(' *
|
|
396
|
-
log(' *
|
|
397
|
-
log(' *
|
|
306
|
+
log(' * 设置用户环境变量 ANTHROPIC_AUTH_TOKEN', 'green');
|
|
307
|
+
log(' * 设置用户环境变量 ANTHROPIC_BASE_URL', 'green');
|
|
308
|
+
log(' * 设置用户环境变量 ANTHROPIC_SMALL_FAST_MODEL', 'green');
|
|
398
309
|
|
|
399
|
-
log('\n[
|
|
400
|
-
|
|
401
|
-
|
|
402
|
-
|
|
403
|
-
|
|
404
|
-
|
|
310
|
+
log('\n[环境变量配置]', 'cyan');
|
|
311
|
+
if (osType === 'windows') {
|
|
312
|
+
log(' 环境变量已通过 setx 设置到用户环境变量', 'reset');
|
|
313
|
+
log(' 可在 系统属性 -> 高级 -> 环境变量 中查看', 'yellow');
|
|
314
|
+
} else if (osType === 'mac') {
|
|
315
|
+
log(' 环境变量已写入: ~/.zshrc', 'reset');
|
|
316
|
+
log(` ${path.join(homeDir, '.zshrc')}`, 'yellow');
|
|
317
|
+
} else {
|
|
318
|
+
log(' 环境变量已写入: ~/.bashrc', 'reset');
|
|
319
|
+
log(` ${path.join(homeDir, '.bashrc')}`, 'yellow');
|
|
320
|
+
}
|
|
405
321
|
|
|
406
322
|
log('\n[启动方式]', 'cyan');
|
|
407
323
|
|
|
@@ -446,16 +362,13 @@ async function main() {
|
|
|
446
362
|
log('\n[提示] 安装失败,但你可以继续配置环境变量', 'yellow');
|
|
447
363
|
}
|
|
448
364
|
|
|
449
|
-
// 2. 配置 API Key
|
|
365
|
+
// 2. 配置 API Key (会自动设置环境变量)
|
|
450
366
|
const configSuccess = await configureEnvironment();
|
|
451
367
|
if (!configSuccess) {
|
|
452
368
|
process.exit(1);
|
|
453
369
|
}
|
|
454
370
|
|
|
455
|
-
// 3.
|
|
456
|
-
setupEnvironmentVariable();
|
|
457
|
-
|
|
458
|
-
// 4. 显示完成信息
|
|
371
|
+
// 3. 显示完成信息
|
|
459
372
|
showCompletionInfo();
|
|
460
373
|
|
|
461
374
|
} catch (error) {
|
|
@@ -474,5 +387,5 @@ module.exports = {
|
|
|
474
387
|
main,
|
|
475
388
|
installClaude,
|
|
476
389
|
configureEnvironment,
|
|
477
|
-
|
|
390
|
+
setupEnvironmentVariables
|
|
478
391
|
};
|