zcf 3.4.1 → 3.4.3

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.
Files changed (31) hide show
  1. package/dist/chunks/claude-code-config-manager.mjs +28 -18
  2. package/dist/chunks/claude-code-incremental-manager.mjs +37 -20
  3. package/dist/chunks/codex-config-switch.mjs +8 -8
  4. package/dist/chunks/codex-provider-manager.mjs +30 -21
  5. package/dist/chunks/codex-uninstaller.mjs +3 -3
  6. package/dist/chunks/commands.mjs +2 -2
  7. package/dist/chunks/features.mjs +32 -20
  8. package/dist/chunks/simple-config.mjs +1046 -107
  9. package/dist/cli.mjs +10 -8
  10. package/dist/i18n/locales/en/cli.json +3 -1
  11. package/dist/i18n/locales/en/codex.json +2 -1
  12. package/dist/i18n/locales/en/common.json +2 -1
  13. package/dist/i18n/locales/en/configuration.json +3 -1
  14. package/dist/i18n/locales/en/errors.json +1 -1
  15. package/dist/i18n/locales/en/installation.json +34 -1
  16. package/dist/i18n/locales/en/updater.json +1 -0
  17. package/dist/i18n/locales/zh-CN/cli.json +3 -1
  18. package/dist/i18n/locales/zh-CN/codex.json +2 -1
  19. package/dist/i18n/locales/zh-CN/common.json +2 -1
  20. package/dist/i18n/locales/zh-CN/configuration.json +3 -1
  21. package/dist/i18n/locales/zh-CN/errors.json +1 -1
  22. package/dist/i18n/locales/zh-CN/installation.json +34 -1
  23. package/dist/i18n/locales/zh-CN/updater.json +1 -0
  24. package/dist/index.d.mts +43 -5
  25. package/dist/index.d.ts +43 -5
  26. package/dist/index.mjs +2 -2
  27. package/package.json +1 -1
  28. package/templates/claude-code/en/workflow/git/commands/git-commit.md +50 -3
  29. package/templates/claude-code/zh-CN/workflow/git/commands/git-commit.md +50 -3
  30. package/templates/codex/en/workflow/git/prompts/git-commit.md +50 -3
  31. package/templates/codex/zh-CN/workflow/git/prompts/git-commit.md +50 -3
@@ -1,6 +1,6 @@
1
1
  import dayjs from 'dayjs';
2
2
  import { join } from 'pathe';
3
- import { q as ZCF_CONFIG_FILE, Z as ZCF_CONFIG_DIR, am as ensureDir, an as readDefaultTomlConfig, ao as createDefaultTomlConfig, ap as exists, aq as readJsonConfig, ar as writeTomlConfig, S as SETTINGS_FILE, as as copyFile } from './simple-config.mjs';
3
+ import { q as ZCF_CONFIG_FILE, Z as ZCF_CONFIG_DIR, ap as ensureDir, aq as readDefaultTomlConfig, ar as createDefaultTomlConfig, as as exists, at as readJsonConfig, au as writeTomlConfig, S as SETTINGS_FILE, av as clearModelEnv, aw as copyFile } from './simple-config.mjs';
4
4
  import 'node:fs';
5
5
  import 'node:process';
6
6
  import 'ansis';
@@ -11,9 +11,9 @@ import 'node:util';
11
11
  import 'node:url';
12
12
  import 'inquirer-toggle';
13
13
  import 'ora';
14
+ import 'tinyexec';
14
15
  import 'semver';
15
16
  import 'smol-toml';
16
- import 'tinyexec';
17
17
  import 'node:fs/promises';
18
18
  import 'i18next';
19
19
  import 'i18next-fs-backend';
