yymaxapi 1.0.66 → 1.0.67

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 (2) hide show
  1. package/bin/yymaxapi.js +73 -17
  2. package/package.json +1 -1
package/bin/yymaxapi.js CHANGED
@@ -726,6 +726,8 @@ function writeCodexConfig(baseUrl, apiKey) {
726
726
 
727
727
  function writeOpencodeConfig(claudeBaseUrl, codexBaseUrl, apiKey, modelId) {
728
728
  const home = os.homedir();
729
+
730
+ // ---- 1. opencode.json (CLI + 桌面版) ----
729
731
  const configDir = process.platform === 'win32'
730
732
  ? path.join(process.env.APPDATA || path.join(home, 'AppData', 'Roaming'), 'opencode')
731
733
  : path.join(home, '.config', 'opencode');
@@ -737,20 +739,14 @@ function writeOpencodeConfig(claudeBaseUrl, codexBaseUrl, apiKey, modelId) {
737
739
  try { existing = JSON.parse(fs.readFileSync(configPath, 'utf8')); } catch { existing = {}; }
738
740
  }
739
741
  const cleanClaudeUrl = claudeBaseUrl.replace(/\/+$/, '');
740
- let cleanCodexUrl = (codexBaseUrl || '').replace(/\/+$/, '');
742
+ const cleanCodexUrl = (codexBaseUrl || '').replace(/\/+$/, '');
741
743
  if (!existing.provider) existing.provider = {};
742
744
  existing.provider.anthropic = {
743
- options: {
744
- apiKey: apiKey,
745
- baseURL: cleanClaudeUrl
746
- }
745
+ options: { apiKey: apiKey, baseURL: cleanClaudeUrl }
747
746
  };
748
747
  if (cleanCodexUrl) {
749
748
  existing.provider.openai = {
750
- options: {
751
- apiKey: apiKey,
752
- baseURL: cleanCodexUrl
753
- }
749
+ options: { apiKey: apiKey, baseURL: cleanCodexUrl }
754
750
  };
755
751
  }
756
752
  const rawModelId = modelId || 'claude-sonnet-4-6';
@@ -759,10 +755,68 @@ function writeOpencodeConfig(claudeBaseUrl, codexBaseUrl, apiKey, modelId) {
759
755
  : `anthropic/${rawModelId}`;
760
756
  if (!existing.$schema) existing.$schema = 'https://opencode.ai/config.json';
761
757
  fs.writeFileSync(configPath, JSON.stringify(existing, null, 2), 'utf8');
762
- return configPath;
763
- } catch {
764
- return null;
765
- }
758
+ } catch { /* 非关键,静默失败 */ }
759
+
760
+ // ---- 2. ~/.codex/config.toml (opencode 也读此格式) ----
761
+ const codexDir = path.join(home, '.codex');
762
+ const codexConfigPath = path.join(codexDir, 'config.toml');
763
+ try {
764
+ if (!fs.existsSync(codexDir)) fs.mkdirSync(codexDir, { recursive: true });
765
+
766
+ const claudeUrl = claudeBaseUrl.replace(/\/+$/, '');
767
+ const codexUrl = (codexBaseUrl || '').replace(/\/+$/, '');
768
+
769
+ const marker = '# >>> yunyi opencode >>>';
770
+ const markerEnd = '# <<< yunyi opencode <<<';
771
+ let existing = '';
772
+ if (fs.existsSync(codexConfigPath)) {
773
+ existing = fs.readFileSync(codexConfigPath, 'utf8');
774
+ const re = new RegExp(`${marker.replace(/[.*+?^${}()|[\\]\\]/g, '\\$&')}[\\s\\S]*?${markerEnd.replace(/[.*+?^${}()|[\\]\\]/g, '\\$&')}\\n?`, 'g');
775
+ existing = existing.replace(re, '').trim();
776
+ }
777
+
778
+ const section = [
779
+ marker,
780
+ `model = "yunyi-claude/claude-sonnet-4-6"`,
781
+ `model_provider = "yunyi-claude"`,
782
+ `model_context_window = 1000000`,
783
+ `model_auto_compact_token_limit = 900000`,
784
+ `model_reasoning_effort = "xhigh"`,
785
+ '',
786
+ `[model_providers.yunyi-claude]`,
787
+ `name = "云翼 Claude"`,
788
+ `base_url = "${claudeUrl}"`,
789
+ `wire_api = "anthropic"`,
790
+ `env_key = "ANTHROPIC_API_KEY"`,
791
+ ];
792
+
793
+ if (codexUrl) {
794
+ section.push(
795
+ '',
796
+ `[model_providers.yunyi-codex]`,
797
+ `name = "云翼 Codex"`,
798
+ `base_url = "${codexUrl}"`,
799
+ `wire_api = "responses"`,
800
+ `requires_openai_auth = true`,
801
+ `env_key = "OPENAI_API_KEY"`,
802
+ );
803
+ }
804
+
805
+ section.push(markerEnd);
806
+ fs.writeFileSync(codexConfigPath, existing ? `${existing}\n\n${section.join('\n')}\n` : `${section.join('\n')}\n`, 'utf8');
807
+
808
+ // ~/.codex/auth.json
809
+ const authPath = path.join(codexDir, 'auth.json');
810
+ let auth = {};
811
+ if (fs.existsSync(authPath)) {
812
+ try { auth = JSON.parse(fs.readFileSync(authPath, 'utf8')); } catch { auth = {}; }
813
+ }
814
+ auth.ANTHROPIC_API_KEY = apiKey;
815
+ auth.OPENAI_API_KEY = apiKey;
816
+ fs.writeFileSync(authPath, JSON.stringify(auth, null, 2), 'utf8');
817
+ } catch { /* 非关键,静默失败 */ }
818
+
819
+ return configPath;
766
820
  }
767
821
 
768
822
  function syncExternalTools(type, baseUrl, apiKey, extra = {}) {
@@ -2966,11 +3020,13 @@ async function activateOpencode(paths, args = {}) {
2966
3020
  console.log(chalk.green('\n✅ Opencode 配置完成!'));
2967
3021
  console.log(chalk.cyan(` Claude: ${claudeBaseUrl}`));
2968
3022
  console.log(chalk.cyan(` Codex: ${codexBaseUrl}`));
2969
- console.log(chalk.gray(` 模型: ${modelId}`));
3023
+ console.log(chalk.gray(` 默认模型: anthropic/${modelId}`));
2970
3024
  console.log(chalk.gray(' API Key: 已设置'));
2971
- if (configPath) {
2972
- console.log(chalk.gray(` 配置文件: ${configPath}`));
2973
- }
3025
+ console.log(chalk.gray('\n 已写入:'));
3026
+ console.log(chalk.gray(' ~/.config/opencode/opencode.json (CLI + 桌面版)'));
3027
+ console.log(chalk.gray(' • ~/.codex/config.toml (model_providers)'));
3028
+ console.log(chalk.gray(' • ~/.codex/auth.json (API Keys)'));
3029
+ console.log(chalk.yellow('\n 切换模型: 在 opencode 内使用 /model 命令切换 claude/gpt'));
2974
3030
  }
2975
3031
 
2976
3032
  // ============ yycode 精简模式(零交互一键配置) ============
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "yymaxapi",
3
- "version": "1.0.66",
3
+ "version": "1.0.67",
4
4
  "description": "跨平台 OpenClaw/Clawdbot 配置管理工具 - 管理中转地址、模型切换、API Keys、测速优化",
5
5
  "main": "bin/yymaxapi.js",
6
6
  "bin": {