badgr-cli 1.0.28 ā 1.0.29
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/package.json +1 -1
- package/src/commands/logs.js +57 -5
- package/src/commands/run.js +12 -8
package/package.json
CHANGED
package/src/commands/logs.js
CHANGED
|
@@ -1,6 +1,12 @@
|
|
|
1
1
|
import { findDeployment, listDeployments } from '../store.js';
|
|
2
2
|
import { requireApiKey } from '../config.js';
|
|
3
|
-
import { getDeploymentLogs } from '../api.js';
|
|
3
|
+
import { getDeploymentLogs, callApi } from '../api.js';
|
|
4
|
+
|
|
5
|
+
const TERMINAL_STATUSES = new Set(['succeeded', 'completed', 'failed', 'stopped', 'terminated']);
|
|
6
|
+
const FOLLOW_POLL_MS = 3000;
|
|
7
|
+
|
|
8
|
+
// Lines that carry structured metadata shown elsewhere (status bar in `badgr run`).
|
|
9
|
+
const LOG_META_RE = /^\[dep-[^\]]+\] (status|gpu|region|endpoint|cost|receipt|provider_status|uptime)=/;
|
|
4
10
|
|
|
5
11
|
export async function logsCommand(config, args, chalk) {
|
|
6
12
|
const idOrName = args.find(a => !a.startsWith('--'));
|
|
@@ -26,13 +32,18 @@ export async function logsCommand(config, args, chalk) {
|
|
|
26
32
|
|
|
27
33
|
console.log(chalk.bold(`\nš Logs: ${localDep?.name ?? deploymentId}\n`));
|
|
28
34
|
|
|
35
|
+
// Fetch and print initial batch of logs.
|
|
36
|
+
const seen = new Set();
|
|
29
37
|
try {
|
|
30
38
|
const data = await getDeploymentLogs(config, deploymentId);
|
|
31
39
|
const lines = data?.logs ?? [];
|
|
32
|
-
if (lines.length === 0) {
|
|
40
|
+
if (lines.length === 0 && !follow) {
|
|
33
41
|
console.log(chalk.dim(' No log lines available yet.\n'));
|
|
34
42
|
} else {
|
|
35
|
-
|
|
43
|
+
for (const line of lines) {
|
|
44
|
+
seen.add(line);
|
|
45
|
+
if (!LOG_META_RE.test(line)) console.log(` ${chalk.dim(line)}`);
|
|
46
|
+
}
|
|
36
47
|
}
|
|
37
48
|
} catch (err) {
|
|
38
49
|
console.log(chalk.yellow(` Could not fetch logs: ${err.message}`));
|
|
@@ -40,10 +51,51 @@ export async function logsCommand(config, args, chalk) {
|
|
|
40
51
|
console.log(chalk.dim(`\n GPU: ${localDep.gpu} Type: ${localDep.type}`));
|
|
41
52
|
console.log(chalk.dim(` Endpoint: ${localDep.endpointUrl}`));
|
|
42
53
|
}
|
|
54
|
+
if (!follow) { console.log(); return; }
|
|
43
55
|
}
|
|
44
56
|
|
|
45
|
-
if (follow) {
|
|
46
|
-
|
|
57
|
+
if (!follow) { console.log(); return; }
|
|
58
|
+
|
|
59
|
+
// --follow: poll until the deployment reaches a terminal state.
|
|
60
|
+
console.log(chalk.dim(' (following ā Ctrl+C to stop)\n'));
|
|
61
|
+
|
|
62
|
+
let stopping = false;
|
|
63
|
+
process.once('SIGINT', () => { stopping = true; });
|
|
64
|
+
|
|
65
|
+
while (!stopping) {
|
|
66
|
+
await new Promise(r => setTimeout(r, FOLLOW_POLL_MS));
|
|
67
|
+
if (stopping) break;
|
|
68
|
+
|
|
69
|
+
let status = null;
|
|
70
|
+
try {
|
|
71
|
+
const dep = await callApi(`/deployments/${deploymentId}`, {
|
|
72
|
+
apiKey: config.apiKey,
|
|
73
|
+
baseUrl: config.baseUrl,
|
|
74
|
+
});
|
|
75
|
+
status = dep?.status ?? null;
|
|
76
|
+
} catch {
|
|
77
|
+
// network blip ā keep following
|
|
78
|
+
}
|
|
79
|
+
|
|
80
|
+
try {
|
|
81
|
+
const data = await getDeploymentLogs(config, deploymentId);
|
|
82
|
+
for (const line of (data?.logs ?? [])) {
|
|
83
|
+
if (seen.has(line)) continue;
|
|
84
|
+
seen.add(line);
|
|
85
|
+
if (!LOG_META_RE.test(line)) {
|
|
86
|
+
const isErr = /^error\b/i.test(line) || /Error response from daemon/i.test(line);
|
|
87
|
+
console.log(` ${isErr ? chalk.red(line) : chalk.dim(line)}`);
|
|
88
|
+
}
|
|
89
|
+
}
|
|
90
|
+
} catch {
|
|
91
|
+
// logs endpoint temporarily unavailable
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
if (status && TERMINAL_STATUSES.has(status)) {
|
|
95
|
+
console.log(chalk.dim(`\n Job ${status}. No more logs.\n`));
|
|
96
|
+
break;
|
|
97
|
+
}
|
|
47
98
|
}
|
|
99
|
+
|
|
48
100
|
console.log();
|
|
49
101
|
}
|
package/src/commands/run.js
CHANGED
|
@@ -450,12 +450,15 @@ export async function runCommand(config, args, chalk) {
|
|
|
450
450
|
|
|
451
451
|
const rcptId = dep.receipt_id || generateReceiptId();
|
|
452
452
|
addReceipt({
|
|
453
|
-
receiptId:
|
|
454
|
-
action:
|
|
455
|
-
deploymentId:
|
|
456
|
-
gpu:
|
|
457
|
-
|
|
458
|
-
|
|
453
|
+
receiptId: rcptId,
|
|
454
|
+
action: 'badgr run',
|
|
455
|
+
deploymentId: dep.deployment_id,
|
|
456
|
+
gpu: dep.gpu_type,
|
|
457
|
+
providerRoute: dep.provider ?? null,
|
|
458
|
+
maxCost: maxCost ?? null,
|
|
459
|
+
maxRuntime: flags.maxRuntime ?? null,
|
|
460
|
+
status: dep.status,
|
|
461
|
+
createdAt: new Date().toISOString(),
|
|
459
462
|
});
|
|
460
463
|
|
|
461
464
|
console.log();
|
|
@@ -506,7 +509,7 @@ export async function runCommand(config, args, chalk) {
|
|
|
506
509
|
}
|
|
507
510
|
const runtimeMs = Date.now() - attachStart;
|
|
508
511
|
const finalCost = ratePerHour * (runtimeMs / 3_600_000);
|
|
509
|
-
updateReceipt(rcptId, { status: reason, runtimeSeconds: Math.round(runtimeMs / 1000), finalCost });
|
|
512
|
+
updateReceipt(rcptId, { status: reason, teardownStatus: 'terminated', runtimeSeconds: Math.round(runtimeMs / 1000), finalCost });
|
|
510
513
|
console.log(chalk.dim(` Runtime: ${fmtRuntime(runtimeMs)} ⢠Est. cost: $${finalCost.toFixed(4)}`));
|
|
511
514
|
console.log(chalk.dim(' Job stopped. Billing ended.\n'));
|
|
512
515
|
process.exit(reason === 'interrupted' ? 0 : 1);
|
|
@@ -525,11 +528,12 @@ export async function runCommand(config, args, chalk) {
|
|
|
525
528
|
|
|
526
529
|
const finalCost = ratePerHour * (runtimeMs / 3_600_000);
|
|
527
530
|
updateReceipt(rcptId, {
|
|
528
|
-
status:
|
|
531
|
+
status: finalStatus,
|
|
529
532
|
exitCode,
|
|
530
533
|
runtimeSeconds: Math.round(runtimeMs / 1000),
|
|
531
534
|
finalCost,
|
|
532
535
|
failureType,
|
|
536
|
+
teardownStatus: (finalStatus === 'completed' || finalStatus === 'succeeded') ? 'terminated' : 'failed',
|
|
533
537
|
});
|
|
534
538
|
|
|
535
539
|
console.log(` ${chalk.bold('Runtime:')} ${fmtRuntime(runtimeMs)}`);
|