@@ -183,18 +183,19 @@ class ClaudeCodeConfigManager {
183
183
  * Apply profile settings to Claude Code runtime
184
184
  */
185
185
  static async applyProfileSettings(profile) {
186
- const { ensureI18nInitialized, i18n } = await import('./simple-config.mjs').then(function (n) { return n.bc; });
186
+ const { ensureI18nInitialized, i18n } = await import('./simple-config.mjs').then(function (n) { return n.bg; });
187
187
  ensureI18nInitialized();
188
188
  try {
189
189
  if (!profile) {
190
- const { switchToOfficialLogin } = await import('./simple-config.mjs').then(function (n) { return n.bg; });
190
+ const { switchToOfficialLogin } = await import('./simple-config.mjs').then(function (n) { return n.bk; });
191
191
  switchToOfficialLogin();
192
192
  return;
193
193
  }
194
- const { readJsonConfig: readJsonConfig2, writeJsonConfig } = await import('./simple-config.mjs').then(function (n) { return n.be; });
194
+ const { readJsonConfig: readJsonConfig2, writeJsonConfig } = await import('./simple-config.mjs').then(function (n) { return n.bi; });
195
195
  const settings = readJsonConfig2(SETTINGS_FILE) || {};
196
196
  if (!settings.env)
197
197
  settings.env = {};
198
+ clearModelEnv(settings.env);
198
199
  let shouldRestartCcr = false;
199
200
  if (profile.authType === "api_key") {
200
201
  settings.env.ANTHROPIC_API_KEY = profile.apiKey;
@@ -203,7 +204,7 @@ class ClaudeCodeConfigManager {
203
204
  settings.env.ANTHROPIC_AUTH_TOKEN = profile.apiKey;
204
205
  delete settings.env.ANTHROPIC_API_KEY;
205
206
  } else if (profile.authType === "ccr_proxy") {
206
- const { readCcrConfig } = await import('./simple-config.mjs').then(function (n) { return n.bh; });
207
+ const { readCcrConfig } = await import('./simple-config.mjs').then(function (n) { return n.bl; });
207
208
  const ccrConfig = readCcrConfig();
208
209
  if (!ccrConfig) {
209
210
  throw new Error(i18n.t("ccr:ccrNotConfigured") || "CCR proxy configuration not found");
@@ -222,18 +223,23 @@ class ClaudeCodeConfigManager {
222
223
  else
223
224
  delete settings.env.ANTHROPIC_BASE_URL;
224
225
  }
225
- if (profile.primaryModel) {
226
- settings.env.ANTHROPIC_MODEL = profile.primaryModel;
227
- } else {
228
- delete settings.env.ANTHROPIC_MODEL;
229
- }
230
- if (profile.fastModel) {
231
- settings.env.ANTHROPIC_SMALL_FAST_MODEL = profile.fastModel;
226
+ const hasModelConfig = Boolean(
227
+ profile.primaryModel || profile.defaultHaikuModel || profile.defaultSonnetModel || profile.defaultOpusModel
228
+ );
229
+ if (hasModelConfig) {
230
+ if (profile.primaryModel)
231
+ settings.env.ANTHROPIC_MODEL = profile.primaryModel;
232
+ if (profile.defaultHaikuModel)
233
+ settings.env.ANTHROPIC_DEFAULT_HAIKU_MODEL = profile.defaultHaikuModel;
234
+ if (profile.defaultSonnetModel)
235
+ settings.env.ANTHROPIC_DEFAULT_SONNET_MODEL = profile.defaultSonnetModel;
236
+ if (profile.defaultOpusModel)
237
+ settings.env.ANTHROPIC_DEFAULT_OPUS_MODEL = profile.defaultOpusModel;
232
238
  } else {
233
- delete settings.env.ANTHROPIC_SMALL_FAST_MODEL;
239
+ clearModelEnv(settings.env);
234
240
  }
235
241
  writeJsonConfig(SETTINGS_FILE, settings);
236
- const { setPrimaryApiKey, addCompletedOnboarding } = await import('./simple-config.mjs').then(function (n) { return n.bf; });
242
+ const { setPrimaryApiKey, addCompletedOnboarding } = await import('./simple-config.mjs').then(function (n) { return n.bj; });
237
243
  setPrimaryApiKey();
238
244
  addCompletedOnboarding();
239
245
  if (shouldRestartCcr) {
@@ -263,8 +269,12 @@ class ClaudeCodeConfigManager {
263
269
  sanitized.baseUrl = profile.baseUrl;
264
270
  if (profile.primaryModel)
265
271
  sanitized.primaryModel = profile.primaryModel;
266
- if (profile.fastModel)
267
- sanitized.fastModel = profile.fastModel;
272
+ if (profile.defaultHaikuModel)
273
+ sanitized.defaultHaikuModel = profile.defaultHaikuModel;
274
+ if (profile.defaultSonnetModel)
275
+ sanitized.defaultSonnetModel = profile.defaultSonnetModel;
276
+ if (profile.defaultOpusModel)
277
+ sanitized.defaultOpusModel = profile.defaultOpusModel;
268
278
  return sanitized;
269
279
  }
270
280
  /**
@@ -590,7 +600,7 @@ class ClaudeCodeConfigManager {
590
600
  */
591
601
  static async syncCcrProfile() {
592
602
  try {
593
- const { readCcrConfig } = await import('./simple-config.mjs').then(function (n) { return n.bh; });
603
+ const { readCcrConfig } = await import('./simple-config.mjs').then(function (n) { return n.bl; });
594
604
  const ccrConfig = readCcrConfig();
595
605
  if (!ccrConfig) {
596
606
  await this.ensureCcrProfileExists(ccrConfig);
@@ -1,6 +1,6 @@
1
1
  import ansis from 'ansis';
2
2
  import inquirer from 'inquirer';
3
- import { ah as ensureI18nInitialized, ai as i18n, aj as addNumbersToChoices, ak as validateApiKey, al as promptBoolean } from './simple-config.mjs';
3
+ import { ak as ensureI18nInitialized, al as i18n, am as addNumbersToChoices, an as validateApiKey, ao as promptBoolean } from './simple-config.mjs';
4
4
  import { ClaudeCodeConfigManager } from './claude-code-config-manager.mjs';
5
5
  import 'node:fs';
6
6
  import 'node:process';
@@ -12,9 +12,9 @@ import 'pathe';
12
12
  import 'node:url';
13
13
  import 'inquirer-toggle';
14
14
  import 'ora';
15
+ import 'tinyexec';
15
16
  import 'semver';
16
17
  import 'smol-toml';
17
- import 'tinyexec';
18
18
  import 'node:fs/promises';
19
19
  import 'i18next';
20
20
  import 'i18next-fs-backend';
@@ -201,16 +201,21 @@ ${i18n.t("multi-config:addingNewProfile")}`));
201
201
  if (modelConfig.primaryModel.trim()) {
202
202
  profile.primaryModel = modelConfig.primaryModel.trim();
203
203
  }
204
- if (modelConfig.fastModel.trim()) {
205
- profile.fastModel = modelConfig.fastModel.trim();
206
- }
204
+ if (modelConfig.haikuModel.trim())
205
+ profile.defaultHaikuModel = modelConfig.haikuModel.trim();
206
+ if (modelConfig.sonnetModel.trim())
207
+ profile.defaultSonnetModel = modelConfig.sonnetModel.trim();
208
+ if (modelConfig.opusModel.trim())
209
+ profile.defaultOpusModel = modelConfig.opusModel.trim();
207
210
  } else if (prefilledDefaultModels?.length) {
208
- if (prefilledDefaultModels[0]?.trim()) {
211
+ if (prefilledDefaultModels[0]?.trim())
209
212
  profile.primaryModel = prefilledDefaultModels[0].trim();
210
- }
211
- if (prefilledDefaultModels[1]?.trim()) {
212
- profile.fastModel = prefilledDefaultModels[1].trim();
213
- }
213
+ if (prefilledDefaultModels[1]?.trim())
214
+ profile.defaultHaikuModel = prefilledDefaultModels[1].trim();
215
+ if (prefilledDefaultModels[2]?.trim())
216
+ profile.defaultSonnetModel = prefilledDefaultModels[2].trim();
217
+ if (prefilledDefaultModels[3]?.trim())
218
+ profile.defaultOpusModel = prefilledDefaultModels[3].trim();
214
219
  }
215
220
  const existingProfile = ClaudeCodeConfigManager.getProfileByName(profile.name);
216
221
  if (existingProfile) {
@@ -235,7 +240,9 @@ ${i18n.t("multi-config:addingNewProfile")}`));
235
240
  apiKey: profile.apiKey,
236
241
  baseUrl: profile.baseUrl,
237
242
  primaryModel: profile.primaryModel,
238
- fastModel: profile.fastModel
243
+ defaultHaikuModel: profile.defaultHaikuModel,
244
+ defaultSonnetModel: profile.defaultSonnetModel,
245
+ defaultOpusModel: profile.defaultOpusModel
239
246
  });
240
247
  if (updateResult.success) {
241
248
  console.log(ansis.green(i18n.t("multi-config:profileUpdated", { name: profile.name })));
@@ -358,7 +365,9 @@ ${i18n.t("multi-config:editingProfile", { name: selectedProfile.name })}`));
358
365
  const { promptCustomModels } = await import('./features.mjs');
359
366
  modelConfig = await promptCustomModels(
360
367
  selectedProfile.primaryModel,
361
- selectedProfile.fastModel
368
+ selectedProfile.defaultHaikuModel,
369
+ selectedProfile.defaultSonnetModel,
370
+ selectedProfile.defaultOpusModel
362
371
  );
363
372
  }
364
373
  const updateData = {
@@ -371,9 +380,12 @@ ${i18n.t("multi-config:editingProfile", { name: selectedProfile.name })}`));
371
380
  if (modelConfig.primaryModel.trim()) {
372
381
  updateData.primaryModel = modelConfig.primaryModel.trim();
373
382
  }
374
- if (modelConfig.fastModel.trim()) {
375
- updateData.fastModel = modelConfig.fastModel.trim();
376
- }
383
+ if (modelConfig.haikuModel.trim())
384
+ updateData.defaultHaikuModel = modelConfig.haikuModel.trim();
385
+ if (modelConfig.sonnetModel.trim())
386
+ updateData.defaultSonnetModel = modelConfig.sonnetModel.trim();
387
+ if (modelConfig.opusModel.trim())
388
+ updateData.defaultOpusModel = modelConfig.opusModel.trim();
377
389
  }
378
390
  }
379
391
  const result = await ClaudeCodeConfigManager.updateProfile(selectedProfile.id, updateData);
@@ -480,7 +492,9 @@ ${i18n.t("multi-config:copyingProfile", { name: selectedProfile.name })}`));
480
492
  const { promptCustomModels } = await import('./features.mjs');
481
493
  modelConfig = await promptCustomModels(
482
494
  selectedProfile.primaryModel,
483
- selectedProfile.fastModel
495
+ selectedProfile.defaultHaikuModel,
496
+ selectedProfile.defaultSonnetModel,
497
+ selectedProfile.defaultOpusModel
484
498
  );
485
499
  }
486
500
  const setAsDefault = await promptBoolean({
@@ -501,9 +515,12 @@ ${i18n.t("multi-config:copyingProfile", { name: selectedProfile.name })}`));
501
515
  if (modelConfig.primaryModel.trim()) {
502
516
  copiedProfile.primaryModel = modelConfig.primaryModel.trim();
503
517
  }
504
- if (modelConfig.fastModel.trim()) {
505
- copiedProfile.fastModel = modelConfig.fastModel.trim();
506
- }
518
+ if (modelConfig.haikuModel.trim())
519
+ copiedProfile.defaultHaikuModel = modelConfig.haikuModel.trim();
520
+ if (modelConfig.sonnetModel.trim())
521
+ copiedProfile.defaultSonnetModel = modelConfig.sonnetModel.trim();
522
+ if (modelConfig.opusModel.trim())
523
+ copiedProfile.defaultOpusModel = modelConfig.opusModel.trim();
507
524
  }
508
525
  }
