@integrity-labs/agt-cli 0.9.3 → 0.9.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/dist/bin/agt.js +2 -2
- package/mcp/index.js +33 -15
- package/package.json +1 -1
package/dist/bin/agt.js
CHANGED
|
@@ -3411,7 +3411,7 @@ async function acpxCloseCommand(agent2, _opts, cmd) {
|
|
|
3411
3411
|
import { execSync } from "child_process";
|
|
3412
3412
|
import chalk19 from "chalk";
|
|
3413
3413
|
import ora15 from "ora";
|
|
3414
|
-
var cliVersion = true ? "0.9.
|
|
3414
|
+
var cliVersion = true ? "0.9.4" : "dev";
|
|
3415
3415
|
async function fetchLatestVersion() {
|
|
3416
3416
|
const host2 = AGT_HOST;
|
|
3417
3417
|
if (!host2) return null;
|
|
@@ -3527,7 +3527,7 @@ async function checkForUpdateOnStartup() {
|
|
|
3527
3527
|
}
|
|
3528
3528
|
|
|
3529
3529
|
// src/bin/agt.ts
|
|
3530
|
-
var cliVersion2 = true ? "0.9.
|
|
3530
|
+
var cliVersion2 = true ? "0.9.4" : "dev";
|
|
3531
3531
|
var program = new Command();
|
|
3532
3532
|
program.name("agt").description("Augmented CLI \u2014 agent provisioning and management").version(cliVersion2).option("--json", "Emit machine-readable JSON output (suppress spinners and colors)").option("--skip-update-check", "Skip the automatic update check on startup");
|
|
3533
3533
|
program.hook("preAction", (thisCommand) => {
|
package/mcp/index.js
CHANGED
|
@@ -14,30 +14,42 @@ if (!AGT_HOST || !AGT_AGENT_ID || (!AGT_TOKEN && !AGT_API_KEY)) {
|
|
|
14
14
|
process.exit(1);
|
|
15
15
|
}
|
|
16
16
|
// ── Token refresh ───────────────────────────────────────────────────────────
|
|
17
|
-
|
|
17
|
+
// If no initial token was provided, force an immediate exchange on first call
|
|
18
|
+
let tokenExpiresAt = AGT_TOKEN ? Date.now() + 50 * 60_000 : 0;
|
|
19
|
+
let exchangeInFlight = null;
|
|
20
|
+
async function refreshToken() {
|
|
21
|
+
const res = await fetch(`${AGT_HOST}/host/exchange`, {
|
|
22
|
+
method: 'POST',
|
|
23
|
+
headers: { 'Content-Type': 'application/json' },
|
|
24
|
+
body: JSON.stringify({ host_key: AGT_API_KEY }),
|
|
25
|
+
});
|
|
26
|
+
if (!res.ok) {
|
|
27
|
+
const text = await res.text().catch(() => res.statusText);
|
|
28
|
+
throw new Error(`Token exchange failed: ${res.status} ${text}`);
|
|
29
|
+
}
|
|
30
|
+
const data = (await res.json());
|
|
31
|
+
AGT_TOKEN = data.token;
|
|
32
|
+
tokenExpiresAt = new Date(data.expires_at).getTime();
|
|
33
|
+
return AGT_TOKEN;
|
|
34
|
+
}
|
|
18
35
|
async function getToken() {
|
|
19
|
-
// If we have an API key and the token is expiring soon (within 5 min), refresh
|
|
20
|
-
if (AGT_API_KEY && Date.now() > tokenExpiresAt - 5 * 60_000) {
|
|
36
|
+
// If we have an API key and the token is missing or expiring soon (within 5 min), refresh
|
|
37
|
+
if (AGT_API_KEY && (!AGT_TOKEN || Date.now() > tokenExpiresAt - 5 * 60_000)) {
|
|
38
|
+
// Coalesce concurrent refresh calls
|
|
39
|
+
if (!exchangeInFlight) {
|
|
40
|
+
exchangeInFlight = refreshToken().finally(() => { exchangeInFlight = null; });
|
|
41
|
+
}
|
|
21
42
|
try {
|
|
22
|
-
|
|
23
|
-
method: 'POST',
|
|
24
|
-
headers: { 'Content-Type': 'application/json' },
|
|
25
|
-
body: JSON.stringify({ host_key: AGT_API_KEY }),
|
|
26
|
-
});
|
|
27
|
-
if (res.ok) {
|
|
28
|
-
const data = (await res.json());
|
|
29
|
-
AGT_TOKEN = data.token;
|
|
30
|
-
tokenExpiresAt = new Date(data.expires_at).getTime();
|
|
31
|
-
}
|
|
43
|
+
return await exchangeInFlight;
|
|
32
44
|
}
|
|
33
45
|
catch {
|
|
34
|
-
//
|
|
46
|
+
// Fall through to return existing token (may be stale but avoids crash)
|
|
35
47
|
}
|
|
36
48
|
}
|
|
37
49
|
return AGT_TOKEN;
|
|
38
50
|
}
|
|
39
51
|
// ── API client ──────────────────────────────────────────────────────────────
|
|
40
|
-
async function apiPost(path, body) {
|
|
52
|
+
async function apiPost(path, body, retried = false) {
|
|
41
53
|
const controller = new AbortController();
|
|
42
54
|
const timeout = setTimeout(() => controller.abort(), 15_000);
|
|
43
55
|
const token = await getToken();
|
|
@@ -51,6 +63,12 @@ async function apiPost(path, body) {
|
|
|
51
63
|
body: JSON.stringify(body),
|
|
52
64
|
signal: controller.signal,
|
|
53
65
|
});
|
|
66
|
+
// Retry once on 401 — token may have expired between cache check and server verification
|
|
67
|
+
if (res.status === 401 && AGT_API_KEY && !retried) {
|
|
68
|
+
clearTimeout(timeout);
|
|
69
|
+
tokenExpiresAt = 0; // force re-exchange
|
|
70
|
+
return apiPost(path, body, true);
|
|
71
|
+
}
|
|
54
72
|
if (!res.ok) {
|
|
55
73
|
const text = await res.text().catch(() => res.statusText);
|
|
56
74
|
throw new Error(`API ${path} returned ${res.status}: ${text}`);
|