@agent-team-foundation/first-tree-hub 0.6.3 → 0.7.0
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/{bootstrap-DNL1cEwv.mjs → bootstrap-CRDR6NwE.mjs} +1 -1
- package/dist/cli/index.mjs +35 -11
- package/dist/{core-B10jgThe.mjs → core-4nvleGlC.mjs} +567 -158
- package/dist/drizzle/0022_session_events.sql +32 -0
- package/dist/drizzle/meta/_journal.json +7 -0
- package/dist/{feishu-BoMJHlOv.mjs → feishu-CJ08ntOD.mjs} +54 -6
- package/dist/index.mjs +3 -3
- package/dist/web/assets/index-30C-bada.js +333 -0
- package/dist/web/assets/index-COlVuDVR.css +1 -0
- package/dist/web/index.html +9 -2
- package/package.json +1 -1
- package/dist/web/assets/index-CTl4pHIL.css +0 -1
- package/dist/web/assets/index-CnLpaSBg.js +0 -308
|
@@ -550,7 +550,7 @@ function isTokenExpired(token) {
|
|
|
550
550
|
if (parts.length !== 3 || !parts[1]) return true;
|
|
551
551
|
const payload = JSON.parse(Buffer.from(parts[1], "base64url").toString());
|
|
552
552
|
if (!payload.exp) return false;
|
|
553
|
-
return payload.exp * 1e3 < Date.now()
|
|
553
|
+
return payload.exp * 1e3 < Date.now() + 3e4;
|
|
554
554
|
} catch {
|
|
555
555
|
return true;
|
|
556
556
|
}
|
package/dist/cli/index.mjs
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
|
-
import { C as setConfigValue, S as serverConfigSchema, _ as loadAgents, b as resetConfigMeta, c as saveCredentials, f as agentConfigSchema, g as initConfig, h as getConfigValue, l as DEFAULT_CONFIG_DIR, n as ensureFreshAccessToken, o as resolveServerUrl, p as clientConfigSchema, r as ensureFreshAdminToken, s as saveAgentConfig, u as DEFAULT_DATA_DIR, v as readConfigFile, y as resetConfig } from "../bootstrap-
|
|
3
|
-
import { A as SdkError, D as createOwner, E as ClientRuntime, M as cleanWorkspaces, T as stopPostgres, _ as checkServerHealth, a as formatCheckReport, b as printResults, c as onboardCreate, d as checkAgentConfigs, f as checkClientConfig, g as checkServerConfig, h as checkNodeVersion, i as promptMissingFields, j as SessionRegistry, k as FirstTreeHubSDK, l as saveOnboardState, m as checkDocker, n as isInteractive, o as loadOnboardState, p as checkDatabase, r as promptAddAgent, s as onboardCheck, t as startServer, u as runMigrations, v as checkServerReachable, y as checkWebSocket } from "../core-
|
|
4
|
-
import { n as bindFeishuUser, t as bindFeishuBot } from "../feishu-
|
|
2
|
+
import { C as setConfigValue, S as serverConfigSchema, _ as loadAgents, b as resetConfigMeta, c as saveCredentials, f as agentConfigSchema, g as initConfig, h as getConfigValue, l as DEFAULT_CONFIG_DIR, n as ensureFreshAccessToken, o as resolveServerUrl, p as clientConfigSchema, r as ensureFreshAdminToken, s as saveAgentConfig, u as DEFAULT_DATA_DIR, v as readConfigFile, y as resetConfig } from "../bootstrap-CRDR6NwE.mjs";
|
|
3
|
+
import { A as SdkError, D as createOwner, E as ClientRuntime, M as cleanWorkspaces, T as stopPostgres, _ as checkServerHealth, a as formatCheckReport, b as printResults, c as onboardCreate, d as checkAgentConfigs, f as checkClientConfig, g as checkServerConfig, h as checkNodeVersion, i as promptMissingFields, j as SessionRegistry, k as FirstTreeHubSDK, l as saveOnboardState, m as checkDocker, n as isInteractive, o as loadOnboardState, p as checkDatabase, r as promptAddAgent, s as onboardCheck, t as startServer, u as runMigrations, v as checkServerReachable, y as checkWebSocket } from "../core-4nvleGlC.mjs";
|
|
4
|
+
import { n as bindFeishuUser, t as bindFeishuBot } from "../feishu-CJ08ntOD.mjs";
|
|
5
5
|
import { createRequire } from "node:module";
|
|
6
6
|
import { Command } from "commander";
|
|
7
7
|
import { existsSync, mkdirSync, readFileSync, readdirSync, rmSync } from "node:fs";
|
|
@@ -439,7 +439,31 @@ function registerAgentCommands(program) {
|
|
|
439
439
|
}
|
|
440
440
|
process.stderr.write(` ${totalRemoved} workspace(s) cleaned.\n`);
|
|
441
441
|
});
|
|
442
|
-
const bind = agent.command("bind").description("Bind external IM
|
|
442
|
+
const bind = agent.command("bind").description("Bind an agent to a client machine or external IM account");
|
|
443
|
+
bind.command("client <agentName>").description("Bind an unbound agent to a client machine (first-time bind only — ID is immutable once set)").requiredOption("--client-id <id>", "Client (machine) ID — must be owned by you. Run `first-tree-hub client connect` on that machine first.").option("--server <url>", "Hub server URL").action(async (agentName, options) => {
|
|
444
|
+
try {
|
|
445
|
+
const serverUrl = resolveServerUrl(options.server);
|
|
446
|
+
const accessToken = await ensureFreshAccessToken();
|
|
447
|
+
const target = await resolveAgent(serverUrl, accessToken, agentName);
|
|
448
|
+
const patchRes = await fetch(`${serverUrl}/api/v1/admin/agents/${target.uuid}`, {
|
|
449
|
+
method: "PATCH",
|
|
450
|
+
headers: {
|
|
451
|
+
Authorization: `Bearer ${accessToken}`,
|
|
452
|
+
"Content-Type": "application/json"
|
|
453
|
+
},
|
|
454
|
+
body: JSON.stringify({ clientId: options.clientId }),
|
|
455
|
+
signal: AbortSignal.timeout(1e4)
|
|
456
|
+
});
|
|
457
|
+
if (!patchRes.ok) fail("BIND_CLIENT_ERROR", (await patchRes.json().catch(() => ({}))).error ?? `Bind failed (HTTP ${patchRes.status})`, 1);
|
|
458
|
+
process.stderr.write(` \u2713 Bound "${target.name ?? target.uuid}" to client ${options.clientId}.\n`);
|
|
459
|
+
success({
|
|
460
|
+
agentId: target.uuid,
|
|
461
|
+
clientId: options.clientId
|
|
462
|
+
});
|
|
463
|
+
} catch (error) {
|
|
464
|
+
fail("BIND_CLIENT_ERROR", error instanceof Error ? error.message : String(error));
|
|
465
|
+
}
|
|
466
|
+
});
|
|
443
467
|
bind.command("bot").description("Bind a Feishu bot to this agent (self-service)").requiredOption("--platform <platform>", "Platform: feishu").requiredOption("--app-id <id>", "Feishu bot App ID").requiredOption("--app-secret <secret>", "Feishu bot App Secret").option("--agent <name>", "Local agent alias (default: first configured)").option("--server <url>", "Hub server URL").action(async (options) => {
|
|
444
468
|
try {
|
|
445
469
|
if (options.platform !== "feishu") fail("UNSUPPORTED_PLATFORM", `Platform "${options.platform}" is not supported. Use "feishu".`);
|
|
@@ -899,21 +923,21 @@ function registerClientCommands(program) {
|
|
|
899
923
|
process.stderr.write(" No agents directory found.\n");
|
|
900
924
|
}
|
|
901
925
|
});
|
|
902
|
-
client.command("hub-list").description("List
|
|
926
|
+
client.command("hub-list").description("List clients on the Hub server").option("--server <url>", "Hub server URL").action(async (options) => {
|
|
903
927
|
try {
|
|
904
928
|
const serverUrl = resolveServerUrl(options.server);
|
|
905
929
|
const token = await ensureFreshAccessToken();
|
|
906
|
-
const response = await fetch(`${serverUrl}/api/v1/
|
|
930
|
+
const response = await fetch(`${serverUrl}/api/v1/clients`, {
|
|
907
931
|
headers: { Authorization: `Bearer ${token}` },
|
|
908
932
|
signal: AbortSignal.timeout(1e4)
|
|
909
933
|
});
|
|
910
934
|
if (!response.ok) fail("FETCH_ERROR", `Server returned ${response.status}`, 1);
|
|
911
935
|
const clients = await response.json();
|
|
912
936
|
if (clients.length === 0) {
|
|
913
|
-
process.stderr.write(" No
|
|
937
|
+
process.stderr.write(" No clients.\n");
|
|
914
938
|
return;
|
|
915
939
|
}
|
|
916
|
-
process.stderr.write(`\n
|
|
940
|
+
process.stderr.write(`\n Clients: ${clients.length}\n\n`);
|
|
917
941
|
const header = ` ${"CLIENT".padEnd(20)} ${"HOST".padEnd(25)} ${"AGENTS".padEnd(8)} CONNECTED`;
|
|
918
942
|
process.stderr.write(`${header}\n`);
|
|
919
943
|
process.stderr.write(` ${"─".repeat(header.length - 2)}\n`);
|
|
@@ -930,7 +954,7 @@ function registerClientCommands(program) {
|
|
|
930
954
|
try {
|
|
931
955
|
const serverUrl = resolveServerUrl(options.server);
|
|
932
956
|
const token = await ensureFreshAccessToken();
|
|
933
|
-
const response = await fetch(`${serverUrl}/api/v1/
|
|
957
|
+
const response = await fetch(`${serverUrl}/api/v1/clients/${clientId}/disconnect`, {
|
|
934
958
|
method: "POST",
|
|
935
959
|
headers: { Authorization: `Bearer ${token}` },
|
|
936
960
|
signal: AbortSignal.timeout(1e4)
|
|
@@ -1049,13 +1073,13 @@ function isSecretField(schema, dotPath) {
|
|
|
1049
1073
|
//#region src/commands/onboard.ts
|
|
1050
1074
|
async function promptMissing(args) {
|
|
1051
1075
|
if (!args.server) try {
|
|
1052
|
-
const { resolveServerUrl } = await import("../bootstrap-
|
|
1076
|
+
const { resolveServerUrl } = await import("../bootstrap-CRDR6NwE.mjs").then((n) => n.t);
|
|
1053
1077
|
resolveServerUrl();
|
|
1054
1078
|
} catch {
|
|
1055
1079
|
args.server = await input({ message: "Hub server URL:" });
|
|
1056
1080
|
saveOnboardState(args);
|
|
1057
1081
|
}
|
|
1058
|
-
const { loadCredentials } = await import("../bootstrap-
|
|
1082
|
+
const { loadCredentials } = await import("../bootstrap-CRDR6NwE.mjs").then((n) => n.t);
|
|
1059
1083
|
if (!loadCredentials()) throw new Error("No saved credentials. Run `first-tree-hub client connect <server-url>` before onboarding.");
|
|
1060
1084
|
if (!args.id) {
|
|
1061
1085
|
args.id = await input({ message: "Agent ID:" });
|