509
526
  const result = await ClaudeCodeConfigManager.addProfile(copiedProfile);
@@ -581,4 +598,4 @@ async function handleDeleteProfile(profiles) {
581
598
  }
582
599
  }
583
600
 
584
- export { configureIncrementalManagement };
601
+ export { configureIncrementalManagement, getAuthTypeLabel };
@@ -1,6 +1,6 @@
1
1
  import ansis from 'ansis';
2
2
  import inquirer from 'inquirer';
3
- import { ah as ensureI18nInitialized, at as detectConfigManagementMode, ai as i18n, aj as addNumbersToChoices, al as promptBoolean, aq as readJsonConfig, l as CODEX_AUTH_FILE } from './simple-config.mjs';
3
+ import { ak as ensureI18nInitialized, ax as detectConfigManagementMode, al as i18n, am as addNumbersToChoices, ao as promptBoolean, at as readJsonConfig, l as CODEX_AUTH_FILE } from './simple-config.mjs';
4
4
  import { deleteProviders, addProviderToExisting, editExistingProvider } from './codex-provider-manager.mjs';
5
5
  import 'node:fs';
6
6
  import 'node:process';
@@ -12,9 +12,9 @@ import 'pathe';
12
12
  import 'node:url';
13
13
  import 'inquirer-toggle';
