agentbnb 3.1.2 → 3.1.3
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/{chunk-P35546JW.js → chunk-7OACGAFD.js} +1 -1
- package/dist/{chunk-KTHJ5F3X.js → chunk-IZZ4FP45.js} +14 -7
- package/dist/{chunk-QVV2P3FN.js → chunk-QHQPXO67.js} +57 -0
- package/dist/{chunk-SVEZBIGE.js → chunk-QSPWE5AE.js} +3 -58
- package/dist/cli/index.js +58 -28
- package/dist/{conduct-5XKKALNX.js → conduct-IEQ567ET.js} +3 -3
- package/dist/{conductor-mode-6MIVMFBC.js → conductor-mode-IO45PWMI.js} +3 -3
- package/dist/{execute-HM25IOG7.js → execute-SWWEHV2K.js} +2 -2
- package/dist/index.js +31 -20
- package/package.json +1 -1
|
@@ -5,8 +5,9 @@ import {
|
|
|
5
5
|
getBalance,
|
|
6
6
|
holdEscrow,
|
|
7
7
|
releaseEscrow,
|
|
8
|
-
settleEscrow
|
|
9
|
-
|
|
8
|
+
settleEscrow,
|
|
9
|
+
signEscrowReceipt
|
|
10
|
+
} from "./chunk-QHQPXO67.js";
|
|
10
11
|
import {
|
|
11
12
|
AgentBnBError
|
|
12
13
|
} from "./chunk-XA63SD4T.js";
|
|
@@ -150,7 +151,7 @@ function filterCards(db, filters) {
|
|
|
150
151
|
// src/gateway/client.ts
|
|
151
152
|
import { randomUUID as randomUUID2 } from "crypto";
|
|
152
153
|
async function requestCapability(opts) {
|
|
153
|
-
const { gatewayUrl, token, cardId, params = {}, timeoutMs = 3e4, escrowReceipt } = opts;
|
|
154
|
+
const { gatewayUrl, token, cardId, params = {}, timeoutMs = 3e4, escrowReceipt, identity } = opts;
|
|
154
155
|
const id = randomUUID2();
|
|
155
156
|
const payload = {
|
|
156
157
|
jsonrpc: "2.0",
|
|
@@ -162,16 +163,22 @@ async function requestCapability(opts) {
|
|
|
162
163
|
...escrowReceipt ? { escrow_receipt: escrowReceipt } : {}
|
|
163
164
|
}
|
|
164
165
|
};
|
|
166
|
+
const headers = { "Content-Type": "application/json" };
|
|
167
|
+
if (identity) {
|
|
168
|
+
const signature = signEscrowReceipt(payload, identity.privateKey);
|
|
169
|
+
headers["X-Agent-Id"] = identity.agentId;
|
|
170
|
+
headers["X-Agent-Public-Key"] = identity.publicKey;
|
|
171
|
+
headers["X-Agent-Signature"] = signature;
|
|
172
|
+
} else if (token) {
|
|
173
|
+
headers["Authorization"] = `Bearer ${token}`;
|
|
174
|
+
}
|
|
165
175
|
const controller = new AbortController();
|
|
166
176
|
const timer = setTimeout(() => controller.abort(), timeoutMs);
|
|
167
177
|
let response;
|
|
168
178
|
try {
|
|
169
179
|
response = await fetch(`${gatewayUrl}/rpc`, {
|
|
170
180
|
method: "POST",
|
|
171
|
-
headers
|
|
172
|
-
"Content-Type": "application/json",
|
|
173
|
-
Authorization: `Bearer ${token}`
|
|
174
|
-
},
|
|
181
|
+
headers,
|
|
175
182
|
body: JSON.stringify(payload),
|
|
176
183
|
signal: controller.signal
|
|
177
184
|
});
|
|
@@ -2,6 +2,58 @@ import {
|
|
|
2
2
|
AgentBnBError
|
|
3
3
|
} from "./chunk-XA63SD4T.js";
|
|
4
4
|
|
|
5
|
+
// src/credit/signing.ts
|
|
6
|
+
import { generateKeyPairSync, sign, verify, createPublicKey, createPrivateKey } from "crypto";
|
|
7
|
+
import { writeFileSync, readFileSync, existsSync, chmodSync } from "fs";
|
|
8
|
+
import { join } from "path";
|
|
9
|
+
function generateKeyPair() {
|
|
10
|
+
const { publicKey, privateKey } = generateKeyPairSync("ed25519", {
|
|
11
|
+
publicKeyEncoding: { type: "spki", format: "der" },
|
|
12
|
+
privateKeyEncoding: { type: "pkcs8", format: "der" }
|
|
13
|
+
});
|
|
14
|
+
return {
|
|
15
|
+
publicKey: Buffer.from(publicKey),
|
|
16
|
+
privateKey: Buffer.from(privateKey)
|
|
17
|
+
};
|
|
18
|
+
}
|
|
19
|
+
function saveKeyPair(configDir, keys) {
|
|
20
|
+
const privatePath = join(configDir, "private.key");
|
|
21
|
+
const publicPath = join(configDir, "public.key");
|
|
22
|
+
writeFileSync(privatePath, keys.privateKey);
|
|
23
|
+
chmodSync(privatePath, 384);
|
|
24
|
+
writeFileSync(publicPath, keys.publicKey);
|
|
25
|
+
}
|
|
26
|
+
function loadKeyPair(configDir) {
|
|
27
|
+
const privatePath = join(configDir, "private.key");
|
|
28
|
+
const publicPath = join(configDir, "public.key");
|
|
29
|
+
if (!existsSync(privatePath) || !existsSync(publicPath)) {
|
|
30
|
+
throw new AgentBnBError("Keypair not found. Run `agentbnb init` to generate one.", "KEYPAIR_NOT_FOUND");
|
|
31
|
+
}
|
|
32
|
+
return {
|
|
33
|
+
publicKey: readFileSync(publicPath),
|
|
34
|
+
privateKey: readFileSync(privatePath)
|
|
35
|
+
};
|
|
36
|
+
}
|
|
37
|
+
function canonicalJson(data) {
|
|
38
|
+
return JSON.stringify(data, Object.keys(data).sort());
|
|
39
|
+
}
|
|
40
|
+
function signEscrowReceipt(data, privateKey) {
|
|
41
|
+
const message = Buffer.from(canonicalJson(data), "utf-8");
|
|
42
|
+
const keyObject = createPrivateKey({ key: privateKey, format: "der", type: "pkcs8" });
|
|
43
|
+
const signature = sign(null, message, keyObject);
|
|
44
|
+
return signature.toString("base64url");
|
|
45
|
+
}
|
|
46
|
+
function verifyEscrowReceipt(data, signature, publicKey) {
|
|
47
|
+
try {
|
|
48
|
+
const message = Buffer.from(canonicalJson(data), "utf-8");
|
|
49
|
+
const keyObject = createPublicKey({ key: publicKey, format: "der", type: "spki" });
|
|
50
|
+
const sigBuffer = Buffer.from(signature, "base64url");
|
|
51
|
+
return verify(null, message, keyObject, sigBuffer);
|
|
52
|
+
} catch {
|
|
53
|
+
return false;
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
|
|
5
57
|
// src/credit/escrow.ts
|
|
6
58
|
import { randomUUID } from "crypto";
|
|
7
59
|
function holdEscrow(db, owner, amount, cardId) {
|
|
@@ -180,6 +232,11 @@ function recordEarning(db, owner, amount, _cardId, receiptNonce) {
|
|
|
180
232
|
}
|
|
181
233
|
|
|
182
234
|
export {
|
|
235
|
+
generateKeyPair,
|
|
236
|
+
saveKeyPair,
|
|
237
|
+
loadKeyPair,
|
|
238
|
+
signEscrowReceipt,
|
|
239
|
+
verifyEscrowReceipt,
|
|
183
240
|
holdEscrow,
|
|
184
241
|
settleEscrow,
|
|
185
242
|
releaseEscrow,
|
|
@@ -9,8 +9,9 @@ import {
|
|
|
9
9
|
holdEscrow,
|
|
10
10
|
recordEarning,
|
|
11
11
|
releaseEscrow,
|
|
12
|
-
settleEscrow
|
|
13
|
-
|
|
12
|
+
settleEscrow,
|
|
13
|
+
verifyEscrowReceipt
|
|
14
|
+
} from "./chunk-QHQPXO67.js";
|
|
14
15
|
import {
|
|
15
16
|
AgentBnBError
|
|
16
17
|
} from "./chunk-XA63SD4T.js";
|
|
@@ -18,58 +19,6 @@ import {
|
|
|
18
19
|
// src/gateway/execute.ts
|
|
19
20
|
import { randomUUID } from "crypto";
|
|
20
21
|
|
|
21
|
-
// src/credit/signing.ts
|
|
22
|
-
import { generateKeyPairSync, sign, verify, createPublicKey, createPrivateKey } from "crypto";
|
|
23
|
-
import { writeFileSync, readFileSync, existsSync, chmodSync } from "fs";
|
|
24
|
-
import { join } from "path";
|
|
25
|
-
function generateKeyPair() {
|
|
26
|
-
const { publicKey, privateKey } = generateKeyPairSync("ed25519", {
|
|
27
|
-
publicKeyEncoding: { type: "spki", format: "der" },
|
|
28
|
-
privateKeyEncoding: { type: "pkcs8", format: "der" }
|
|
29
|
-
});
|
|
30
|
-
return {
|
|
31
|
-
publicKey: Buffer.from(publicKey),
|
|
32
|
-
privateKey: Buffer.from(privateKey)
|
|
33
|
-
};
|
|
34
|
-
}
|
|
35
|
-
function saveKeyPair(configDir, keys) {
|
|
36
|
-
const privatePath = join(configDir, "private.key");
|
|
37
|
-
const publicPath = join(configDir, "public.key");
|
|
38
|
-
writeFileSync(privatePath, keys.privateKey);
|
|
39
|
-
chmodSync(privatePath, 384);
|
|
40
|
-
writeFileSync(publicPath, keys.publicKey);
|
|
41
|
-
}
|
|
42
|
-
function loadKeyPair(configDir) {
|
|
43
|
-
const privatePath = join(configDir, "private.key");
|
|
44
|
-
const publicPath = join(configDir, "public.key");
|
|
45
|
-
if (!existsSync(privatePath) || !existsSync(publicPath)) {
|
|
46
|
-
throw new AgentBnBError("Keypair not found. Run `agentbnb init` to generate one.", "KEYPAIR_NOT_FOUND");
|
|
47
|
-
}
|
|
48
|
-
return {
|
|
49
|
-
publicKey: readFileSync(publicPath),
|
|
50
|
-
privateKey: readFileSync(privatePath)
|
|
51
|
-
};
|
|
52
|
-
}
|
|
53
|
-
function canonicalJson(data) {
|
|
54
|
-
return JSON.stringify(data, Object.keys(data).sort());
|
|
55
|
-
}
|
|
56
|
-
function signEscrowReceipt(data, privateKey) {
|
|
57
|
-
const message = Buffer.from(canonicalJson(data), "utf-8");
|
|
58
|
-
const keyObject = createPrivateKey({ key: privateKey, format: "der", type: "pkcs8" });
|
|
59
|
-
const signature = sign(null, message, keyObject);
|
|
60
|
-
return signature.toString("base64url");
|
|
61
|
-
}
|
|
62
|
-
function verifyEscrowReceipt(data, signature, publicKey) {
|
|
63
|
-
try {
|
|
64
|
-
const message = Buffer.from(canonicalJson(data), "utf-8");
|
|
65
|
-
const keyObject = createPublicKey({ key: publicKey, format: "der", type: "spki" });
|
|
66
|
-
const sigBuffer = Buffer.from(signature, "base64url");
|
|
67
|
-
return verify(null, message, keyObject, sigBuffer);
|
|
68
|
-
} catch {
|
|
69
|
-
return false;
|
|
70
|
-
}
|
|
71
|
-
}
|
|
72
|
-
|
|
73
22
|
// src/credit/settlement.ts
|
|
74
23
|
function settleProviderEarning(providerDb, providerOwner, receipt) {
|
|
75
24
|
recordEarning(
|
|
@@ -247,10 +196,6 @@ async function executeCapabilityRequest(opts) {
|
|
|
247
196
|
}
|
|
248
197
|
|
|
249
198
|
export {
|
|
250
|
-
generateKeyPair,
|
|
251
|
-
saveKeyPair,
|
|
252
|
-
loadKeyPair,
|
|
253
|
-
signEscrowReceipt,
|
|
254
199
|
settleRequesterEscrow,
|
|
255
200
|
releaseRequesterEscrow,
|
|
256
201
|
executeCapabilityRequest
|
package/dist/cli/index.js
CHANGED
|
@@ -1,13 +1,9 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
import {
|
|
3
3
|
executeCapabilityRequest,
|
|
4
|
-
generateKeyPair,
|
|
5
|
-
loadKeyPair,
|
|
6
4
|
releaseRequesterEscrow,
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
signEscrowReceipt
|
|
10
|
-
} from "../chunk-SVEZBIGE.js";
|
|
5
|
+
settleRequesterEscrow
|
|
6
|
+
} from "../chunk-QSPWE5AE.js";
|
|
11
7
|
import {
|
|
12
8
|
RelayMessageSchema
|
|
13
9
|
} from "../chunk-3Y36WQDV.js";
|
|
@@ -24,7 +20,7 @@ import {
|
|
|
24
20
|
requestCapability,
|
|
25
21
|
resolvePendingRequest,
|
|
26
22
|
searchCards
|
|
27
|
-
} from "../chunk-
|
|
23
|
+
} from "../chunk-IZZ4FP45.js";
|
|
28
24
|
import {
|
|
29
25
|
findPeer,
|
|
30
26
|
getConfigDir,
|
|
@@ -49,12 +45,17 @@ import {
|
|
|
49
45
|
} from "../chunk-UOGDK2S2.js";
|
|
50
46
|
import {
|
|
51
47
|
bootstrapAgent,
|
|
48
|
+
generateKeyPair,
|
|
52
49
|
getBalance,
|
|
53
50
|
getTransactions,
|
|
54
51
|
holdEscrow,
|
|
52
|
+
loadKeyPair,
|
|
55
53
|
openCreditDb,
|
|
56
|
-
releaseEscrow
|
|
57
|
-
|
|
54
|
+
releaseEscrow,
|
|
55
|
+
saveKeyPair,
|
|
56
|
+
signEscrowReceipt,
|
|
57
|
+
verifyEscrowReceipt
|
|
58
|
+
} from "../chunk-QHQPXO67.js";
|
|
58
59
|
import {
|
|
59
60
|
AgentBnBError,
|
|
60
61
|
AnyCardSchema,
|
|
@@ -1525,7 +1526,7 @@ var AgentRuntime = class {
|
|
|
1525
1526
|
}
|
|
1526
1527
|
const modes = /* @__PURE__ */ new Map();
|
|
1527
1528
|
if (this.conductorEnabled) {
|
|
1528
|
-
const { ConductorMode } = await import("../conductor-mode-
|
|
1529
|
+
const { ConductorMode } = await import("../conductor-mode-IO45PWMI.js");
|
|
1529
1530
|
const { registerConductorCard, CONDUCTOR_OWNER } = await import("../card-IE5UV5QX.js");
|
|
1530
1531
|
const { loadPeers: loadPeers2 } = await import("../peers-G36URZYB.js");
|
|
1531
1532
|
registerConductorCard(this.registryDb);
|
|
@@ -1648,22 +1649,27 @@ function createGatewayServer(opts) {
|
|
|
1648
1649
|
fastify.addHook("onRequest", async (request, reply) => {
|
|
1649
1650
|
if (request.method === "GET" && request.url === "/health") return;
|
|
1650
1651
|
const auth = request.headers.authorization;
|
|
1651
|
-
if (
|
|
1652
|
-
|
|
1653
|
-
|
|
1654
|
-
|
|
1655
|
-
|
|
1656
|
-
|
|
1657
|
-
|
|
1658
|
-
|
|
1659
|
-
|
|
1660
|
-
|
|
1661
|
-
|
|
1662
|
-
|
|
1663
|
-
|
|
1664
|
-
|
|
1665
|
-
}
|
|
1652
|
+
if (auth && auth.startsWith("Bearer ")) {
|
|
1653
|
+
const token = auth.slice("Bearer ".length).trim();
|
|
1654
|
+
if (tokenSet.has(token)) return;
|
|
1655
|
+
}
|
|
1656
|
+
const agentId = request.headers["x-agent-id"];
|
|
1657
|
+
const publicKeyHex = request.headers["x-agent-public-key"];
|
|
1658
|
+
const signature = request.headers["x-agent-signature"];
|
|
1659
|
+
if (agentId && publicKeyHex && signature) {
|
|
1660
|
+
try {
|
|
1661
|
+
const publicKeyBuf = Buffer.from(publicKeyHex, "hex");
|
|
1662
|
+
const body = request.body;
|
|
1663
|
+
const valid = verifyEscrowReceipt(body, signature, publicKeyBuf);
|
|
1664
|
+
if (valid) return;
|
|
1665
|
+
} catch {
|
|
1666
|
+
}
|
|
1666
1667
|
}
|
|
1668
|
+
await reply.status(401).send({
|
|
1669
|
+
jsonrpc: "2.0",
|
|
1670
|
+
id: null,
|
|
1671
|
+
error: { code: -32e3, message: "Unauthorized: provide Bearer token or X-Agent-Id/Signature headers" }
|
|
1672
|
+
});
|
|
1667
1673
|
});
|
|
1668
1674
|
fastify.get("/health", async () => {
|
|
1669
1675
|
return { status: "ok", version: VERSION, uptime: process.uptime() };
|
|
@@ -3434,6 +3440,7 @@ program.command("request [card-id]").description("Request a capability from anot
|
|
|
3434
3440
|
let gatewayUrl;
|
|
3435
3441
|
let token;
|
|
3436
3442
|
let isRemoteRequest = false;
|
|
3443
|
+
let identityAuth;
|
|
3437
3444
|
if (opts.peer) {
|
|
3438
3445
|
const peer = findPeer(opts.peer);
|
|
3439
3446
|
if (!peer) {
|
|
@@ -3443,6 +3450,16 @@ program.command("request [card-id]").description("Request a capability from anot
|
|
|
3443
3450
|
gatewayUrl = peer.url;
|
|
3444
3451
|
token = peer.token;
|
|
3445
3452
|
isRemoteRequest = true;
|
|
3453
|
+
const configDir = getConfigDir();
|
|
3454
|
+
const agentIdentity = loadIdentity(configDir);
|
|
3455
|
+
if (agentIdentity) {
|
|
3456
|
+
const keys = loadKeyPair(configDir);
|
|
3457
|
+
identityAuth = {
|
|
3458
|
+
agentId: agentIdentity.agent_id,
|
|
3459
|
+
publicKey: agentIdentity.public_key,
|
|
3460
|
+
privateKey: keys.privateKey
|
|
3461
|
+
};
|
|
3462
|
+
}
|
|
3446
3463
|
} else {
|
|
3447
3464
|
const db = openDatabase(config.db_path);
|
|
3448
3465
|
let localCard;
|
|
@@ -3481,6 +3498,18 @@ program.command("request [card-id]").description("Request a capability from anot
|
|
|
3481
3498
|
gatewayUrl = remoteCard.gateway_url;
|
|
3482
3499
|
token = "";
|
|
3483
3500
|
isRemoteRequest = true;
|
|
3501
|
+
const configDir = getConfigDir();
|
|
3502
|
+
const agentIdentity = loadIdentity(configDir);
|
|
3503
|
+
if (!agentIdentity) {
|
|
3504
|
+
console.error("Error: no agent identity found. Run `agentbnb init` first.");
|
|
3505
|
+
process.exit(1);
|
|
3506
|
+
}
|
|
3507
|
+
const keys = loadKeyPair(configDir);
|
|
3508
|
+
identityAuth = {
|
|
3509
|
+
agentId: agentIdentity.agent_id,
|
|
3510
|
+
publicKey: agentIdentity.public_key,
|
|
3511
|
+
privateKey: keys.privateKey
|
|
3512
|
+
};
|
|
3484
3513
|
if (!opts.json) {
|
|
3485
3514
|
const displayName = remoteCard.name ?? remoteCard.agent_name ?? cardId;
|
|
3486
3515
|
console.log(`Found remote card: ${displayName} @ ${gatewayUrl}`);
|
|
@@ -3533,7 +3562,8 @@ program.command("request [card-id]").description("Request a capability from anot
|
|
|
3533
3562
|
token,
|
|
3534
3563
|
cardId,
|
|
3535
3564
|
params: { ...params, ...opts.skill ? { skill_id: opts.skill } : {} },
|
|
3536
|
-
escrowReceipt
|
|
3565
|
+
escrowReceipt,
|
|
3566
|
+
identity: identityAuth
|
|
3537
3567
|
});
|
|
3538
3568
|
if (useReceipt && escrowId) {
|
|
3539
3569
|
const configDir = getConfigDir();
|
|
@@ -3704,7 +3734,7 @@ program.command("serve").description("Start the AgentBnB gateway server").option
|
|
|
3704
3734
|
}
|
|
3705
3735
|
if (opts.registry) {
|
|
3706
3736
|
const { RelayClient } = await import("../websocket-client-5TIQDYQ4.js");
|
|
3707
|
-
const { executeCapabilityRequest: executeCapabilityRequest2 } = await import("../execute-
|
|
3737
|
+
const { executeCapabilityRequest: executeCapabilityRequest2 } = await import("../execute-SWWEHV2K.js");
|
|
3708
3738
|
const cards = listCards(runtime.registryDb, config.owner);
|
|
3709
3739
|
const card = cards[0] ?? {
|
|
3710
3740
|
id: config.owner,
|
|
@@ -3973,7 +4003,7 @@ openclaw.command("rules").description("Print HEARTBEAT.md rules block (or inject
|
|
|
3973
4003
|
}
|
|
3974
4004
|
});
|
|
3975
4005
|
program.command("conduct <task>").description("Orchestrate a complex task across the AgentBnB network").option("--plan-only", "Show execution plan without executing").option("--max-budget <credits>", "Maximum credits to spend", "100").option("--json", "Output as JSON").action(async (task, opts) => {
|
|
3976
|
-
const { conductAction } = await import("../conduct-
|
|
4006
|
+
const { conductAction } = await import("../conduct-IEQ567ET.js");
|
|
3977
4007
|
const result = await conductAction(task, opts);
|
|
3978
4008
|
if (opts.json) {
|
|
3979
4009
|
console.log(JSON.stringify(result, null, 2));
|
|
@@ -4,10 +4,10 @@ import {
|
|
|
4
4
|
decompose,
|
|
5
5
|
matchSubTasks,
|
|
6
6
|
orchestrate
|
|
7
|
-
} from "./chunk-
|
|
7
|
+
} from "./chunk-7OACGAFD.js";
|
|
8
8
|
import {
|
|
9
9
|
BudgetManager
|
|
10
|
-
} from "./chunk-
|
|
10
|
+
} from "./chunk-IZZ4FP45.js";
|
|
11
11
|
import {
|
|
12
12
|
loadConfig,
|
|
13
13
|
loadPeers
|
|
@@ -17,7 +17,7 @@ import {
|
|
|
17
17
|
} from "./chunk-UOGDK2S2.js";
|
|
18
18
|
import {
|
|
19
19
|
openCreditDb
|
|
20
|
-
} from "./chunk-
|
|
20
|
+
} from "./chunk-QHQPXO67.js";
|
|
21
21
|
import "./chunk-XA63SD4T.js";
|
|
22
22
|
|
|
23
23
|
// src/cli/conduct.ts
|
|
@@ -3,12 +3,12 @@ import {
|
|
|
3
3
|
decompose,
|
|
4
4
|
matchSubTasks,
|
|
5
5
|
orchestrate
|
|
6
|
-
} from "./chunk-
|
|
6
|
+
} from "./chunk-7OACGAFD.js";
|
|
7
7
|
import {
|
|
8
8
|
BudgetManager
|
|
9
|
-
} from "./chunk-
|
|
9
|
+
} from "./chunk-IZZ4FP45.js";
|
|
10
10
|
import "./chunk-BEI5MTNZ.js";
|
|
11
|
-
import "./chunk-
|
|
11
|
+
import "./chunk-QHQPXO67.js";
|
|
12
12
|
import "./chunk-XA63SD4T.js";
|
|
13
13
|
|
|
14
14
|
// src/conductor/conductor-mode.ts
|
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
import {
|
|
2
2
|
executeCapabilityRequest
|
|
3
|
-
} from "./chunk-
|
|
3
|
+
} from "./chunk-QSPWE5AE.js";
|
|
4
4
|
import "./chunk-UOGDK2S2.js";
|
|
5
|
-
import "./chunk-
|
|
5
|
+
import "./chunk-QHQPXO67.js";
|
|
6
6
|
import "./chunk-XA63SD4T.js";
|
|
7
7
|
export {
|
|
8
8
|
executeCapabilityRequest
|
package/dist/index.js
CHANGED
|
@@ -946,22 +946,27 @@ function createGatewayServer(opts) {
|
|
|
946
946
|
fastify.addHook("onRequest", async (request, reply) => {
|
|
947
947
|
if (request.method === "GET" && request.url === "/health") return;
|
|
948
948
|
const auth = request.headers.authorization;
|
|
949
|
-
if (
|
|
950
|
-
|
|
951
|
-
|
|
952
|
-
|
|
953
|
-
|
|
954
|
-
|
|
955
|
-
|
|
956
|
-
|
|
957
|
-
|
|
958
|
-
|
|
959
|
-
|
|
960
|
-
|
|
961
|
-
|
|
962
|
-
|
|
963
|
-
}
|
|
949
|
+
if (auth && auth.startsWith("Bearer ")) {
|
|
950
|
+
const token = auth.slice("Bearer ".length).trim();
|
|
951
|
+
if (tokenSet.has(token)) return;
|
|
952
|
+
}
|
|
953
|
+
const agentId = request.headers["x-agent-id"];
|
|
954
|
+
const publicKeyHex = request.headers["x-agent-public-key"];
|
|
955
|
+
const signature = request.headers["x-agent-signature"];
|
|
956
|
+
if (agentId && publicKeyHex && signature) {
|
|
957
|
+
try {
|
|
958
|
+
const publicKeyBuf = Buffer.from(publicKeyHex, "hex");
|
|
959
|
+
const body = request.body;
|
|
960
|
+
const valid = verifyEscrowReceipt(body, signature, publicKeyBuf);
|
|
961
|
+
if (valid) return;
|
|
962
|
+
} catch {
|
|
963
|
+
}
|
|
964
964
|
}
|
|
965
|
+
await reply.status(401).send({
|
|
966
|
+
jsonrpc: "2.0",
|
|
967
|
+
id: null,
|
|
968
|
+
error: { code: -32e3, message: "Unauthorized: provide Bearer token or X-Agent-Id/Signature headers" }
|
|
969
|
+
});
|
|
965
970
|
});
|
|
966
971
|
fastify.get("/health", async () => {
|
|
967
972
|
return { status: "ok", version: VERSION, uptime: process.uptime() };
|
|
@@ -1917,7 +1922,7 @@ function decompose(task, _availableCapabilities) {
|
|
|
1917
1922
|
// src/gateway/client.ts
|
|
1918
1923
|
import { randomUUID as randomUUID5 } from "crypto";
|
|
1919
1924
|
async function requestCapability(opts) {
|
|
1920
|
-
const { gatewayUrl, token, cardId, params = {}, timeoutMs = 3e4, escrowReceipt } = opts;
|
|
1925
|
+
const { gatewayUrl, token, cardId, params = {}, timeoutMs = 3e4, escrowReceipt, identity } = opts;
|
|
1921
1926
|
const id = randomUUID5();
|
|
1922
1927
|
const payload = {
|
|
1923
1928
|
jsonrpc: "2.0",
|
|
@@ -1929,16 +1934,22 @@ async function requestCapability(opts) {
|
|
|
1929
1934
|
...escrowReceipt ? { escrow_receipt: escrowReceipt } : {}
|
|
1930
1935
|
}
|
|
1931
1936
|
};
|
|
1937
|
+
const headers = { "Content-Type": "application/json" };
|
|
1938
|
+
if (identity) {
|
|
1939
|
+
const signature = signEscrowReceipt(payload, identity.privateKey);
|
|
1940
|
+
headers["X-Agent-Id"] = identity.agentId;
|
|
1941
|
+
headers["X-Agent-Public-Key"] = identity.publicKey;
|
|
1942
|
+
headers["X-Agent-Signature"] = signature;
|
|
1943
|
+
} else if (token) {
|
|
1944
|
+
headers["Authorization"] = `Bearer ${token}`;
|
|
1945
|
+
}
|
|
1932
1946
|
const controller = new AbortController();
|
|
1933
1947
|
const timer = setTimeout(() => controller.abort(), timeoutMs);
|
|
1934
1948
|
let response;
|
|
1935
1949
|
try {
|
|
1936
1950
|
response = await fetch(`${gatewayUrl}/rpc`, {
|
|
1937
1951
|
method: "POST",
|
|
1938
|
-
headers
|
|
1939
|
-
"Content-Type": "application/json",
|
|
1940
|
-
Authorization: `Bearer ${token}`
|
|
1941
|
-
},
|
|
1952
|
+
headers,
|
|
1942
1953
|
body: JSON.stringify(payload),
|
|
1943
1954
|
signal: controller.signal
|
|
1944
1955
|
});
|