aixxai 1.4.2 → 1.4.4
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 +45 -45
- package/bin/aixx.js +88 -88
- package/package.json +1 -1
- package/src/commands/balance.js +147 -147
- package/src/commands/config.js +68 -68
- package/src/commands/help.js +43 -43
- package/src/commands/install.js +383 -383
- package/src/commands/models.js +140 -140
- package/src/commands/recharge.js +131 -131
- package/src/commands/test.js +101 -101
- package/src/utils/download.js +147 -147
- package/src/utils/env.js +136 -136
- package/templates/QUICKSTART.md +100 -100
- package/templates/SKILL.md +137 -135
- package/templates/references/account.md +68 -68
- package/templates/references/apps.md +208 -150
- package/templates/references/chat.md +135 -133
- package/templates/references/data.md +151 -151
- package/templates/references/notify.md +53 -53
- package/templates/references/search.md +96 -96
package/src/commands/models.js
CHANGED
|
@@ -1,140 +1,140 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* AIXX CLI - models 命令
|
|
3
|
-
*
|
|
4
|
-
* 列出AIXX支持的所有模型,按"国产/海外"分组展示。
|
|
5
|
-
*
|
|
6
|
-
* 数据来源:GET /v1/models
|
|
7
|
-
* 后端返回的模型列表是动态的,但分组规则是固定的(按模型名前缀分类)。
|
|
8
|
-
*/
|
|
9
|
-
|
|
10
|
-
import { DEFAULT_BASE_URL } from '../../bin/aixx.js';
|
|
11
|
-
import { loadApiKey, maskKey } from '../utils/env.js';
|
|
12
|
-
|
|
13
|
-
// 所有对外请求统一 15 秒超时
|
|
14
|
-
const FETCH_TIMEOUT = 15000;
|
|
15
|
-
// 网络/超时异常统一成友好提示
|
|
16
|
-
function friendlyNetErr(err) {
|
|
17
|
-
return err?.name === 'TimeoutError' || err?.name === 'AbortError'
|
|
18
|
-
? '连接超时,请检查网络'
|
|
19
|
-
: err?.message || String(err);
|
|
20
|
-
}
|
|
21
|
-
|
|
22
|
-
/**
|
|
23
|
-
* apiKey 读取统一走 src/utils/env.js 的 loadApiKey:
|
|
24
|
-
* 环境变量 AIXX_API_KEY → ~/.aixx/config.json → ~/.aixx/account.json
|
|
25
|
-
*/
|
|
26
|
-
|
|
27
|
-
// 给每个模型加一句人话说明,让用户知道怎么选
|
|
28
|
-
const MODEL_DESC = {
|
|
29
|
-
'deepseek-chat': '最便宜,¥0.001/千token,日常首选',
|
|
30
|
-
'deepseek-reasoner': '推理增强(带思考过程)',
|
|
31
|
-
'glm-4-flash': '智谱免费档,速度快',
|
|
32
|
-
'glm-4-plus': '中文写作强(渠道维护中,文案任务先用 deepseek-chat)',
|
|
33
|
-
'glm-4': '智谱通用',
|
|
34
|
-
'moonshot-v1-8k': 'Kimi,短上下文',
|
|
35
|
-
'moonshot-v1-32k': 'Kimi,中等上下文',
|
|
36
|
-
'moonshot-v1-128k': 'Kimi,超长文本(读整本书)',
|
|
37
|
-
'claude-sonnet-4-20250514': '日常主力,平衡性价比',
|
|
38
|
-
'claude-haiku-4-5-20251001': '便宜快速,简单任务',
|
|
39
|
-
'claude-opus-4-8': '最强,复杂任务',
|
|
40
|
-
'claude-3-5-sonnet': 'Claude 3.5 经典款',
|
|
41
|
-
'gpt-4o': 'OpenAI通用旗舰',
|
|
42
|
-
'gpt-4o-mini': 'OpenAI便宜款',
|
|
43
|
-
'gpt-4': 'GPT-4 经典',
|
|
44
|
-
'gpt-3.5-turbo': 'GPT-3.5,老牌便宜',
|
|
45
|
-
'grok-2-latest': 'xAI Grok,最新版',
|
|
46
|
-
'grok-beta': 'xAI Grok 测试版',
|
|
47
|
-
};
|
|
48
|
-
|
|
49
|
-
// 模型分组规则:返回 'cn'(国产)或 'overseas'(海外)
|
|
50
|
-
function classifyModel(id) {
|
|
51
|
-
const domestic = ['deepseek', 'glm', 'moonshot', 'qwen', 'ernie', 'spark', 'hunyuan', 'baichuan', 'yi-', 'step'];
|
|
52
|
-
const lower = id.toLowerCase();
|
|
53
|
-
if (domestic.some((p) => lower.startsWith(p))) return 'cn';
|
|
54
|
-
return 'overseas';
|
|
55
|
-
}
|
|
56
|
-
|
|
57
|
-
function descOf(id) {
|
|
58
|
-
return MODEL_DESC[id] || '';
|
|
59
|
-
}
|
|
60
|
-
|
|
61
|
-
export async function models(subArgs) {
|
|
62
|
-
console.log('╔══════════════════════════════════════════╗');
|
|
63
|
-
console.log('║ AIXX 可用模型 ║');
|
|
64
|
-
console.log('╚══════════════════════════════════════════╝\n');
|
|
65
|
-
|
|
66
|
-
const apiKey = loadApiKey();
|
|
67
|
-
const baseUrl = process.env.AIXX_BASE_URL || DEFAULT_BASE_URL;
|
|
68
|
-
|
|
69
|
-
if (!apiKey) {
|
|
70
|
-
console.error('❌ 未找到AIXX API Key');
|
|
71
|
-
console.error(' 请先运行 npx aixxai install,或设置环境变量 AIXX_API_KEY');
|
|
72
|
-
process.exit(1);
|
|
73
|
-
}
|
|
74
|
-
|
|
75
|
-
// 拉模型列表
|
|
76
|
-
let modelIds = [];
|
|
77
|
-
try {
|
|
78
|
-
const resp = await fetch(`${baseUrl}/models`, {
|
|
79
|
-
headers: { Authorization: `Bearer ${apiKey}` },
|
|
80
|
-
signal: AbortSignal.timeout(FETCH_TIMEOUT),
|
|
81
|
-
});
|
|
82
|
-
if (!resp.ok) {
|
|
83
|
-
if (resp.status === 401) {
|
|
84
|
-
console.error('❌ API Key 无效(401),请重新 install 或检查 key');
|
|
85
|
-
process.exit(1);
|
|
86
|
-
}
|
|
87
|
-
console.error(`❌ 获取模型列表失败: HTTP ${resp.status}`);
|
|
88
|
-
process.exit(1);
|
|
89
|
-
}
|
|
90
|
-
const data = await resp.json();
|
|
91
|
-
const arr = data.data || data.models || [];
|
|
92
|
-
modelIds = arr
|
|
93
|
-
.map((m) => (typeof m === 'string' ? m : m.id))
|
|
94
|
-
.filter(Boolean)
|
|
95
|
-
.sort();
|
|
96
|
-
} catch (err) {
|
|
97
|
-
console.error(`❌ ${friendlyNetErr(err)}`);
|
|
98
|
-
process.exit(1);
|
|
99
|
-
}
|
|
100
|
-
|
|
101
|
-
if (modelIds.length === 0) {
|
|
102
|
-
console.log('⚠️ 后端未返回任何模型,可能是账户没有可用模型权限。');
|
|
103
|
-
return;
|
|
104
|
-
}
|
|
105
|
-
|
|
106
|
-
// 分组
|
|
107
|
-
const cn = modelIds.filter((id) => classifyModel(id) === 'cn');
|
|
108
|
-
const overseas = modelIds.filter((id) => classifyModel(id) === 'overseas');
|
|
109
|
-
|
|
110
|
-
// 国产组
|
|
111
|
-
console.log('🇨🇳 国产模型(便宜):');
|
|
112
|
-
if (cn.length > 0) {
|
|
113
|
-
cn.forEach((id) => {
|
|
114
|
-
const desc = descOf(id);
|
|
115
|
-
console.log(` • ${id}${desc ? ' —— ' + desc : ''}`);
|
|
116
|
-
});
|
|
117
|
-
} else {
|
|
118
|
-
console.log(' (暂无)');
|
|
119
|
-
}
|
|
120
|
-
|
|
121
|
-
// 海外组
|
|
122
|
-
console.log('\n🚀 海外模型(强):');
|
|
123
|
-
if (overseas.length > 0) {
|
|
124
|
-
overseas.forEach((id) => {
|
|
125
|
-
const desc = descOf(id);
|
|
126
|
-
console.log(` • ${id}${desc ? ' —— ' + desc : ''}`);
|
|
127
|
-
});
|
|
128
|
-
} else {
|
|
129
|
-
console.log(' (暂无)');
|
|
130
|
-
}
|
|
131
|
-
|
|
132
|
-
console.log(`\n📊 共 ${modelIds.length} 个模型\n`);
|
|
133
|
-
|
|
134
|
-
console.log('💡 选模型小抄:');
|
|
135
|
-
console.log(' - 最便宜日常任务 → deepseek-chat');
|
|
136
|
-
console.log(' - 写中文文案/邮件 → deepseek-chat(glm渠道维护中)');
|
|
137
|
-
console.log(' - 读超长文档/书籍 → moonshot-v1-128k');
|
|
138
|
-
console.log(' - 复杂推理/代码 → deepseek-reasoner 或 claude-opus-4-8');
|
|
139
|
-
console.log(' - 通用旗舰 → gpt-4o 或 claude-sonnet-4\n');
|
|
140
|
-
}
|
|
1
|
+
/**
|
|
2
|
+
* AIXX CLI - models 命令
|
|
3
|
+
*
|
|
4
|
+
* 列出AIXX支持的所有模型,按"国产/海外"分组展示。
|
|
5
|
+
*
|
|
6
|
+
* 数据来源:GET /v1/models
|
|
7
|
+
* 后端返回的模型列表是动态的,但分组规则是固定的(按模型名前缀分类)。
|
|
8
|
+
*/
|
|
9
|
+
|
|
10
|
+
import { DEFAULT_BASE_URL } from '../../bin/aixx.js';
|
|
11
|
+
import { loadApiKey, maskKey } from '../utils/env.js';
|
|
12
|
+
|
|
13
|
+
// 所有对外请求统一 15 秒超时
|
|
14
|
+
const FETCH_TIMEOUT = 15000;
|
|
15
|
+
// 网络/超时异常统一成友好提示
|
|
16
|
+
function friendlyNetErr(err) {
|
|
17
|
+
return err?.name === 'TimeoutError' || err?.name === 'AbortError'
|
|
18
|
+
? '连接超时,请检查网络'
|
|
19
|
+
: err?.message || String(err);
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
/**
|
|
23
|
+
* apiKey 读取统一走 src/utils/env.js 的 loadApiKey:
|
|
24
|
+
* 环境变量 AIXX_API_KEY → ~/.aixx/config.json → ~/.aixx/account.json
|
|
25
|
+
*/
|
|
26
|
+
|
|
27
|
+
// 给每个模型加一句人话说明,让用户知道怎么选
|
|
28
|
+
const MODEL_DESC = {
|
|
29
|
+
'deepseek-chat': '最便宜,¥0.001/千token,日常首选',
|
|
30
|
+
'deepseek-reasoner': '推理增强(带思考过程)',
|
|
31
|
+
'glm-4-flash': '智谱免费档,速度快',
|
|
32
|
+
'glm-4-plus': '中文写作强(渠道维护中,文案任务先用 deepseek-chat)',
|
|
33
|
+
'glm-4': '智谱通用',
|
|
34
|
+
'moonshot-v1-8k': 'Kimi,短上下文',
|
|
35
|
+
'moonshot-v1-32k': 'Kimi,中等上下文',
|
|
36
|
+
'moonshot-v1-128k': 'Kimi,超长文本(读整本书)',
|
|
37
|
+
'claude-sonnet-4-20250514': '日常主力,平衡性价比',
|
|
38
|
+
'claude-haiku-4-5-20251001': '便宜快速,简单任务',
|
|
39
|
+
'claude-opus-4-8': '最强,复杂任务',
|
|
40
|
+
'claude-3-5-sonnet': 'Claude 3.5 经典款',
|
|
41
|
+
'gpt-4o': 'OpenAI通用旗舰',
|
|
42
|
+
'gpt-4o-mini': 'OpenAI便宜款',
|
|
43
|
+
'gpt-4': 'GPT-4 经典',
|
|
44
|
+
'gpt-3.5-turbo': 'GPT-3.5,老牌便宜',
|
|
45
|
+
'grok-2-latest': 'xAI Grok,最新版',
|
|
46
|
+
'grok-beta': 'xAI Grok 测试版',
|
|
47
|
+
};
|
|
48
|
+
|
|
49
|
+
// 模型分组规则:返回 'cn'(国产)或 'overseas'(海外)
|
|
50
|
+
function classifyModel(id) {
|
|
51
|
+
const domestic = ['deepseek', 'glm', 'moonshot', 'qwen', 'ernie', 'spark', 'hunyuan', 'baichuan', 'yi-', 'step'];
|
|
52
|
+
const lower = id.toLowerCase();
|
|
53
|
+
if (domestic.some((p) => lower.startsWith(p))) return 'cn';
|
|
54
|
+
return 'overseas';
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
function descOf(id) {
|
|
58
|
+
return MODEL_DESC[id] || '';
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
export async function models(subArgs) {
|
|
62
|
+
console.log('╔══════════════════════════════════════════╗');
|
|
63
|
+
console.log('║ AIXX 可用模型 ║');
|
|
64
|
+
console.log('╚══════════════════════════════════════════╝\n');
|
|
65
|
+
|
|
66
|
+
const apiKey = loadApiKey();
|
|
67
|
+
const baseUrl = process.env.AIXX_BASE_URL || DEFAULT_BASE_URL;
|
|
68
|
+
|
|
69
|
+
if (!apiKey) {
|
|
70
|
+
console.error('❌ 未找到AIXX API Key');
|
|
71
|
+
console.error(' 请先运行 npx aixxai install,或设置环境变量 AIXX_API_KEY');
|
|
72
|
+
process.exit(1);
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
// 拉模型列表
|
|
76
|
+
let modelIds = [];
|
|
77
|
+
try {
|
|
78
|
+
const resp = await fetch(`${baseUrl}/models`, {
|
|
79
|
+
headers: { Authorization: `Bearer ${apiKey}` },
|
|
80
|
+
signal: AbortSignal.timeout(FETCH_TIMEOUT),
|
|
81
|
+
});
|
|
82
|
+
if (!resp.ok) {
|
|
83
|
+
if (resp.status === 401) {
|
|
84
|
+
console.error('❌ API Key 无效(401),请重新 install 或检查 key');
|
|
85
|
+
process.exit(1);
|
|
86
|
+
}
|
|
87
|
+
console.error(`❌ 获取模型列表失败: HTTP ${resp.status}`);
|
|
88
|
+
process.exit(1);
|
|
89
|
+
}
|
|
90
|
+
const data = await resp.json();
|
|
91
|
+
const arr = data.data || data.models || [];
|
|
92
|
+
modelIds = arr
|
|
93
|
+
.map((m) => (typeof m === 'string' ? m : m.id))
|
|
94
|
+
.filter(Boolean)
|
|
95
|
+
.sort();
|
|
96
|
+
} catch (err) {
|
|
97
|
+
console.error(`❌ ${friendlyNetErr(err)}`);
|
|
98
|
+
process.exit(1);
|
|
99
|
+
}
|
|
100
|
+
|
|
101
|
+
if (modelIds.length === 0) {
|
|
102
|
+
console.log('⚠️ 后端未返回任何模型,可能是账户没有可用模型权限。');
|
|
103
|
+
return;
|
|
104
|
+
}
|
|
105
|
+
|
|
106
|
+
// 分组
|
|
107
|
+
const cn = modelIds.filter((id) => classifyModel(id) === 'cn');
|
|
108
|
+
const overseas = modelIds.filter((id) => classifyModel(id) === 'overseas');
|
|
109
|
+
|
|
110
|
+
// 国产组
|
|
111
|
+
console.log('🇨🇳 国产模型(便宜):');
|
|
112
|
+
if (cn.length > 0) {
|
|
113
|
+
cn.forEach((id) => {
|
|
114
|
+
const desc = descOf(id);
|
|
115
|
+
console.log(` • ${id}${desc ? ' —— ' + desc : ''}`);
|
|
116
|
+
});
|
|
117
|
+
} else {
|
|
118
|
+
console.log(' (暂无)');
|
|
119
|
+
}
|
|
120
|
+
|
|
121
|
+
// 海外组
|
|
122
|
+
console.log('\n🚀 海外模型(强):');
|
|
123
|
+
if (overseas.length > 0) {
|
|
124
|
+
overseas.forEach((id) => {
|
|
125
|
+
const desc = descOf(id);
|
|
126
|
+
console.log(` • ${id}${desc ? ' —— ' + desc : ''}`);
|
|
127
|
+
});
|
|
128
|
+
} else {
|
|
129
|
+
console.log(' (暂无)');
|
|
130
|
+
}
|
|
131
|
+
|
|
132
|
+
console.log(`\n📊 共 ${modelIds.length} 个模型\n`);
|
|
133
|
+
|
|
134
|
+
console.log('💡 选模型小抄:');
|
|
135
|
+
console.log(' - 最便宜日常任务 → deepseek-chat');
|
|
136
|
+
console.log(' - 写中文文案/邮件 → deepseek-chat(glm渠道维护中)');
|
|
137
|
+
console.log(' - 读超长文档/书籍 → moonshot-v1-128k');
|
|
138
|
+
console.log(' - 复杂推理/代码 → deepseek-reasoner 或 claude-opus-4-8');
|
|
139
|
+
console.log(' - 通用旗舰 → gpt-4o 或 claude-sonnet-4\n');
|
|
140
|
+
}
|
package/src/commands/recharge.js
CHANGED
|
@@ -1,131 +1,131 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* AIXX CLI - recharge 命令
|
|
3
|
-
*
|
|
4
|
-
* 显示充值方式。优先尝试调后端 creem/pay 接口生成在线充值链接;
|
|
5
|
-
* 如果后端不支持或失败,则给出通用引导(联系客服/后台充值)。
|
|
6
|
-
*/
|
|
7
|
-
|
|
8
|
-
import { DEFAULT_BASE_URL } from '../../bin/aixx.js';
|
|
9
|
-
import { loadApiKey, maskKey } from '../utils/env.js';
|
|
10
|
-
|
|
11
|
-
// 所有对外请求统一 15 秒超时
|
|
12
|
-
const FETCH_TIMEOUT = 15000;
|
|
13
|
-
|
|
14
|
-
/**
|
|
15
|
-
* apiKey 读取统一走 src/utils/env.js 的 loadApiKey:
|
|
16
|
-
* 环境变量 AIXX_API_KEY → ~/.aixx/config.json → ~/.aixx/account.json
|
|
17
|
-
*/
|
|
18
|
-
|
|
19
|
-
/**
|
|
20
|
-
* 尝试调后端的 creem 支付接口生成充值链接。
|
|
21
|
-
* New-API 的在线充值常见接口:
|
|
22
|
-
* POST /api/user/creem/pay { amount, ... }
|
|
23
|
-
* 不同版本字段不一,失败就回退到手动引导。
|
|
24
|
-
*/
|
|
25
|
-
async function tryGetCreemLink(apiKey, baseUrl, amount) {
|
|
26
|
-
const apiBase = baseUrl.replace(/\/v1$/, '');
|
|
27
|
-
const candidates = [
|
|
28
|
-
{
|
|
29
|
-
url: `${apiBase}/api/user/creem/pay`,
|
|
30
|
-
body: { amount, currency: 'USD', gateway: 'creem' },
|
|
31
|
-
},
|
|
32
|
-
{
|
|
33
|
-
url: `${apiBase}/api/user/topup`,
|
|
34
|
-
body: { amount, top_up_code: '', payment_method: 'creem' },
|
|
35
|
-
},
|
|
36
|
-
];
|
|
37
|
-
|
|
38
|
-
for (const c of candidates) {
|
|
39
|
-
try {
|
|
40
|
-
const resp = await fetch(c.url, {
|
|
41
|
-
method: 'POST',
|
|
42
|
-
headers: {
|
|
43
|
-
Authorization: `Bearer ${apiKey}`,
|
|
44
|
-
'Content-Type': 'application/json',
|
|
45
|
-
},
|
|
46
|
-
body: JSON.stringify(c.body),
|
|
47
|
-
signal: AbortSignal.timeout(FETCH_TIMEOUT),
|
|
48
|
-
});
|
|
49
|
-
if (!resp.ok) continue;
|
|
50
|
-
const data = await resp.json().catch(() => null);
|
|
51
|
-
if (!data) continue;
|
|
52
|
-
// 多种可能的字段名兜底
|
|
53
|
-
const link =
|
|
54
|
-
data.data?.url ||
|
|
55
|
-
data.data?.payment_url ||
|
|
56
|
-
data.data?.checkout_url ||
|
|
57
|
-
data.url ||
|
|
58
|
-
data.payment_url;
|
|
59
|
-
if (link) return link;
|
|
60
|
-
} catch (e) {
|
|
61
|
-
// 超时单独提示一次(其余错误静默试下一个候选接口)
|
|
62
|
-
if (e?.name === 'TimeoutError' || e?.name === 'AbortError') {
|
|
63
|
-
console.log(' ⚠️ 连接超时,请检查网络');
|
|
64
|
-
}
|
|
65
|
-
}
|
|
66
|
-
}
|
|
67
|
-
return null;
|
|
68
|
-
}
|
|
69
|
-
|
|
70
|
-
export async function recharge(subArgs) {
|
|
71
|
-
console.log('╔══════════════════════════════════════════╗');
|
|
72
|
-
console.log('║ AIXX 充值 ║');
|
|
73
|
-
console.log('╚══════════════════════════════════════════╝\n');
|
|
74
|
-
|
|
75
|
-
const apiKey = loadApiKey();
|
|
76
|
-
const baseUrl = process.env.AIXX_BASE_URL || DEFAULT_BASE_URL;
|
|
77
|
-
|
|
78
|
-
// 从参数取金额,默认 $5(最低)
|
|
79
|
-
let amount = 5;
|
|
80
|
-
if (subArgs[0]) {
|
|
81
|
-
const n = Number(subArgs[0]);
|
|
82
|
-
if (!Number.isNaN(n) && n > 0) amount = n;
|
|
83
|
-
}
|
|
84
|
-
|
|
85
|
-
if (!apiKey) {
|
|
86
|
-
console.log('⚠️ 未检测到AIXX API Key,以下为通用充值方式:\n');
|
|
87
|
-
console.log('充值方式:');
|
|
88
|
-
console.log(' 信用卡 / ApplePay:登录 AIXX 后台 → 充值 → Creem');
|
|
89
|
-
console.log(' USDT 加密货币:联系客服或后台提交');
|
|
90
|
-
console.log(`\n 最低充值 $5`);
|
|
91
|
-
console.log(`\n🌐 后台地址:${baseUrl.replace(/\/v1$/, '')}`);
|
|
92
|
-
return;
|
|
93
|
-
}
|
|
94
|
-
|
|
95
|
-
console.log(`使用Key: ${maskKey(apiKey)}`);
|
|
96
|
-
console.log(`充值金额:$${amount}\n`);
|
|
97
|
-
|
|
98
|
-
// 尝试生成在线支付链接
|
|
99
|
-
console.log('🔄 正在生成在线充值链接...');
|
|
100
|
-
const link = await tryGetCreemLink(apiKey, baseUrl, amount);
|
|
101
|
-
|
|
102
|
-
console.log('\n────────────────────────────────────');
|
|
103
|
-
console.log('💳 充值方式:');
|
|
104
|
-
console.log('────────────────────────────────────');
|
|
105
|
-
|
|
106
|
-
if (link) {
|
|
107
|
-
console.log('\n ① 信用卡 / ApplePay(推荐,即时到账):');
|
|
108
|
-
console.log(` ${link}`);
|
|
109
|
-
console.log('\n 复制链接到浏览器打开即可支付。');
|
|
110
|
-
} else {
|
|
111
|
-
console.log('\n ① 信用卡 / ApplePay:');
|
|
112
|
-
console.log(' 自动生成链接失败,请直接登录后台充值:');
|
|
113
|
-
console.log(` ${baseUrl.replace(/\/v1$/, '')} → 充值`);
|
|
114
|
-
}
|
|
115
|
-
|
|
116
|
-
console.log('\n ② USDT 加密货币:');
|
|
117
|
-
console.log(' 联系 AIXX 客服,或后台提交 USDT 充值订单');
|
|
118
|
-
console.log(' (后续会支持自动生成钱包地址)');
|
|
119
|
-
|
|
120
|
-
console.log('\n ③ 微信/支付宝:');
|
|
121
|
-
console.log(' 联系 AIXX 客服走人工充值');
|
|
122
|
-
|
|
123
|
-
console.log('\n────────────────────────────────────');
|
|
124
|
-
console.log(`最低充值 $5(约 ¥${(amount * 7).toFixed(0)})`);
|
|
125
|
-
console.log(`充值后额度即时到账,可直接使用。\n`);
|
|
126
|
-
|
|
127
|
-
console.log('💡 充值提示:');
|
|
128
|
-
console.log(' - 充 $5 用 deepseek-chat 能聊 5 万次以上');
|
|
129
|
-
console.log(' - 充 $20 够用 Claude/GPT 跑一个月');
|
|
130
|
-
console.log(' - 推荐码注册的用户充值后推荐人有分润\n');
|
|
131
|
-
}
|
|
1
|
+
/**
|
|
2
|
+
* AIXX CLI - recharge 命令
|
|
3
|
+
*
|
|
4
|
+
* 显示充值方式。优先尝试调后端 creem/pay 接口生成在线充值链接;
|
|
5
|
+
* 如果后端不支持或失败,则给出通用引导(联系客服/后台充值)。
|
|
6
|
+
*/
|
|
7
|
+
|
|
8
|
+
import { DEFAULT_BASE_URL } from '../../bin/aixx.js';
|
|
9
|
+
import { loadApiKey, maskKey } from '../utils/env.js';
|
|
10
|
+
|
|
11
|
+
// 所有对外请求统一 15 秒超时
|
|
12
|
+
const FETCH_TIMEOUT = 15000;
|
|
13
|
+
|
|
14
|
+
/**
|
|
15
|
+
* apiKey 读取统一走 src/utils/env.js 的 loadApiKey:
|
|
16
|
+
* 环境变量 AIXX_API_KEY → ~/.aixx/config.json → ~/.aixx/account.json
|
|
17
|
+
*/
|
|
18
|
+
|
|
19
|
+
/**
|
|
20
|
+
* 尝试调后端的 creem 支付接口生成充值链接。
|
|
21
|
+
* New-API 的在线充值常见接口:
|
|
22
|
+
* POST /api/user/creem/pay { amount, ... }
|
|
23
|
+
* 不同版本字段不一,失败就回退到手动引导。
|
|
24
|
+
*/
|
|
25
|
+
async function tryGetCreemLink(apiKey, baseUrl, amount) {
|
|
26
|
+
const apiBase = baseUrl.replace(/\/v1$/, '');
|
|
27
|
+
const candidates = [
|
|
28
|
+
{
|
|
29
|
+
url: `${apiBase}/api/user/creem/pay`,
|
|
30
|
+
body: { amount, currency: 'USD', gateway: 'creem' },
|
|
31
|
+
},
|
|
32
|
+
{
|
|
33
|
+
url: `${apiBase}/api/user/topup`,
|
|
34
|
+
body: { amount, top_up_code: '', payment_method: 'creem' },
|
|
35
|
+
},
|
|
36
|
+
];
|
|
37
|
+
|
|
38
|
+
for (const c of candidates) {
|
|
39
|
+
try {
|
|
40
|
+
const resp = await fetch(c.url, {
|
|
41
|
+
method: 'POST',
|
|
42
|
+
headers: {
|
|
43
|
+
Authorization: `Bearer ${apiKey}`,
|
|
44
|
+
'Content-Type': 'application/json',
|
|
45
|
+
},
|
|
46
|
+
body: JSON.stringify(c.body),
|
|
47
|
+
signal: AbortSignal.timeout(FETCH_TIMEOUT),
|
|
48
|
+
});
|
|
49
|
+
if (!resp.ok) continue;
|
|
50
|
+
const data = await resp.json().catch(() => null);
|
|
51
|
+
if (!data) continue;
|
|
52
|
+
// 多种可能的字段名兜底
|
|
53
|
+
const link =
|
|
54
|
+
data.data?.url ||
|
|
55
|
+
data.data?.payment_url ||
|
|
56
|
+
data.data?.checkout_url ||
|
|
57
|
+
data.url ||
|
|
58
|
+
data.payment_url;
|
|
59
|
+
if (link) return link;
|
|
60
|
+
} catch (e) {
|
|
61
|
+
// 超时单独提示一次(其余错误静默试下一个候选接口)
|
|
62
|
+
if (e?.name === 'TimeoutError' || e?.name === 'AbortError') {
|
|
63
|
+
console.log(' ⚠️ 连接超时,请检查网络');
|
|
64
|
+
}
|
|
65
|
+
}
|
|
66
|
+
}
|
|
67
|
+
return null;
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
export async function recharge(subArgs) {
|
|
71
|
+
console.log('╔══════════════════════════════════════════╗');
|
|
72
|
+
console.log('║ AIXX 充值 ║');
|
|
73
|
+
console.log('╚══════════════════════════════════════════╝\n');
|
|
74
|
+
|
|
75
|
+
const apiKey = loadApiKey();
|
|
76
|
+
const baseUrl = process.env.AIXX_BASE_URL || DEFAULT_BASE_URL;
|
|
77
|
+
|
|
78
|
+
// 从参数取金额,默认 $5(最低)
|
|
79
|
+
let amount = 5;
|
|
80
|
+
if (subArgs[0]) {
|
|
81
|
+
const n = Number(subArgs[0]);
|
|
82
|
+
if (!Number.isNaN(n) && n > 0) amount = n;
|
|
83
|
+
}
|
|
84
|
+
|
|
85
|
+
if (!apiKey) {
|
|
86
|
+
console.log('⚠️ 未检测到AIXX API Key,以下为通用充值方式:\n');
|
|
87
|
+
console.log('充值方式:');
|
|
88
|
+
console.log(' 信用卡 / ApplePay:登录 AIXX 后台 → 充值 → Creem');
|
|
89
|
+
console.log(' USDT 加密货币:联系客服或后台提交');
|
|
90
|
+
console.log(`\n 最低充值 $5`);
|
|
91
|
+
console.log(`\n🌐 后台地址:${baseUrl.replace(/\/v1$/, '')}`);
|
|
92
|
+
return;
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
console.log(`使用Key: ${maskKey(apiKey)}`);
|
|
96
|
+
console.log(`充值金额:$${amount}\n`);
|
|
97
|
+
|
|
98
|
+
// 尝试生成在线支付链接
|
|
99
|
+
console.log('🔄 正在生成在线充值链接...');
|
|
100
|
+
const link = await tryGetCreemLink(apiKey, baseUrl, amount);
|
|
101
|
+
|
|
102
|
+
console.log('\n────────────────────────────────────');
|
|
103
|
+
console.log('💳 充值方式:');
|
|
104
|
+
console.log('────────────────────────────────────');
|
|
105
|
+
|
|
106
|
+
if (link) {
|
|
107
|
+
console.log('\n ① 信用卡 / ApplePay(推荐,即时到账):');
|
|
108
|
+
console.log(` ${link}`);
|
|
109
|
+
console.log('\n 复制链接到浏览器打开即可支付。');
|
|
110
|
+
} else {
|
|
111
|
+
console.log('\n ① 信用卡 / ApplePay:');
|
|
112
|
+
console.log(' 自动生成链接失败,请直接登录后台充值:');
|
|
113
|
+
console.log(` ${baseUrl.replace(/\/v1$/, '')} → 充值`);
|
|
114
|
+
}
|
|
115
|
+
|
|
116
|
+
console.log('\n ② USDT 加密货币:');
|
|
117
|
+
console.log(' 联系 AIXX 客服,或后台提交 USDT 充值订单');
|
|
118
|
+
console.log(' (后续会支持自动生成钱包地址)');
|
|
119
|
+
|
|
120
|
+
console.log('\n ③ 微信/支付宝:');
|
|
121
|
+
console.log(' 联系 AIXX 客服走人工充值');
|
|
122
|
+
|
|
123
|
+
console.log('\n────────────────────────────────────');
|
|
124
|
+
console.log(`最低充值 $5(约 ¥${(amount * 7).toFixed(0)})`);
|
|
125
|
+
console.log(`充值后额度即时到账,可直接使用。\n`);
|
|
126
|
+
|
|
127
|
+
console.log('💡 充值提示:');
|
|
128
|
+
console.log(' - 充 $5 用 deepseek-chat 能聊 5 万次以上');
|
|
129
|
+
console.log(' - 充 $20 够用 Claude/GPT 跑一个月');
|
|
130
|
+
console.log(' - 推荐码注册的用户充值后推荐人有分润\n');
|
|
131
|
+
}
|