14
14
  import 'ora';
15
+ import 'tinyexec';
15
16
  import 'semver';
16
17
  import 'smol-toml';
17
- import 'tinyexec';
18
18
  import 'node:fs/promises';
19
19
  import 'i18next';
20
20
  import 'i18next-fs-backend';
@@ -150,7 +150,7 @@ async function handleAddProvider() {
150
150
  name: answers.providerName.trim(),
151
151
  baseUrl: selectedProvider === "custom" ? answers.baseUrl.trim() : prefilledBaseUrl,
152
152
  wireApi: selectedProvider === "custom" ? answers.wireApi : prefilledWireApi,
153
- envKey: `${providerId.toUpperCase().replace(/-/g, "_")}_API_KEY`,
153
+ tempEnvKey: `${providerId.toUpperCase().replace(/-/g, "_")}_API_KEY`,
154
154
  requiresOpenaiAuth: true,
155
155
  model: prefilledModel || "gpt-5-codex"
156
156
  // Use provider's default model or fallback
@@ -166,7 +166,7 @@ async function handleAddProvider() {
166
166
  defaultValue: true
167
167
  });
168
168
  if (setAsDefault) {
169
- const { switchToProvider } = await import('./simple-config.mjs').then(function (n) { return n.bj; });
169
+ const { switchToProvider } = await import('./simple-config.mjs').then(function (n) { return n.bn; });
170
170
  const switched = await switchToProvider(provider.id);
171
171
  if (switched) {
172
172
  console.log(ansis.green(i18n.t("multi-config:profileSetAsDefault", { name: provider.name })));
@@ -197,7 +197,7 @@ async function handleEditProvider(providers) {
197
197
  return;
198
198
  }
199
199
  const existingAuth = readJsonConfig(CODEX_AUTH_FILE, { defaultValue: {} }) || {};
200
- const existingApiKey = existingAuth[provider.envKey] || "";
200
+ const existingApiKey = existingAuth[provider.tempEnvKey] || "";
201
201
  const answers = await inquirer.prompt([
202
202
  {
203
203
  type: "input",
@@ -288,7 +288,7 @@ async function handleCopyProvider(providers) {
288
288
  console.log(ansis.cyan(`
289
289
  ${i18n.t("codex:copyingProvider", { name: provider.name })}`));
290
290
  const existingAuth = readJsonConfig(CODEX_AUTH_FILE, { defaultValue: {} }) || {};
291
- const existingApiKey = existingAuth[provider.envKey] || "";
291
+ const existingApiKey = existingAuth[provider.tempEnvKey] || "";
292
292
  const copiedName = `${provider.name}-copy`;
293
293
  const answers = await inquirer.prompt([
294
294
  {
@@ -346,7 +346,7 @@ ${i18n.t("codex:copyingProvider", { name: provider.name })}`));
346
346
  name: answers.providerName.trim(),
347
347
  baseUrl: answers.baseUrl.trim(),
348
348
  wireApi: answers.wireApi,
349
- envKey: `${providerId.toUpperCase().replace(/-/g, "_")}_API_KEY`,
349
+ tempEnvKey: `${providerId.toUpperCase().replace(/-/g, "_")}_API_KEY`,
350
350
  requiresOpenaiAuth: provider.requiresOpenaiAuth ?? true,
351
351
  model: model.trim()
352
352
  };
@@ -361,7 +361,7 @@ ${i18n.t("codex:copyingProvider", { name: provider.name })}`));
361
361
  defaultValue: false
362
362
  });
363
363
  if (setAsDefault) {
364
- const { switchToProvider } = await import('./simple-config.mjs').then(function (n) { return n.bj; });
364
+ const { switchToProvider } = await import('./simple-config.mjs').then(function (n) { return n.bn; });
365
365
  const switched = await switchToProvider(copiedProvider.id);
366
366
  if (switched) {
367
367
  console.log(ansis.green(i18n.t("multi-config:profileSetAsDefault", { name: copiedProvider.name })));
@@ -1,4 +1,4 @@
1
- import { ah as ensureI18nInitialized, au as readCodexConfig, ai as i18n, av as backupCodexComplete, aw as writeCodexConfig, ax as writeAuthFile } from './simple-config.mjs';
1
+ import { ak as ensureI18nInitialized, ay as readCodexConfig, al as i18n, az as backupCodexComplete, aA as writeCodexConfig, aB as writeAuthFile } from './simple-config.mjs';
2
2
  import 'node:fs';
3
3
  import 'node:process';
4
4
  import 'ansis';
@@ -11,9 +11,9 @@ import 'pathe';
11
11
  import 'node:url';
12
12
  import 'inquirer-toggle';
13
13
  import 'ora';
14
+ import 'tinyexec';
14
15
  import 'semver';
15
16
  import 'smol-toml';
16
- import 'tinyexec';
17
17
  import 'node:fs/promises';
18
18
  import 'i18next';
19
19
  import 'i18next-fs-backend';
@@ -22,43 +22,52 @@ async function addProviderToExisting(provider, apiKey, allowOverwrite = false) {
22
22
  ensureI18nInitialized();
23
23
  try {
24
24
  const existingConfig = readCodexConfig();
25
- if (!existingConfig) {
26
- return {
27
- success: false,
28
- error: i18n.t("codex:providerManager.noConfig")
29
- };
30
- }
31
- const existingProviderIndex = existingConfig.providers.findIndex((p) => p.id === provider.id);
25
+ const existingProviderIndex = existingConfig?.providers.findIndex((p) => p.id === provider.id) ?? -1;
32
26
  if (existingProviderIndex !== -1 && !allowOverwrite) {
33
27
  return {
34
28
  success: false,
35
29
  error: i18n.t("codex:providerManager.providerExists", { id: provider.id })
36
30
  };
37
31
  }
38
- const backupPath = backupCodexComplete();
39
- if (!backupPath) {
40
- return {
41
- success: false,
42
- error: i18n.t("codex:providerManager.backupFailed")
43
- };
44
- }
45
32
  let updatedConfig;
46
- if (existingProviderIndex !== -1) {
33
+ if (!existingConfig) {
34
+ updatedConfig = {
35
+ model: provider.model || null,
36
+ modelProvider: provider.id,
37
+ providers: [provider],
38
+ mcpServices: [],
39
+ managed: true,
40
+ otherConfig: []
41
+ };
42
+ } else if (existingProviderIndex !== -1) {
47
43
  const updatedProviders = [...existingConfig.providers];
48
44
  updatedProviders[existingProviderIndex] = provider;
49
45
  updatedConfig = {
50
46
  ...existingConfig,
51
- providers: updatedProviders
47
+ providers: updatedProviders,
48
+ modelProvider: existingConfig.modelProvider || provider.id
52
49
  };
53
50
  } else {
54
51
  updatedConfig = {
55
52
  ...existingConfig,
56
- providers: [...existingConfig.providers, provider]
53
+ providers: [...existingConfig.providers, provider],
54
+ modelProvider: existingConfig.modelProvider || provider.id
57
55
  };
58
56
  }
57
+ let backupPath;
58
+ if (existingConfig) {
59
+ const backup = backupCodexComplete();
60
+ if (!backup) {
61
+ return {
62
+ success: false,
63
+ error: i18n.t("codex:providerManager.backupFailed")
64
+ };
65
+ }
66
+ backupPath = backup || void 0;
67
+ }
59
68
  writeCodexConfig(updatedConfig);
60
69
  const authEntries = {};
61
- authEntries[provider.envKey] = apiKey;
70
+ authEntries[provider.tempEnvKey] = apiKey;
62
71
  writeAuthFile(authEntries);
63
72
  return {
64
73
  success: true,
@@ -112,7 +121,7 @@ async function editExistingProvider(providerId, updates) {
112
121
  writeCodexConfig(updatedConfig);
113
122
  if (updates.apiKey) {
114
123
  const authEntries = {};
115
- authEntries[updatedProvider.envKey] = updates.apiKey;
124
+ authEntries[updatedProvider.tempEnvKey] = updates.apiKey;
116
125
  writeAuthFile(authEntries);
117
126
  }
118
127
  return {
@@ -1,6 +1,6 @@
1
1
  import { pathExists } from 'fs-extra';
2
2
  import { join } from 'pathe';
3
- import { j as CODEX_DIR, k as CODEX_CONFIG_FILE, ai as i18n, l as CODEX_AUTH_FILE, n as CODEX_AGENTS_FILE, p as CODEX_PROMPTS_DIR } from './simple-config.mjs';
3
+ import { j as CODEX_DIR, k as CODEX_CONFIG_FILE, al as i18n, l as CODEX_AUTH_FILE, n as CODEX_AGENTS_FILE, p as CODEX_PROMPTS_DIR } from './simple-config.mjs';
4
4
  import { m as moveToTrash } from '../shared/zcf.DGjQxTq_.mjs';
5
5
  import 'node:fs';
6
6
  import 'node:process';
@@ -13,9 +13,9 @@ import 'dayjs';
13
13
  import 'node:url';
14
14
  import 'inquirer-toggle';
15
15
  import 'ora';
16
+ import 'tinyexec';
16
17
  import 'semver';
17
18
  import 'smol-toml';
18
- import 'tinyexec';
19
19
  import 'node:fs/promises';
20
20
  import 'i18next';
21
21
  import 'i18next-fs-backend';
@@ -155,7 +155,7 @@ class CodexUninstaller {
155
155
  warnings: []
156
156
  };
157
157
  try {
158
- const { uninstallCodeTool } = await import('./simple-config.mjs').then(function (n) { return n.bk; });
158
+ const { uninstallCodeTool } = await import('./simple-config.mjs').then(function (n) { return n.bo; });
159
159
  const success = await uninstallCodeTool("codex");
160
160
  if (success) {
161
161
  result.removed.push("@openai/codex");
@@ -1,7 +1,7 @@
1
1
  import { exec } from 'node:child_process';
2
2
  import { promisify } from 'node:util';
3
3
  import ansis from 'ansis';
4
- import { ah as ensureI18nInitialized, ai as i18n } from './simple-config.mjs';
4
+ import { ak as ensureI18nInitialized, al as i18n } from './simple-config.mjs';
5
5
  import 'node:fs';
6
6
  import 'node:process';
7
7
  import 'inquirer';
@@ -11,9 +11,9 @@ import 'pathe';
11
11
  import 'node:url';
12
12
  import 'inquirer-toggle';
13
13
  import 'ora';
14
+ import 'tinyexec';
14
15
  import 'semver';
15
16
  import 'smol-toml';
16
- import 'tinyexec';
17
17
  import 'node:fs/promises';
18
18
  import 'i18next';
19
19
  import 'i18next-fs-backend';
@@ -1,6 +1,6 @@
1
1
  import ansis from 'ansis';
2
2
  import inquirer from 'inquirer';
3
- import { ai as i18n, ah as ensureI18nInitialized, x as SUPPORTED_LANGS, aj as addNumbersToChoices, y as LANG_LABELS, ay as updateZcfConfig, az as changeLanguage, aA as readZcfConfig, al as promptBoolean, o as openSettingsJson, d as importRecommendedPermissions, b as importRecommendedEnv, a1 as applyAiLanguageDirective, aB as configureOutputStyle, $ as getExistingModelConfig, X as updateCustomModel, Y as updateDefaultModel, aC as isWindows, F as readMcpConfig, K as fixWindowsMcpConfig, G as writeMcpConfig, aD as selectMcpServices, H as backupMcpConfig, aE as getMcpServices, J as buildMcpServerConfig, I as mergeMcpServers, aF as isCcrInstalled, aG as installCcr, aH as setupCcrConfiguration, a0 as getExistingApiConfig, a3 as promptApiConfigurationAction, aI as modifyApiConfigPartially, ak as validateApiKey, V as configureApi, aJ as formatApiKeyDisplay, a2 as switchToOfficialLogin } from './simple-config.mjs';
3
+ import { al as i18n, ak as ensureI18nInitialized, x as SUPPORTED_LANGS, am as addNumbersToChoices, y as LANG_LABELS, aC as updateZcfConfig, aD as changeLanguage, aE as readZcfConfig, ao as promptBoolean, o as openSettingsJson, d as importRecommendedPermissions, b as importRecommendedEnv, a1 as applyAiLanguageDirective, aF as configureOutputStyle, $ as getExistingModelConfig, X as updateCustomModel, Y as updateDefaultModel, aG as isWindows, F as readMcpConfig, K as fixWindowsMcpConfig, G as writeMcpConfig, aH as selectMcpServices, H as backupMcpConfig, aI as getMcpServices, J as buildMcpServerConfig, I as mergeMcpServers, aJ as isCcrInstalled, aK as installCcr, aL as setupCcrConfiguration, a0 as getExistingApiConfig, a3 as promptApiConfigurationAction, aM as modifyApiConfigPartially, an as validateApiKey, V as configureApi, aN as formatApiKeyDisplay, a2 as switchToOfficialLogin } from './simple-config.mjs';
4
4
  import 'node:fs';
5
5
  import 'node:process';
6
6
  import 'node:child_process';
@@ -11,9 +11,9 @@ import 'pathe';
11
11
  import 'node:url';
12
12
  import 'inquirer-toggle';
13
13
  import 'ora';
14
+ import 'tinyexec';
14
15
  import 'semver';
15
16
  import 'smol-toml';
16
- import 'tinyexec';
17
17
  import 'node:fs/promises';
18
18
  import 'i18next';
19
19
  import 'i18next-fs-backend';
@@ -273,32 +273,44 @@ ${ansis.blue(`\u2139 ${i18n.t("configuration:existingModelConfig") || "Existing
273
273
  return;
274
274
  }
275
275
  if (model === "custom") {
276
- const { primaryModel, fastModel } = await promptCustomModels();
277
- if (!primaryModel.trim() && !fastModel.trim()) {
276
+ const { primaryModel, haikuModel, sonnetModel, opusModel } = await promptCustomModels();
277
+ if (!primaryModel.trim() && !haikuModel.trim() && !sonnetModel.trim() && !opusModel.trim()) {
278
278
  console.log(ansis.yellow(`\u26A0 ${i18n.t("configuration:customModelSkipped") || "Custom model configuration skipped"}`));
279
279
  return;
280
280
  }
281
- updateCustomModel(primaryModel, fastModel);
281
+ updateCustomModel(primaryModel, haikuModel, sonnetModel, opusModel);
282
282
  console.log(ansis.green(`\u2714 ${i18n.t("configuration:customModelConfigured") || "Custom model configuration completed"}`));
283
283
  return;
284
284
  }
285
285
  updateDefaultModel(model);
286
286
  console.log(ansis.green(`\u2714 ${i18n.t("configuration:modelConfigured") || "Default model configured"}`));
287
287
  }
288
- async function promptCustomModels(defaultPrimaryModel, defaultFastModel) {
288
+ async function promptCustomModels(defaultPrimaryModel, defaultHaikuModel, defaultSonnetModel, defaultOpusModel) {
289
289
  const { primaryModel } = await inquirer.prompt({
290
290
  type: "input",
291
291
  name: "primaryModel",
292
292
  message: `${i18n.t("configuration:enterPrimaryModel")}${i18n.t("common:emptyToSkip")}`,
293
293
  default: defaultPrimaryModel || ""
294
294
  });
295
- const { fastModel } = await inquirer.prompt({
295
+ const { haikuModel } = await inquirer.prompt({
296
+ type: "input",
297
+ name: "haikuModel",
298
+ message: `${i18n.t("configuration:enterHaikuModel")}${i18n.t("common:emptyToSkip")}`,
299
+ default: defaultHaikuModel || ""
300
+ });
301
+ const { sonnetModel } = await inquirer.prompt({
302
+ type: "input",
303
+ name: "sonnetModel",
304
+ message: `${i18n.t("configuration:enterSonnetModel")}${i18n.t("common:emptyToSkip")}`,
305
+ default: defaultSonnetModel || ""
306
+ });
307
+ const { opusModel } = await inquirer.prompt({
296
308
  type: "input",
297
- name: "fastModel",
298
- message: `${i18n.t("configuration:enterFastModel")}${i18n.t("common:emptyToSkip")}`,
299
- default: defaultFastModel || ""
309
+ name: "opusModel",
310
+ message: `${i18n.t("configuration:enterOpusModel")}${i18n.t("common:emptyToSkip")}`,
311
+ default: defaultOpusModel || ""
300
312
  });
301
- return { primaryModel, fastModel };
313
+ return { primaryModel, haikuModel, sonnetModel, opusModel };
302
314
  }
303
315
  async function configureAiMemoryFeature() {
304
316
  ensureI18nInitialized();
@@ -339,7 +351,7 @@ ${ansis.blue(`\u2139 ${i18n.t("configuration:existingLanguageConfig") || "Existi
339
351
  return;
340
352
  }
341
353
  }
342
- const { selectAiOutputLanguage } = await import('./simple-config.mjs').then(function (n) { return n.bi; });
354
+ const { selectAiOutputLanguage } = await import('./simple-config.mjs').then(function (n) { return n.bm; });
343
355
  const aiOutputLang = await selectAiOutputLanguage();
344
356
  applyAiLanguageDirective(aiOutputLang);
345
357
  updateZcfConfig({ aiOutputLang });
@@ -372,7 +384,7 @@ async function changeScriptLanguageFeature(currentLang) {
372
384
  }
373
385
  async function configureCodexDefaultModelFeature() {
374
386
  ensureI18nInitialized();
375
- const { readCodexConfig } = await import('./simple-config.mjs').then(function (n) { return n.bj; });
387
+ const { readCodexConfig } = await import('./simple-config.mjs').then(function (n) { return n.bn; });
376
388
  const existingConfig = readCodexConfig();
377
389
  const currentModel = existingConfig?.model;
378
390
  if (currentModel) {
@@ -473,7 +485,7 @@ ${ansis.blue(`\u2139 ${i18n.t("configuration:existingLanguageConfig") || "Existi
473
485
  return;
474
486
  }
475
487
  }
476
- const { selectAiOutputLanguage } = await import('./simple-config.mjs').then(function (n) { return n.bi; });
488
+ const { selectAiOutputLanguage } = await import('./simple-config.mjs').then(function (n) { return n.bm; });
477
489
  const aiOutputLang = await selectAiOutputLanguage();
478
490
  await updateCodexLanguageDirective(aiOutputLang);
479
491
  updateZcfConfig({ aiOutputLang });
@@ -481,14 +493,14 @@ ${ansis.blue(`\u2139 ${i18n.t("configuration:existingLanguageConfig") || "Existi
481
493
  } else if (option === "systemPrompt") {
482
494
  const zcfConfig = readZcfConfig();
483
495
  const currentLang = zcfConfig?.aiOutputLang || "English";
484
- const { runCodexSystemPromptSelection } = await import('./simple-config.mjs').then(function (n) { return n.bj; });
496
+ const { runCodexSystemPromptSelection } = await import('./simple-config.mjs').then(function (n) { return n.bn; });
485
497
  await runCodexSystemPromptSelection();
486
498
  await ensureLanguageDirectiveInAgents(currentLang);
487
499
  console.log(ansis.green(`\u2714 ${i18n.t("configuration:systemPromptConfigured")}`));
488
500
  }
489
501
  }
490
502
  async function updateCodexModelProvider(modelProvider) {
491
- const { readCodexConfig, writeCodexConfig, backupCodexConfig, getBackupMessage } = await import('./simple-config.mjs').then(function (n) { return n.bj; });
503
+ const { readCodexConfig, writeCodexConfig, backupCodexConfig, getBackupMessage } = await import('./simple-config.mjs').then(function (n) { return n.bn; });
492
504
  const backupPath = backupCodexConfig();
493
505
  if (backupPath) {
494
506
  console.log(ansis.gray(getBackupMessage(backupPath)));
@@ -509,7 +521,7 @@ async function updateCodexModelProvider(modelProvider) {
509
521
  writeCodexConfig(updatedConfig);
510
522
  }
511
523
  async function ensureLanguageDirectiveInAgents(aiOutputLang) {
512
- const { readFile, writeFile, exists } = await import('./simple-config.mjs').then(function (n) { return n.bd; });
524
+ const { readFile, writeFile, exists } = await import('./simple-config.mjs').then(function (n) { return n.bh; });
513
525
  const { homedir } = await import('node:os');
514
526
  const { join } = await import('pathe');
515
527
  const CODEX_AGENTS_FILE = join(homedir(), ".codex", "AGENTS.md");
@@ -527,7 +539,7 @@ async function ensureLanguageDirectiveInAgents(aiOutputLang) {
527
539
  const langLabel = languageLabels[aiOutputLang] || aiOutputLang;
528
540
  const hasLanguageDirective = /\*\*Most Important:\s*Always respond in [^*]+\*\*/i.test(content);
529
541
  if (!hasLanguageDirective) {
530
- const { backupCodexAgents, getBackupMessage } = await import('./simple-config.mjs').then(function (n) { return n.bj; });
542
+ const { backupCodexAgents, getBackupMessage } = await import('./simple-config.mjs').then(function (n) { return n.bn; });
531
543
  const backupPath = backupCodexAgents();
532
544
  if (backupPath) {
533
545
  console.log(ansis.gray(getBackupMessage(backupPath)));
@@ -544,8 +556,8 @@ async function ensureLanguageDirectiveInAgents(aiOutputLang) {
544
556
  }
545
557
  }
546
558
  async function updateCodexLanguageDirective(aiOutputLang) {
547
- const { readFile, writeFile, exists } = await import('./simple-config.mjs').then(function (n) { return n.bd; });
548
- const { backupCodexAgents, getBackupMessage } = await import('./simple-config.mjs').then(function (n) { return n.bj; });
559
+ const { readFile, writeFile, exists } = await import('./simple-config.mjs').then(function (n) { return n.bh; });
560
+ const { backupCodexAgents, getBackupMessage } = await import('./simple-config.mjs').then(function (n) { return n.bn; });
549
561
  const { homedir } = await import('node:os');
550
562
  const { join } = await import('pathe');
551
563
  const CODEX_AGENTS_FILE = join(homedir(), ".codex", "AGENTS.md");