claudmax 1.0.2 → 1.0.5
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/index.js +149 -73
- package/package.json +1 -1
package/index.js
CHANGED
|
@@ -398,7 +398,8 @@ function installMCPServer() {
|
|
|
398
398
|
console.log(` ${CHECK} ${C.green(MCP_PKG + ' installed successfully.')}`);
|
|
399
399
|
return true;
|
|
400
400
|
} catch (err) {
|
|
401
|
-
|
|
401
|
+
const errMsg = String(err.stderr || err.message || '');
|
|
402
|
+
console.log(` ${WARN} Could not install ${MCP_PKG}: ${C.dim(errMsg.trim())}`);
|
|
402
403
|
console.log(` ${INFO} Install manually later: ${C.bold('npm install -g ' + MCP_PKG)}`);
|
|
403
404
|
return false;
|
|
404
405
|
}
|
|
@@ -407,14 +408,116 @@ function installMCPServer() {
|
|
|
407
408
|
// ── Banner ────────────────────────────────────────────────────────────────────
|
|
408
409
|
function printBanner() {
|
|
409
410
|
console.log('');
|
|
410
|
-
console.log(C.magenta('\u2554' + '\u2550'.repeat(
|
|
411
|
-
console.log(C.magenta('\u2551') + C.bold('
|
|
411
|
+
console.log(C.magenta('\u2554' + '\u2550'.repeat(44) + '\u2557'));
|
|
412
|
+
console.log(C.magenta('\u2551') + C.bold(' \u26A1 ClaudMax Setup ') + C.magenta('\u2551'));
|
|
413
|
+
console.log(C.magenta('\u255A' + '\u2550'.repeat(44) + '\u255D'));
|
|
414
|
+
console.log('');
|
|
415
|
+
}
|
|
416
|
+
|
|
417
|
+
// ── CLI argument parsing ────────────────────────────────────────────────────────
|
|
418
|
+
const args = process.argv.slice(2);
|
|
419
|
+
const command = args[0];
|
|
420
|
+
|
|
421
|
+
// ── Status command ─────────────────────────────────────────────────────────────
|
|
422
|
+
async function showStatus() {
|
|
423
|
+
const config = readJson(CONFIG_FILE);
|
|
424
|
+
if (!config || !config.apiKey) {
|
|
425
|
+
console.log(`\n${WARN} No API key configured. Run ${C.bold('npx claudmax')} first.\n`);
|
|
426
|
+
process.exit(1);
|
|
427
|
+
}
|
|
428
|
+
|
|
429
|
+
console.log(`\n${C.magenta('\u2554' + '\u2550'.repeat(48) + '\u2557')}`);
|
|
430
|
+
console.log(C.magenta('\u2551') + C.bold(' \u2726 ClaudMax Status \u2726 ') + C.magenta('\u2551'));
|
|
412
431
|
console.log(C.magenta('\u255A' + '\u2550'.repeat(48) + '\u255D'));
|
|
413
432
|
console.log('');
|
|
433
|
+
|
|
434
|
+
// Fetch key status
|
|
435
|
+
const body = JSON.stringify({ apiKey: config.apiKey });
|
|
436
|
+
const postData = Buffer.from(body);
|
|
437
|
+
|
|
438
|
+
const options = {
|
|
439
|
+
hostname: 'api.claudmax.pro',
|
|
440
|
+
port: 443,
|
|
441
|
+
path: '/v1/key-status',
|
|
442
|
+
method: 'POST',
|
|
443
|
+
headers: {
|
|
444
|
+
'Content-Type': 'application/json',
|
|
445
|
+
'Content-Length': postData.length,
|
|
446
|
+
'User-Agent': 'ClaudMax-CLI/1.0.0',
|
|
447
|
+
},
|
|
448
|
+
timeout: 15000,
|
|
449
|
+
};
|
|
450
|
+
|
|
451
|
+
return new Promise((resolve) => {
|
|
452
|
+
const req = https.request(options, (res) => {
|
|
453
|
+
let data = '';
|
|
454
|
+
res.on('data', (chunk) => { data += chunk; });
|
|
455
|
+
res.on('end', () => {
|
|
456
|
+
try {
|
|
457
|
+
const json = JSON.parse(data);
|
|
458
|
+
if (res.statusCode === 200) {
|
|
459
|
+
const pct = json.tokensLimit > 0 ? Math.min(100, (json.tokensUsed / json.tokensLimit) * 100) : 0;
|
|
460
|
+
const tierColors = { free: C.dim('Gray'), '5x': C.cyan('Blue'), '20x': C.magenta('Purple'), unlimited: C.green('Gold') };
|
|
461
|
+
console.log(` ${CHECK} ${C.green('API Key is active')}`);
|
|
462
|
+
console.log(` ${INFO} Name: ${C.bold(json.name || 'ClaudMax Key')}`);
|
|
463
|
+
console.log(` ${INFO} Prefix: ${C.magenta(json.prefix)}••••••`);
|
|
464
|
+
console.log(` ${INFO} Tier: ${tierColors[json.tier] || C.dim('Free')} (${C.bold(json.tier?.toUpperCase() || 'FREE')})`);
|
|
465
|
+
console.log(` ${INFO} Status: ${json.isActive ? C.green('Active') : C.red('Inactive')}`);
|
|
466
|
+
console.log('');
|
|
467
|
+
console.log(` ${C.bold('Usage (5h window):')}`);
|
|
468
|
+
const barLen = 30;
|
|
469
|
+
const filled = Math.round((pct / 100) * barLen);
|
|
470
|
+
const bar = C.purple('\u2588'.repeat(filled)) + C.dim('\u2591'.repeat(barLen - filled));
|
|
471
|
+
console.log(` ${bar} ${C.dim(`${pct.toFixed(1)}%`)}`);
|
|
472
|
+
console.log(` ${INFO} Requests: ${C.cyan(json.requestsUsed?.toLocaleString() || 0)} / ${C.cyan(json.requestsLimit?.toLocaleString() || 'N/A')}`);
|
|
473
|
+
console.log(` ${INFO} Tokens: ${C.cyan((json.tokensUsed || 0).toLocaleString())} / ${C.cyan((json.tokensLimit || 0).toLocaleString())}`);
|
|
474
|
+
console.log('');
|
|
475
|
+
if (json.windowResetAt) {
|
|
476
|
+
const reset = new Date(json.windowResetAt);
|
|
477
|
+
console.log(` ${INFO} Resets: ${C.dim(reset.toLocaleString())}`);
|
|
478
|
+
}
|
|
479
|
+
} else {
|
|
480
|
+
console.log(` ${CROSS} ${C.red('Failed to fetch status: ' + (json.error || `HTTP ${res.statusCode}`))}`);
|
|
481
|
+
}
|
|
482
|
+
} catch {
|
|
483
|
+
console.log(` ${CROSS} ${C.red('Failed to parse response')}`);
|
|
484
|
+
}
|
|
485
|
+
console.log('');
|
|
486
|
+
resolve();
|
|
487
|
+
});
|
|
488
|
+
});
|
|
489
|
+
req.on('error', (err) => {
|
|
490
|
+
console.log(` ${WARN} ${C.yellow('Network error: ' + err.message)}`);
|
|
491
|
+
console.log('');
|
|
492
|
+
resolve();
|
|
493
|
+
});
|
|
494
|
+
req.on('timeout', () => { req.destroy(); console.log(` ${CROSS} ${C.red('Request timed out')}\n`); resolve(); });
|
|
495
|
+
req.write(postData);
|
|
496
|
+
req.end();
|
|
497
|
+
});
|
|
498
|
+
}
|
|
499
|
+
|
|
500
|
+
// ── Help ───────────────────────────────────────────────────────────────────────
|
|
501
|
+
function showHelp() {
|
|
502
|
+
console.log(`\n${C.bold('ClaudMax CLI')} — Configure Claude Code and other IDEs to use ClaudMax API.\n`);
|
|
503
|
+
console.log(` ${C.cyan('npx claudmax')} ${C.dim('Launch the interactive setup wizard')}`);
|
|
504
|
+
console.log(` ${C.cyan('npx claudmax status')} ${C.dim('Check your API key usage and limits')}`);
|
|
505
|
+
console.log(` ${C.cyan('npx claudmax --help')} ${C.dim('Show this help message')}`);
|
|
506
|
+
console.log('');
|
|
414
507
|
}
|
|
415
508
|
|
|
416
509
|
// ── Main ──────────────────────────────────────────────────────────────────────
|
|
417
510
|
async function main() {
|
|
511
|
+
if (command === 'status') {
|
|
512
|
+
await showStatus();
|
|
513
|
+
return;
|
|
514
|
+
}
|
|
515
|
+
if (command === '--help' || command === '-h') {
|
|
516
|
+
showHelp();
|
|
517
|
+
return;
|
|
518
|
+
}
|
|
519
|
+
|
|
520
|
+
// Default: interactive setup wizard
|
|
418
521
|
const rl = createRL();
|
|
419
522
|
|
|
420
523
|
printBanner();
|
|
@@ -450,31 +553,8 @@ async function main() {
|
|
|
450
553
|
}
|
|
451
554
|
}
|
|
452
555
|
|
|
453
|
-
|
|
454
|
-
|
|
455
|
-
console.log(`\n${C.yellow('Git installation failed. You can install it manually.')}`);
|
|
456
|
-
} else {
|
|
457
|
-
gitOk = isCommandAvailable('git');
|
|
458
|
-
}
|
|
459
|
-
}
|
|
460
|
-
|
|
461
|
-
if (nodeOk && !claudeOk) {
|
|
462
|
-
const installClaude = await ask(rl, `\n${WARN} Claude CLI not found. Install it? ${C.bold('[Y/n]: ')}`);
|
|
463
|
-
if (!installClaude || installClaude.toLowerCase() === 'y' || installClaude.toLowerCase() === 'yes') {
|
|
464
|
-
if (!installDep('Claude CLI', installClaudeCLI)) {
|
|
465
|
-
console.log(`\n${C.yellow('Claude CLI installation failed. You can install it with: npm i -g @anthropic-ai/claude-code')}`);
|
|
466
|
-
} else {
|
|
467
|
-
claudeOk = isCommandAvailable('claude');
|
|
468
|
-
}
|
|
469
|
-
}
|
|
470
|
-
}
|
|
471
|
-
|
|
472
|
-
console.log('');
|
|
473
|
-
|
|
474
|
-
// ── Step 2: API key prompt ───────────────────────────────────────────────
|
|
475
|
-
console.log(C.bold('Step 2: Enter your ClaudMax API key\n'));
|
|
476
|
-
console.log(` ${INFO} Get your API key from the ${C.bold('ClaudMax Admin Dashboard')}: ${C.cyan('https://claudmax.pro/admin/dashboard')}`);
|
|
477
|
-
console.log('');
|
|
556
|
+
// ── Step 1: API key prompt ───────────────────────────────────────────────
|
|
557
|
+
console.log(C.bold('\nStep 1: Enter your ClaudMax API key\n'));
|
|
478
558
|
|
|
479
559
|
let apiKey = '';
|
|
480
560
|
while (!apiKey.trim()) {
|
|
@@ -486,42 +566,14 @@ async function main() {
|
|
|
486
566
|
apiKey = apiKey.trim();
|
|
487
567
|
console.log('');
|
|
488
568
|
|
|
489
|
-
// ── Step
|
|
490
|
-
console.log(C.bold('Step
|
|
491
|
-
const result = await verifyConnection(apiKey);
|
|
492
|
-
|
|
493
|
-
if (result.ok) {
|
|
494
|
-
const data = result.data;
|
|
495
|
-
if (result.status === 401) {
|
|
496
|
-
console.log(` ${CROSS} ${C.red('Invalid API key. Please check and try again.')}`);
|
|
497
|
-
console.log(` ${INFO} ${C.dim(data.error || 'Authentication failed')}`);
|
|
498
|
-
rl.close();
|
|
499
|
-
process.exit(1);
|
|
500
|
-
} else {
|
|
501
|
-
console.log(` ${CHECK} ${C.green('API key is valid!')}`);
|
|
502
|
-
const tier = (data.tier || 'free').toUpperCase();
|
|
503
|
-
const limit = data.requestsLimit?.toLocaleString() || 'N/A';
|
|
504
|
-
const tokenLimit = data.tokensLimit ? (data.tokensLimit >= 1e9 ? 'Unlimited' : (data.tokensLimit / 1e6).toFixed(0) + 'M tokens/5h') : 'N/A';
|
|
505
|
-
console.log(` ${INFO} Plan: ${C.magenta(tier)} | Requests: ${C.cyan(limit)} | Tokens: ${C.cyan(tokenLimit)}`);
|
|
506
|
-
}
|
|
507
|
-
} else {
|
|
508
|
-
console.log(` ${WARN} ${C.yellow('Could not verify API key (network error). Continuing with setup anyway...')}`);
|
|
509
|
-
console.log(` ${INFO} ${C.dim(result.error || 'Connection failed')}`);
|
|
510
|
-
}
|
|
511
|
-
|
|
512
|
-
// ── Step 4: Configure system ──────────────────────────────────────────────
|
|
513
|
-
console.log('');
|
|
514
|
-
const profile = configureSystem(apiKey);
|
|
515
|
-
|
|
516
|
-
// ── Step 5: IDE selection ─────────────────────────────────────────────────
|
|
517
|
-
console.log('');
|
|
518
|
-
console.log(C.bold('Step 5: Select IDEs to configure\n'));
|
|
569
|
+
// ── Step 2: IDE selection ─────────────────────────────────────────────────
|
|
570
|
+
console.log(C.bold('Step 2: Select IDEs to configure\n'));
|
|
519
571
|
|
|
520
572
|
const IDES = [
|
|
521
|
-
{ id: 1, name: 'Claude Code CLI',
|
|
573
|
+
{ id: 1, name: 'Claude Code (CLI)', shortName: 'Claude Code', configure: configureClaudeCLI },
|
|
522
574
|
{ id: 2, name: 'VS Code (Claude Extension)', shortName: 'VS Code', configure: configureVSCodeClaude },
|
|
523
|
-
{ id: 3, name: 'Cursor',
|
|
524
|
-
{ id: 4, name: 'Windsurf',
|
|
575
|
+
{ id: 3, name: 'Cursor', shortName: 'Cursor', configure: configureCursor },
|
|
576
|
+
{ id: 4, name: 'Windsurf', shortName: 'Windsurf', configure: configureWindsurf },
|
|
525
577
|
{ id: 5, name: 'Cline (VS Code Extension)', shortName: 'Cline', configure: configureCline },
|
|
526
578
|
{ id: 6, name: 'Roo Code (VS Code Extension)', shortName: 'Roo Code', configure: configureRooCode },
|
|
527
579
|
];
|
|
@@ -530,7 +582,7 @@ async function main() {
|
|
|
530
582
|
console.log(` ${C.purple('[' + ide.id + ']')} ${ide.name}`);
|
|
531
583
|
}
|
|
532
584
|
console.log('');
|
|
533
|
-
console.log(` ${C.dim("Enter numbers separated by spaces (e.g. 1 3 4), " + C.bold("'a'") + " for all
|
|
585
|
+
console.log(` ${C.dim("Enter numbers separated by spaces (e.g. 1 3 4), or " + C.bold("'a'") + " for all")}`);
|
|
534
586
|
|
|
535
587
|
const choice = await ask(rl, ` ${C.bold('Your choice')}: `);
|
|
536
588
|
let selectedIds = [];
|
|
@@ -541,42 +593,66 @@ async function main() {
|
|
|
541
593
|
selectedIds = choice.trim().split(/[\s,]+/).map(Number).filter((n) => n >= 1 && n <= IDES.length);
|
|
542
594
|
}
|
|
543
595
|
|
|
596
|
+
console.log('');
|
|
597
|
+
|
|
598
|
+
// ── Configure selected IDEs ──────────────────────────────────────────────
|
|
544
599
|
if (selectedIds.length > 0) {
|
|
545
600
|
const selectedIDEs = IDES.filter((ide) => selectedIds.includes(ide.id));
|
|
546
601
|
for (const ide of selectedIDEs) {
|
|
547
602
|
try {
|
|
548
603
|
ide.configure(apiKey);
|
|
549
604
|
} catch (err) {
|
|
550
|
-
console.log(` ${CROSS} Failed to configure ${ide.name}: ${err.message}`);
|
|
605
|
+
console.log(` ${CROSS} Failed to configure ${ide.name}: ${String(err.message || err)}`);
|
|
551
606
|
}
|
|
552
607
|
}
|
|
553
608
|
} else {
|
|
554
|
-
console.log(
|
|
609
|
+
console.log(` ${WARN} ${C.yellow('No IDEs selected. Skipping IDE configuration.')}`);
|
|
555
610
|
}
|
|
556
611
|
|
|
557
|
-
// ──
|
|
612
|
+
// ── Install MCP server ───────────────────────────────────────────────────
|
|
558
613
|
installMCPServer();
|
|
559
614
|
|
|
615
|
+
// ── Verify connection ─────────────────────────────────────────────────────
|
|
616
|
+
console.log(`\n${ARROW} ${C.bold('Verifying connection to ClaudMax API...')}`);
|
|
617
|
+
const result = await verifyConnection(apiKey);
|
|
618
|
+
|
|
619
|
+
if (result.ok) {
|
|
620
|
+
const data = result.data;
|
|
621
|
+
if (result.status === 401) {
|
|
622
|
+
console.log(` ${CROSS} ${C.red('Invalid API key. Please check and try again.')}`);
|
|
623
|
+
console.log(` ${INFO} ${C.dim(data.error || 'Authentication failed')}`);
|
|
624
|
+
rl.close();
|
|
625
|
+
process.exit(1);
|
|
626
|
+
} else {
|
|
627
|
+
console.log(` ${CHECK} ${C.green('Connected — API key is valid.')}`);
|
|
628
|
+
const tier = (data.tier || 'free').toUpperCase();
|
|
629
|
+
const limit = data.requestsLimit?.toLocaleString() || 'N/A';
|
|
630
|
+
const tokenLimit = data.tokensLimit ? (data.tokensLimit >= 1e9 ? 'Unlimited' : (data.tokensLimit / 1e6).toFixed(0) + 'M tokens/5h') : 'N/A';
|
|
631
|
+
console.log(` ${INFO} Plan: ${C.magenta(tier)} | Requests: ${C.cyan(limit)} | Tokens: ${C.cyan(tokenLimit)}`);
|
|
632
|
+
}
|
|
633
|
+
} else {
|
|
634
|
+
console.log(` ${WARN} ${C.yellow('Could not verify API key (network error).')}`);
|
|
635
|
+
console.log(` ${INFO} ${C.dim(result.error || 'Connection failed')}`);
|
|
636
|
+
}
|
|
637
|
+
|
|
560
638
|
// ── Summary ───────────────────────────────────────────────────────────────
|
|
561
639
|
console.log('');
|
|
562
|
-
console.log(C.magenta('\u2554' + '\u2550'.repeat(
|
|
563
|
-
console.log(C.magenta('\u2551') + C.bold(' \u2713 Setup complete!
|
|
564
|
-
console.log(C.magenta('\u2551') + C.green('
|
|
565
|
-
console.log(C.magenta('\u255A' + '\u2550'.repeat(
|
|
640
|
+
console.log(C.magenta('\u2554' + '\u2550'.repeat(44) + '\u2557'));
|
|
641
|
+
console.log(C.magenta('\u2551') + C.bold(' \u2713 Setup complete! ') + C.magenta('\u2551'));
|
|
642
|
+
console.log(C.magenta('\u2551') + C.green(' Restart your IDE(s) to apply. ') + C.magenta('\u2551'));
|
|
643
|
+
console.log(C.magenta('\u255A' + '\u2550'.repeat(44) + '\u255D'));
|
|
566
644
|
console.log('');
|
|
567
645
|
console.log(` ${INFO} ${C.bold('Next steps:')}`);
|
|
568
|
-
console.log(` 1. ${C.dim('
|
|
646
|
+
console.log(` 1. ${C.dim('Restart your IDE(s) to apply.')}`);
|
|
569
647
|
console.log(` 2. ${C.dim('Verify with:')} ${C.bold('claude --version')}`);
|
|
570
648
|
console.log(` 3. ${C.dim('Start chatting:')} ${C.bold('claude')}`);
|
|
571
649
|
console.log(` 4. ${C.dim('Check usage:')} ${C.bold('npx claudmax status')}`);
|
|
572
650
|
console.log('');
|
|
573
|
-
console.log(` ${INFO} Config saved at: ${C.magenta(CONFIG_FILE)}`);
|
|
574
|
-
console.log('');
|
|
575
651
|
|
|
576
652
|
rl.close();
|
|
577
653
|
}
|
|
578
654
|
|
|
579
655
|
main().catch((err) => {
|
|
580
|
-
console.error('\n' + C.red('\u2717 Fatal error: ' + err.message));
|
|
656
|
+
console.error('\n' + C.red('\u2717 Fatal error: ' + String(err.message || err)));
|
|
581
657
|
process.exit(1);
|
|
582
658
|
});
|
package/package.json
CHANGED