@heyanon-arp/cli 0.0.30 → 0.0.32
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/cli.js +196 -175
- package/dist/cli.js.map +1 -1
- package/package.json +2 -2
package/dist/cli.js
CHANGED
|
@@ -585,6 +585,30 @@ var init_api = __esm({
|
|
|
585
585
|
)
|
|
586
586
|
);
|
|
587
587
|
}
|
|
588
|
+
/**
|
|
589
|
+
* Signed `GET /v1/agents/:did/active-delegations`. The signer's own
|
|
590
|
+
* IN-FLIGHT delegations as recipient — the worker's task list in one
|
|
591
|
+
* indexed read instead of crawling every relationship. Signer must
|
|
592
|
+
* equal `did`. Oldest-first (FIFO). Same inbound content-security as
|
|
593
|
+
* `listDelegations`: scope/title/brief/acceptanceCriteria are
|
|
594
|
+
* OFFERER-authored, so they are shield-scanned (the reader is the
|
|
595
|
+
* recipient here, never the offerer, so every row is scanned).
|
|
596
|
+
*/
|
|
597
|
+
async listActiveDelegations(did, signer, query, signal) {
|
|
598
|
+
const rows = await this.signedRequest(
|
|
599
|
+
"GET",
|
|
600
|
+
`/v1/agents/${encodeURIComponent(did)}/active-delegations`,
|
|
601
|
+
null,
|
|
602
|
+
signer,
|
|
603
|
+
query,
|
|
604
|
+
signal
|
|
605
|
+
);
|
|
606
|
+
return Promise.all(
|
|
607
|
+
rows.map(
|
|
608
|
+
(row) => signer.did === row.offererDid ? row : (0, import_shield.guardInboundFields)(row, ["scopeSummary", "title", "brief", "acceptanceCriteria"], { selfDid: signer.did }).then((r) => r.event)
|
|
609
|
+
)
|
|
610
|
+
);
|
|
611
|
+
}
|
|
588
612
|
/**
|
|
589
613
|
* Signed `GET /v1/relationships/:id/work`. One row per
|
|
590
614
|
* `(delegationId, requestId)`, ordered chronologically with the
|
|
@@ -735,13 +759,13 @@ var init_api = __esm({
|
|
|
735
759
|
});
|
|
736
760
|
|
|
737
761
|
// src/cli.ts
|
|
738
|
-
var
|
|
762
|
+
var import_shield4 = require("@heyanon-arp/shield");
|
|
739
763
|
var import_commander = require("commander");
|
|
740
764
|
|
|
741
765
|
// package.json
|
|
742
766
|
var package_default = {
|
|
743
767
|
name: "@heyanon-arp/cli",
|
|
744
|
-
version: "0.0.
|
|
768
|
+
version: "0.0.32",
|
|
745
769
|
description: "Command-line client for the Agent Relationship Protocol \u2014 register agents, sign envelopes, run escrowed work cycles on Solana.",
|
|
746
770
|
license: "MIT",
|
|
747
771
|
keywords: ["arp", "agent-relationship-protocol", "did", "solana", "escrow", "ed25519", "agents", "a2a", "cli"],
|
|
@@ -1022,7 +1046,7 @@ function requireCredential(commandName, serverUrl) {
|
|
|
1022
1046
|
|
|
1023
1047
|
// src/state.ts
|
|
1024
1048
|
init_paths();
|
|
1025
|
-
var STATE_WARNING = "DO NOT COMMIT \u2014 contains private keys (Ed25519 +
|
|
1049
|
+
var STATE_WARNING = "DO NOT COMMIT \u2014 contains private keys (Ed25519 identity + settlement).";
|
|
1026
1050
|
function stateFilePath() {
|
|
1027
1051
|
return (0, import_node_path4.join)(arpHomeDir(), "agents.json");
|
|
1028
1052
|
}
|
|
@@ -1135,9 +1159,6 @@ function toKeyBundle(agent, exportedAt) {
|
|
|
1135
1159
|
identitySecretKeyB64: agent.identitySecretKeyB64,
|
|
1136
1160
|
settlementPublicKeyB58: agent.settlementPublicKeyB58,
|
|
1137
1161
|
settlementSecretKeyB64: agent.settlementSecretKeyB64,
|
|
1138
|
-
scryptKeyB64: agent.scryptKeyB64,
|
|
1139
|
-
scryptSaltB64: agent.scryptSaltB64,
|
|
1140
|
-
scryptSaltId: agent.scryptSaltId,
|
|
1141
1162
|
ownerWallet: agent.ownerWallet,
|
|
1142
1163
|
exportedAt
|
|
1143
1164
|
};
|
|
@@ -1147,16 +1168,7 @@ function validateKeyBundle(raw) {
|
|
|
1147
1168
|
throw new Error("recover: key file is not a JSON object");
|
|
1148
1169
|
}
|
|
1149
1170
|
const o = raw;
|
|
1150
|
-
const required = [
|
|
1151
|
-
"did",
|
|
1152
|
-
"identityPublicKeyB58",
|
|
1153
|
-
"identitySecretKeyB64",
|
|
1154
|
-
"settlementPublicKeyB58",
|
|
1155
|
-
"settlementSecretKeyB64",
|
|
1156
|
-
"scryptKeyB64",
|
|
1157
|
-
"scryptSaltB64",
|
|
1158
|
-
"scryptSaltId"
|
|
1159
|
-
];
|
|
1171
|
+
const required = ["did", "identityPublicKeyB58", "identitySecretKeyB64", "settlementPublicKeyB58", "settlementSecretKeyB64"];
|
|
1160
1172
|
for (const f of required) {
|
|
1161
1173
|
if (typeof o[f] !== "string" || o[f].length === 0) {
|
|
1162
1174
|
throw new Error(`recover: key file is missing or has an invalid '${f}' (expected a non-empty string) \u2014 is this a 'heyarp keys export' file?`);
|
|
@@ -1171,9 +1183,6 @@ function validateKeyBundle(raw) {
|
|
|
1171
1183
|
identitySecretKeyB64: o.identitySecretKeyB64,
|
|
1172
1184
|
settlementPublicKeyB58: o.settlementPublicKeyB58,
|
|
1173
1185
|
settlementSecretKeyB64: o.settlementSecretKeyB64,
|
|
1174
|
-
scryptKeyB64: o.scryptKeyB64,
|
|
1175
|
-
scryptSaltB64: o.scryptSaltB64,
|
|
1176
|
-
scryptSaltId: o.scryptSaltId,
|
|
1177
1186
|
ownerWallet: o.ownerWallet,
|
|
1178
1187
|
exportedAt: typeof o.exportedAt === "string" ? o.exportedAt : ""
|
|
1179
1188
|
};
|
|
@@ -4011,6 +4020,7 @@ var DELEGATION_CURRENCY_FLAGS = {
|
|
|
4011
4020
|
|
|
4012
4021
|
// src/commands/delegations.ts
|
|
4013
4022
|
var import_sdk14 = require("@heyanon-arp/sdk");
|
|
4023
|
+
var import_shield2 = require("@heyanon-arp/shield");
|
|
4014
4024
|
var import_chalk12 = __toESM(require("chalk"));
|
|
4015
4025
|
init_api();
|
|
4016
4026
|
var ALLOWED_STATES = /* @__PURE__ */ new Set([import_sdk14.DelegationStates.OFFERED, import_sdk14.DelegationStates.ACCEPTED, import_sdk14.DelegationStates.DECLINED, import_sdk14.DelegationStates.CANCELED]);
|
|
@@ -4070,7 +4080,7 @@ function formatDelegationLine(d, selfDid, opts = {}) {
|
|
|
4070
4080
|
const state = colorState(d.state).padEnd(stateColumnWidth());
|
|
4071
4081
|
const offerer = d.offererDid === selfDid ? import_chalk12.default.bold("me") : import_chalk12.default.dim(opts.fullIds ? d.offererDid : didHead(d.offererDid));
|
|
4072
4082
|
const amount = formatAmount(d);
|
|
4073
|
-
const title = d.title ? import_chalk12.default.dim(`"${truncate2(d.title, 40)}"`) : import_chalk12.default.dim("(no title)");
|
|
4083
|
+
const title = (0, import_shield2.isShieldRedacted)(d.title) ? import_chalk12.default.dim("(redacted)") : d.title ? import_chalk12.default.dim(`"${truncate2(d.title, 40)}"`) : import_chalk12.default.dim("(no title)");
|
|
4074
4084
|
let declineSuffix = "";
|
|
4075
4085
|
if (d.state === import_sdk14.DelegationStates.DECLINED && d.declineReason) {
|
|
4076
4086
|
const detail = d.declineReasonDetail ? `: ${truncate2(d.declineReasonDetail, 40)}` : "";
|
|
@@ -5097,6 +5107,12 @@ var GUIDE_SECTIONS = [
|
|
|
5097
5107
|
" ARP is asynchronous \u2014 offers + work_requests ARRIVE whenever the buyer",
|
|
5098
5108
|
" acts. Pick whichever loop your runtime can actually sustain:",
|
|
5099
5109
|
"",
|
|
5110
|
+
" COLD-START / RECONCILE: `heyarp tasks` returns your in-flight delegations as",
|
|
5111
|
+
" recipient (offered|accepted|pending_lock_finalization|locked|disputing) in ONE",
|
|
5112
|
+
' indexed read \u2014 the snapshot of "what is on my plate" without crawling every',
|
|
5113
|
+
" relationship. Pull it on startup / after a restart, then ride a loop below for",
|
|
5114
|
+
" new arrivals (the inbox stream is the realtime signal; `tasks` is the catch-up):",
|
|
5115
|
+
"",
|
|
5100
5116
|
" A) LONG-LIVED (a process that can hold a thread \u2014 e.g. a daemon):",
|
|
5101
5117
|
" block on the next state:",
|
|
5102
5118
|
" heyarp status <rel-id> --wait --until <state> (exit 124 on timeout)",
|
|
@@ -6457,7 +6473,7 @@ function registerProfileCommand(root) {
|
|
|
6457
6473
|
|
|
6458
6474
|
// src/commands/receipt.ts
|
|
6459
6475
|
var import_sdk22 = require("@heyanon-arp/sdk");
|
|
6460
|
-
var
|
|
6476
|
+
var import_shield3 = require("@heyanon-arp/shield");
|
|
6461
6477
|
var import_chalk25 = __toESM(require("chalk"));
|
|
6462
6478
|
init_api();
|
|
6463
6479
|
function registerReceiptCommands(root) {
|
|
@@ -6668,7 +6684,7 @@ async function computeWorkLogHashes(api, sender, relationshipId, delegationId, r
|
|
|
6668
6684
|
`receipt propose --auto-hashes: work-log row ${requestId} is in state '${workLog.state}', not 'responded'. The payee must \`work respond\` before a receipt can be proposed.`
|
|
6669
6685
|
);
|
|
6670
6686
|
}
|
|
6671
|
-
if ((0,
|
|
6687
|
+
if ((0, import_shield3.isShieldRedacted)(workLog.requestParams) || (0, import_shield3.isShieldRedacted)(workLog.responseOutput)) {
|
|
6672
6688
|
throw new Error(
|
|
6673
6689
|
`receipt propose --auto-hashes: work-log row ${requestId} has shield-withheld content (the counterparty's request or response was flagged by content-security). Cannot reconstruct canonical hashes over withheld content \u2014 do not settle; review and dispute. See ~/.heyshield/receipts.jsonl.`
|
|
6674
6690
|
);
|
|
@@ -6939,9 +6955,6 @@ async function runRecover(opts) {
|
|
|
6939
6955
|
identitySecretKeyB64: bundle.identitySecretKeyB64,
|
|
6940
6956
|
settlementPublicKeyB58: bundle.settlementPublicKeyB58,
|
|
6941
6957
|
settlementSecretKeyB64: bundle.settlementSecretKeyB64,
|
|
6942
|
-
scryptKeyB64: bundle.scryptKeyB64,
|
|
6943
|
-
scryptSaltB64: bundle.scryptSaltB64,
|
|
6944
|
-
scryptSaltId: bundle.scryptSaltId,
|
|
6945
6958
|
currentAttestationId: row.currentAttestationId,
|
|
6946
6959
|
name: row.name ?? void 0,
|
|
6947
6960
|
description: row.description ?? void 0,
|
|
@@ -6959,7 +6972,6 @@ async function runRecover(opts) {
|
|
|
6959
6972
|
}
|
|
6960
6973
|
|
|
6961
6974
|
// src/commands/register.ts
|
|
6962
|
-
var import_node_crypto4 = require("crypto");
|
|
6963
6975
|
var import_node_fs9 = require("fs");
|
|
6964
6976
|
var import_sdk25 = require("@heyanon-arp/sdk");
|
|
6965
6977
|
var import_chalk28 = __toESM(require("chalk"));
|
|
@@ -6971,28 +6983,10 @@ function registerRegisterCommand(root) {
|
|
|
6971
6983
|
[
|
|
6972
6984
|
"Register a new ARP agent. Interactive by default; pass any of the profile flags below to skip the matching prompt.",
|
|
6973
6985
|
"",
|
|
6974
|
-
"
|
|
6986
|
+
"No password \u2014 the agent identity key self-signs the owner key-link; ownership is your `heyarp login` wallet.",
|
|
6975
6987
|
"`--yes` is the non-interactive switch \u2014 every required field must arrive via flags (no prompts). Use this for scripted setups."
|
|
6976
6988
|
].join("\n")
|
|
6977
|
-
).option("--server <url>", "Override ARP server base URL").option("--from-keys <file>", "Load identity + settlement keys from a JSON file instead of generating").option("--name <s>", "Unique handle \u2014 lowercase a-z0-9_, 3-32 chars, immutable (skips the name prompt)").option("--description <s>", "Description (skips the description prompt)").option("--tag <s>", "Capability tag \u2014 repeatable, e.g. --tag translation --tag fr", accumulate3, []).option(
|
|
6978
|
-
"--password <s>",
|
|
6979
|
-
// `--password` puts the secret in `argv` — visible via
|
|
6980
|
-
// `ps aux` / kernel process table on shared hosts,
|
|
6981
|
-
// recorded by `/proc/<pid>/cmdline`, and almost always
|
|
6982
|
-
// logged by CI runners (e.g. GitHub Actions echoes the
|
|
6983
|
-
// full command). Safer alternatives:
|
|
6984
|
-
// • interactive prompt (default) — never written anywhere
|
|
6985
|
-
// • `HEYARP_PASSWORD` env var (tracked) reads from env so
|
|
6986
|
-
// the secret stays out of argv even in scripts
|
|
6987
|
-
// Treat `--password <s>` as a one-off local-dev affordance;
|
|
6988
|
-
// do NOT use it in CI pipelines without a secret-redacting
|
|
6989
|
-
// runner.
|
|
6990
|
-
"Owner password \u2014 MUST be at least 8 characters. REQUIRED when --yes is set; otherwise the CLI prompts for it. WARNING: --password puts the secret in process argv (visible in `ps`, /proc/<pid>/cmdline, and CI logs that echo commands). Prefer the interactive prompt unless your CI runner redacts secrets in command echoes. HEYARP_PASSWORD env var support is tracked."
|
|
6991
|
-
).option(
|
|
6992
|
-
"--yes",
|
|
6993
|
-
"Strict non-interactive: fail if any required field is still missing after merging flags. With --yes, --password must be supplied explicitly (>= 8 chars).",
|
|
6994
|
-
false
|
|
6995
|
-
).option(
|
|
6989
|
+
).option("--server <url>", "Override ARP server base URL").option("--from-keys <file>", "Load identity + settlement keys from a JSON file instead of generating").option("--name <s>", "Unique handle \u2014 lowercase a-z0-9_, 3-32 chars, immutable (skips the name prompt)").option("--description <s>", "Description (skips the description prompt)").option("--tag <s>", "Capability tag \u2014 repeatable, e.g. --tag translation --tag fr", accumulate3, []).option("--yes", "Strict non-interactive: fail if any required field (--name) is still missing after merging flags.", false).option(
|
|
6996
6990
|
"--json",
|
|
6997
6991
|
// Emit a single JSON object instead of human-friendly
|
|
6998
6992
|
// success prints. Output shape:
|
|
@@ -7029,9 +7023,6 @@ async function runRegister(opts, deps = defaultRegisterDeps) {
|
|
|
7029
7023
|
const did = (0, import_sdk25.formatDid)(keys.identityPublicKey);
|
|
7030
7024
|
if (!opts.json) console.log(import_chalk28.default.dim(`DID will be: ${did}`));
|
|
7031
7025
|
const answers = await mergeAnswers(opts);
|
|
7032
|
-
const scryptSalt = (0, import_node_crypto4.randomBytes)(16);
|
|
7033
|
-
if (!opts.json) console.log(import_chalk28.default.dim("Deriving scrypt key, this may take a moment..."));
|
|
7034
|
-
const scryptKey = (0, import_sdk25.deriveScryptKey)(answers.password, new Uint8Array(scryptSalt));
|
|
7035
7026
|
const challenge = await api.issueChallenge("register");
|
|
7036
7027
|
const challengeBytes = base64UrlNoPadDecode(challenge.challengeB64);
|
|
7037
7028
|
if (challengeBytes.length !== 32) {
|
|
@@ -7045,7 +7036,6 @@ async function runRegister(opts, deps = defaultRegisterDeps) {
|
|
|
7045
7036
|
signature: Buffer.from(challengeSig).toString("base64")
|
|
7046
7037
|
});
|
|
7047
7038
|
const settlementPublicKeyB58 = (0, import_sdk25.base58btcEncode)(keys.settlementPublicKey);
|
|
7048
|
-
const scryptSaltId = (0, import_sdk25.uuidV4)();
|
|
7049
7039
|
const payload = {
|
|
7050
7040
|
purpose: import_sdk25.Purpose.KEY_LINK,
|
|
7051
7041
|
agent_did: did,
|
|
@@ -7056,18 +7046,15 @@ async function runRegister(opts, deps = defaultRegisterDeps) {
|
|
|
7056
7046
|
created_at: (0, import_sdk25.rfc3339)(),
|
|
7057
7047
|
nonce: (0, import_sdk25.senderNonce)()
|
|
7058
7048
|
};
|
|
7059
|
-
const attestation = (0, import_sdk25.signKeyLinkAttestation)({ payload,
|
|
7049
|
+
const attestation = (0, import_sdk25.signKeyLinkAttestation)({ payload, identitySecretKey: keys.identitySecretKey });
|
|
7060
7050
|
const body = {
|
|
7061
7051
|
challengeId: challenge.challengeId,
|
|
7062
7052
|
identityPublicKey: identityPublicKeyB58,
|
|
7063
7053
|
settlementPublicKey: settlementPublicKeyB58,
|
|
7064
7054
|
ownerAttestation: {
|
|
7065
7055
|
payload: attestation.payload,
|
|
7066
|
-
sig: attestation.sig
|
|
7067
|
-
scrypt_salt_id: attestation.scrypt_salt_id
|
|
7056
|
+
sig: attestation.sig
|
|
7068
7057
|
},
|
|
7069
|
-
scryptKeyB64: Buffer.from(scryptKey).toString("base64"),
|
|
7070
|
-
scryptSaltB64: Buffer.from(scryptSalt).toString("base64"),
|
|
7071
7058
|
name: answers.name,
|
|
7072
7059
|
description: answers.description ? answers.description : void 0,
|
|
7073
7060
|
tags: answers.tags.length > 0 ? answers.tags : void 0
|
|
@@ -7078,9 +7065,6 @@ async function runRegister(opts, deps = defaultRegisterDeps) {
|
|
|
7078
7065
|
identitySecretKeyB64: Buffer.from(keys.identitySecretKey).toString("base64"),
|
|
7079
7066
|
settlementPublicKeyB58,
|
|
7080
7067
|
settlementSecretKeyB64: Buffer.from(keys.settlementSecretKey).toString("base64"),
|
|
7081
|
-
scryptKeyB64: Buffer.from(scryptKey).toString("base64"),
|
|
7082
|
-
scryptSaltB64: Buffer.from(scryptSalt).toString("base64"),
|
|
7083
|
-
scryptSaltId,
|
|
7084
7068
|
// Placeholder until the server confirms registration and returns
|
|
7085
7069
|
// the canonical attestation id (finalized in Step 8 below).
|
|
7086
7070
|
currentAttestationId: "",
|
|
@@ -7159,32 +7143,15 @@ Local state saved to ${arpHomeDir()}/agents.json (mode 0600).`));
|
|
|
7159
7143
|
}
|
|
7160
7144
|
}
|
|
7161
7145
|
async function mergeAnswers(opts) {
|
|
7162
|
-
const need = opts.yes ? {
|
|
7163
|
-
password: opts.password === void 0,
|
|
7146
|
+
const need = opts.yes ? { name: false, description: false, tagsCsv: false } : {
|
|
7164
7147
|
name: opts.name === void 0,
|
|
7165
7148
|
description: opts.description === void 0,
|
|
7166
7149
|
tagsCsv: opts.tag === void 0 || opts.tag.length === 0
|
|
7167
7150
|
};
|
|
7168
|
-
if (opts.yes) {
|
|
7169
|
-
|
|
7170
|
-
if (opts.password === void 0) missing.push("--password");
|
|
7171
|
-
if (opts.name === void 0) missing.push("--name");
|
|
7172
|
-
if (missing.length > 0) {
|
|
7173
|
-
throw new Error(`register --yes: missing required flag${missing.length > 1 ? "s" : ""}: ${missing.join(", ")}`);
|
|
7174
|
-
}
|
|
7175
|
-
}
|
|
7176
|
-
if (opts.password !== void 0 && opts.password.length < 8) {
|
|
7177
|
-
throw new Error("register --password: password must be at least 8 characters");
|
|
7151
|
+
if (opts.yes && opts.name === void 0) {
|
|
7152
|
+
throw new Error("register --yes: missing required flag: --name");
|
|
7178
7153
|
}
|
|
7179
7154
|
const promptDefs = [];
|
|
7180
|
-
if (need.password) {
|
|
7181
|
-
promptDefs.push({
|
|
7182
|
-
type: "password",
|
|
7183
|
-
name: "password",
|
|
7184
|
-
message: "Owner password (used to derive the scrypt key)",
|
|
7185
|
-
validate: (v) => v.length >= 8 ? true : "must be at least 8 characters"
|
|
7186
|
-
});
|
|
7187
|
-
}
|
|
7188
7155
|
if (need.name) {
|
|
7189
7156
|
promptDefs.push({
|
|
7190
7157
|
type: "text",
|
|
@@ -7218,7 +7185,6 @@ async function mergeAnswers(opts) {
|
|
|
7218
7185
|
const tags = (opts.tag && opts.tag.length > 0 ? opts.tag : parseTagsCsv(typeof prompted.tagsCsv === "string" ? prompted.tagsCsv : "")).map((t) => t.trim().toLowerCase()).filter((t) => t.length > 0);
|
|
7219
7186
|
const name = normalizeAndValidateName(opts.name ?? prompted.name);
|
|
7220
7187
|
return {
|
|
7221
|
-
password: opts.password ?? prompted.password,
|
|
7222
7188
|
name,
|
|
7223
7189
|
description: opts.description ?? prompted.description ?? "",
|
|
7224
7190
|
tags
|
|
@@ -8070,9 +8036,63 @@ function renderAssets(assets) {
|
|
|
8070
8036
|
}
|
|
8071
8037
|
}
|
|
8072
8038
|
|
|
8073
|
-
// src/commands/
|
|
8039
|
+
// src/commands/tasks.ts
|
|
8040
|
+
var import_sdk30 = require("@heyanon-arp/sdk");
|
|
8074
8041
|
var import_chalk35 = __toESM(require("chalk"));
|
|
8075
8042
|
init_api();
|
|
8043
|
+
var INFLIGHT = new Set(import_sdk30.DELEGATION_INFLIGHT_STATES);
|
|
8044
|
+
function registerTasksCommand(root) {
|
|
8045
|
+
root.command("tasks").description("List MY in-flight delegations as recipient \u2014 the worker task list (offered|accepted|pending_lock_finalization|locked|disputing), oldest-first").option("--server <url>", "Override ARP server base URL").option("--state <s>", "Filter by ONE in-flight state (offered|accepted|pending_lock_finalization|locked|disputing)").option("--after <id>", "Cursor: pass the previous page's last `id` to fetch the next page").option("--limit <n>", "Max rows to return (1..100)", "20").option("--from-did <did>", "Signer DID \u2014 required only if multiple agents are registered against this server").option("--from <name>", "Signer agent NAME (handle) \u2014 alternative to --from-did, resolved against your local agents").option("--json", "Machine-readable mode \u2014 emit a single JSON array of delegation rows, no chalk, no summary. Pipe-safe.", false).option("--full-ids", "Print delegationId / DIDs in full (no truncation) for copy-paste into the next command.", false).action(async (opts) => {
|
|
8046
|
+
await runTasks(opts);
|
|
8047
|
+
});
|
|
8048
|
+
}
|
|
8049
|
+
async function runTasks(opts) {
|
|
8050
|
+
const limit = parseLimit7(opts.limit);
|
|
8051
|
+
const state = parseInflightState(opts.state);
|
|
8052
|
+
const api = new ArpApiClient(opts.server);
|
|
8053
|
+
const sender = resolveSenderAgent("tasks", opts.server, opts.fromDid, opts.from);
|
|
8054
|
+
progress(opts.json, import_chalk35.default.dim(`Server: ${api.serverUrl}`));
|
|
8055
|
+
progress(opts.json, import_chalk35.default.dim(`Signer: ${sender.did}`));
|
|
8056
|
+
const query = { limit };
|
|
8057
|
+
if (state) query.state = state;
|
|
8058
|
+
if (opts.after) query.after = opts.after;
|
|
8059
|
+
const signer = makeSigner(sender);
|
|
8060
|
+
const rows = await api.listActiveDelegations(sender.did, signer, query);
|
|
8061
|
+
if (opts.json) {
|
|
8062
|
+
jsonOut(rows);
|
|
8063
|
+
return;
|
|
8064
|
+
}
|
|
8065
|
+
if (rows.length === 0) {
|
|
8066
|
+
console.log(import_chalk35.default.dim("\n(no in-flight delegations \u2014 your task queue is empty)"));
|
|
8067
|
+
return;
|
|
8068
|
+
}
|
|
8069
|
+
console.log("");
|
|
8070
|
+
for (const d of rows) {
|
|
8071
|
+
console.log(formatDelegationLine(d, sender.did, { fullIds: !!opts.fullIds }));
|
|
8072
|
+
}
|
|
8073
|
+
const lastId = rows[rows.length - 1].id;
|
|
8074
|
+
console.log(import_chalk35.default.dim(`
|
|
8075
|
+
${rows.length} active task(s). Paginate with --after ${lastId}.`));
|
|
8076
|
+
}
|
|
8077
|
+
function parseLimit7(raw) {
|
|
8078
|
+
if (raw === void 0) return 20;
|
|
8079
|
+
const n = Number(raw);
|
|
8080
|
+
if (!Number.isFinite(n) || !Number.isInteger(n) || n < 1 || n > 100) {
|
|
8081
|
+
throw new Error(`tasks: --limit must be an integer between 1 and 100 (got '${raw}')`);
|
|
8082
|
+
}
|
|
8083
|
+
return n;
|
|
8084
|
+
}
|
|
8085
|
+
function parseInflightState(raw) {
|
|
8086
|
+
if (raw === void 0) return void 0;
|
|
8087
|
+
if (!INFLIGHT.has(raw)) {
|
|
8088
|
+
throw new Error(`tasks: --state must be an in-flight state (offered|accepted|pending_lock_finalization|locked|disputing) (got '${raw}')`);
|
|
8089
|
+
}
|
|
8090
|
+
return raw;
|
|
8091
|
+
}
|
|
8092
|
+
|
|
8093
|
+
// src/commands/watch.ts
|
|
8094
|
+
var import_chalk36 = __toESM(require("chalk"));
|
|
8095
|
+
init_api();
|
|
8076
8096
|
function registerWatchCommand(root) {
|
|
8077
8097
|
root.command("watch").description("Live tail filtered to a single relationship (SSE). Server-side $match; only envelopes belonging to <rel-id> are streamed.").argument("<relationship-id>", "Relationship UUID to watch").option("--server <url>", "Override ARP server base URL").option("--from-did <did>", "Signer DID \u2014 required only if multiple agents are registered against this server").option("--from <name>", "Signer agent NAME (handle) \u2014 alternative to --from-did, resolved against your local agents").option("--verbose", "After each envelope, print the full JSON with a per-row label including eventId + serverEventHash", false).option("--json", "Machine-readable: one NDJSON object per line. Pipe-safe into `jq -c`.", false).option("--full-ids", "Print DIDs + serverEventHash in full (no truncation).", false).action(async (relationshipId, opts) => {
|
|
8078
8098
|
await runWatch(relationshipId, opts);
|
|
@@ -8082,9 +8102,9 @@ async function runWatch(relationshipId, opts) {
|
|
|
8082
8102
|
const local = resolveSenderAgent("watch", opts.server, opts.fromDid, opts.from);
|
|
8083
8103
|
const api = new ArpApiClient(opts.server);
|
|
8084
8104
|
if (!opts.json) {
|
|
8085
|
-
console.log(
|
|
8086
|
-
console.log(
|
|
8087
|
-
console.log(
|
|
8105
|
+
console.log(import_chalk36.default.dim(`Server: ${api.serverUrl}`));
|
|
8106
|
+
console.log(import_chalk36.default.dim(`Signer: ${local.did}`));
|
|
8107
|
+
console.log(import_chalk36.default.dim(`Watching: ${relationshipId}`));
|
|
8088
8108
|
}
|
|
8089
8109
|
const controller = new AbortController();
|
|
8090
8110
|
let userAborted = false;
|
|
@@ -8103,7 +8123,7 @@ async function runWatch(relationshipId, opts) {
|
|
|
8103
8123
|
}
|
|
8104
8124
|
if (event.type === "heartbeat") continue;
|
|
8105
8125
|
if (event.type === "connected") {
|
|
8106
|
-
console.log(
|
|
8126
|
+
console.log(import_chalk36.default.green(`\u25CF stream open \u2014 watching ${relationshipId}`));
|
|
8107
8127
|
continue;
|
|
8108
8128
|
}
|
|
8109
8129
|
if (event.type === "envelope") {
|
|
@@ -8117,7 +8137,7 @@ async function runWatch(relationshipId, opts) {
|
|
|
8117
8137
|
}
|
|
8118
8138
|
continue;
|
|
8119
8139
|
}
|
|
8120
|
-
console.log(
|
|
8140
|
+
console.log(import_chalk36.default.dim(`(unknown event: ${event.type})`));
|
|
8121
8141
|
}
|
|
8122
8142
|
if (!userAborted) {
|
|
8123
8143
|
throw new Error(`watch ${relationshipId}: stream ended unexpectedly (server may have restarted, or the change stream errored). Re-run to reconnect.`);
|
|
@@ -8125,7 +8145,7 @@ async function runWatch(relationshipId, opts) {
|
|
|
8125
8145
|
} catch (err) {
|
|
8126
8146
|
const name = err.name;
|
|
8127
8147
|
if (name === "AbortError" || userAborted) {
|
|
8128
|
-
if (!opts.json) console.log(
|
|
8148
|
+
if (!opts.json) console.log(import_chalk36.default.dim("\nstream closed."));
|
|
8129
8149
|
return;
|
|
8130
8150
|
}
|
|
8131
8151
|
throw err;
|
|
@@ -8139,21 +8159,21 @@ function formatWatchLine(ev, selfDid, opts = {}) {
|
|
|
8139
8159
|
const type = ev.type.padEnd(20);
|
|
8140
8160
|
const direction = directionLabel2(ev, selfDid, opts);
|
|
8141
8161
|
const hash = opts.fullIds ? ev.serverEventHash : hashHead4(ev.serverEventHash);
|
|
8142
|
-
return `${
|
|
8162
|
+
return `${import_chalk36.default.dim(`[${ts}]`)} ${type} ${direction} ${import_chalk36.default.cyan(hash)}`;
|
|
8143
8163
|
}
|
|
8144
8164
|
function directionLabel2(ev, selfDid, opts = {}) {
|
|
8145
8165
|
const senderHead = opts.fullIds ? ev.senderDid : didHead4(ev.senderDid);
|
|
8146
8166
|
const recipientHead = opts.fullIds ? ev.recipientDid : didHead4(ev.recipientDid);
|
|
8147
|
-
if (ev.senderDid === selfDid) return `${
|
|
8148
|
-
if (ev.recipientDid === selfDid) return `${
|
|
8149
|
-
return `${
|
|
8167
|
+
if (ev.senderDid === selfDid) return `${import_chalk36.default.bold("me")} \u2192 ${import_chalk36.default.dim(recipientHead)}`;
|
|
8168
|
+
if (ev.recipientDid === selfDid) return `${import_chalk36.default.dim(senderHead)} \u2192 ${import_chalk36.default.bold("me")}`;
|
|
8169
|
+
return `${import_chalk36.default.dim(senderHead)} \u2192 ${import_chalk36.default.dim(recipientHead)}`;
|
|
8150
8170
|
}
|
|
8151
8171
|
function didHead4(did) {
|
|
8152
8172
|
if (did.length <= 20) return did;
|
|
8153
8173
|
return `${did.slice(0, 20)}...`;
|
|
8154
8174
|
}
|
|
8155
8175
|
function hashHead4(hash) {
|
|
8156
|
-
if (!hash) return
|
|
8176
|
+
if (!hash) return import_chalk36.default.dim("(none)");
|
|
8157
8177
|
if (hash.length <= 14) return hash;
|
|
8158
8178
|
return `${hash.slice(0, 14)}...`;
|
|
8159
8179
|
}
|
|
@@ -8165,7 +8185,7 @@ function formatClock(iso) {
|
|
|
8165
8185
|
}
|
|
8166
8186
|
|
|
8167
8187
|
// src/commands/whoami.ts
|
|
8168
|
-
var
|
|
8188
|
+
var import_chalk37 = __toESM(require("chalk"));
|
|
8169
8189
|
init_api();
|
|
8170
8190
|
function registerWhoamiCommand(root) {
|
|
8171
8191
|
root.command("whoami").description(
|
|
@@ -8196,12 +8216,12 @@ function registerWhoamiCommand(root) {
|
|
|
8196
8216
|
if (opts.json) {
|
|
8197
8217
|
console.log(formatJson({ ...localJson, account: credential ? { wallet: credential.wallet } : null }));
|
|
8198
8218
|
} else {
|
|
8199
|
-
console.log(
|
|
8200
|
-
console.log(` DID: ${
|
|
8201
|
-
console.log(` Settlement pubkey: ${
|
|
8202
|
-
console.log(` Identity pubkey: ${
|
|
8219
|
+
console.log(import_chalk37.default.bold("Local agent:"));
|
|
8220
|
+
console.log(` DID: ${import_chalk37.default.cyan(local.did)}`);
|
|
8221
|
+
console.log(` Settlement pubkey: ${import_chalk37.default.cyan(local.settlementPublicKeyB58)}`);
|
|
8222
|
+
console.log(` Identity pubkey: ${import_chalk37.default.cyan(local.identityPublicKeyB58)}`);
|
|
8203
8223
|
if (local.name) console.log(` Name: ${local.name}`);
|
|
8204
|
-
console.log(` Account: ${credential ?
|
|
8224
|
+
console.log(` Account: ${credential ? import_chalk37.default.cyan(credential.wallet) : import_chalk37.default.dim("not logged in (heyarp login)")}`);
|
|
8205
8225
|
}
|
|
8206
8226
|
return;
|
|
8207
8227
|
}
|
|
@@ -8219,19 +8239,19 @@ function registerWhoamiCommand(root) {
|
|
|
8219
8239
|
if (opts.json) {
|
|
8220
8240
|
console.log(formatJson({ local: localJson, account, server: agent }));
|
|
8221
8241
|
} else {
|
|
8222
|
-
console.log(
|
|
8223
|
-
console.log(
|
|
8224
|
-
console.log(` DID: ${
|
|
8225
|
-
console.log(` Settlement pubkey: ${
|
|
8226
|
-
console.log(` Identity pubkey: ${
|
|
8227
|
-
console.log(
|
|
8242
|
+
console.log(import_chalk37.default.dim(`Server: ${api.serverUrl}`));
|
|
8243
|
+
console.log(import_chalk37.default.bold("\nLocal agent:"));
|
|
8244
|
+
console.log(` DID: ${import_chalk37.default.cyan(local.did)}`);
|
|
8245
|
+
console.log(` Settlement pubkey: ${import_chalk37.default.cyan(local.settlementPublicKeyB58)}`);
|
|
8246
|
+
console.log(` Identity pubkey: ${import_chalk37.default.cyan(local.identityPublicKeyB58)}`);
|
|
8247
|
+
console.log(import_chalk37.default.bold("\nAccount:"));
|
|
8228
8248
|
if (account) {
|
|
8229
|
-
console.log(` Wallet: ${
|
|
8249
|
+
console.log(` Wallet: ${import_chalk37.default.cyan(account.wallet)}`);
|
|
8230
8250
|
console.log(` Agents registered: ${account.agentCount}`);
|
|
8231
8251
|
} else {
|
|
8232
|
-
console.log(` ${
|
|
8252
|
+
console.log(` ${import_chalk37.default.dim("not logged in (heyarp login)")}`);
|
|
8233
8253
|
}
|
|
8234
|
-
console.log(
|
|
8254
|
+
console.log(import_chalk37.default.bold("\nServer profile:"));
|
|
8235
8255
|
console.log(formatJson(agent));
|
|
8236
8256
|
}
|
|
8237
8257
|
} catch (err) {
|
|
@@ -8242,13 +8262,13 @@ function registerWhoamiCommand(root) {
|
|
|
8242
8262
|
}
|
|
8243
8263
|
|
|
8244
8264
|
// src/commands/whois.ts
|
|
8245
|
-
var
|
|
8246
|
-
var
|
|
8265
|
+
var import_sdk31 = require("@heyanon-arp/sdk");
|
|
8266
|
+
var import_chalk38 = __toESM(require("chalk"));
|
|
8247
8267
|
init_api();
|
|
8248
8268
|
function registerWhoisCommand(root) {
|
|
8249
8269
|
root.command("whois").description("Resolve an agent name (handle) or DID to its public profile \u2014 DID, description, reputation, liveness.").argument("<name-or-did>", "Agent name (handle) or DID (did:arp:...)").option("--server <url>", "Override ARP server base URL").option("--json", "Emit the full composed profile (DiscoveryProfile) as a single JSON object on stdout.", false).action(async (input, opts) => {
|
|
8250
8270
|
const api = new ArpApiClient(opts.server);
|
|
8251
|
-
progress(opts.json,
|
|
8271
|
+
progress(opts.json, import_chalk38.default.dim(`Server: ${api.serverUrl}`));
|
|
8252
8272
|
const profile = await resolveProfile(api, input);
|
|
8253
8273
|
if (opts.json) {
|
|
8254
8274
|
jsonOut(profile);
|
|
@@ -8259,31 +8279,31 @@ function registerWhoisCommand(root) {
|
|
|
8259
8279
|
}
|
|
8260
8280
|
async function resolveProfile(api, input) {
|
|
8261
8281
|
if (input.startsWith("did:arp:")) {
|
|
8262
|
-
if (!(0,
|
|
8282
|
+
if (!(0, import_sdk31.isValidDid)(input)) {
|
|
8263
8283
|
throw new Error(`whois: '${input}' starts with did:arp: but is not a valid DID (base58btc-encoded 32-byte Ed25519 pubkey).`);
|
|
8264
8284
|
}
|
|
8265
8285
|
return api.discoverProfile(input);
|
|
8266
8286
|
}
|
|
8267
|
-
const name = (0,
|
|
8268
|
-
if (!(0,
|
|
8287
|
+
const name = (0, import_sdk31.normalizeName)(input);
|
|
8288
|
+
if (!(0, import_sdk31.isValidAgentName)(name)) {
|
|
8269
8289
|
throw new Error(`whois: '${input}' is neither a DID (did:arp:...) nor a valid agent name (lowercase a-z0-9_, 3-32 chars).`);
|
|
8270
8290
|
}
|
|
8271
8291
|
return api.discoverByName(name);
|
|
8272
8292
|
}
|
|
8273
8293
|
function printProfile(p) {
|
|
8274
|
-
console.log(`${
|
|
8275
|
-
console.log(`${
|
|
8276
|
-
if (p.description) console.log(`${
|
|
8277
|
-
if (p.tags.length > 0) console.log(`${
|
|
8278
|
-
console.log(`${
|
|
8294
|
+
console.log(`${import_chalk38.default.bold("Name")}: ${import_chalk38.default.cyan(p.name ?? "(unnamed)")}`);
|
|
8295
|
+
console.log(`${import_chalk38.default.bold("DID")}: ${import_chalk38.default.cyan(p.did)}`);
|
|
8296
|
+
if (p.description) console.log(`${import_chalk38.default.bold("Description")}: ${p.description}`);
|
|
8297
|
+
if (p.tags.length > 0) console.log(`${import_chalk38.default.bold("Tags")}: ${p.tags.join(", ")}`);
|
|
8298
|
+
console.log(`${import_chalk38.default.bold("Registered")}: ${p.registeredAt}`);
|
|
8279
8299
|
const rep = p.reputation;
|
|
8280
|
-
console.log(`${
|
|
8281
|
-
console.log(`${
|
|
8300
|
+
console.log(`${import_chalk38.default.bold("Reputation")}: composite ${rep.scores.composite}/100${rep.computed ? "" : import_chalk38.default.dim(" (cold-start \u2014 no settled cycles yet)")}`);
|
|
8301
|
+
console.log(`${import_chalk38.default.bold("Online")}: ${p.liveness.online ? import_chalk38.default.green("yes") : import_chalk38.default.dim("no")}`);
|
|
8282
8302
|
}
|
|
8283
8303
|
|
|
8284
8304
|
// src/commands/work.ts
|
|
8285
|
-
var
|
|
8286
|
-
var
|
|
8305
|
+
var import_sdk32 = require("@heyanon-arp/sdk");
|
|
8306
|
+
var import_chalk39 = __toESM(require("chalk"));
|
|
8287
8307
|
init_api();
|
|
8288
8308
|
function registerWorkCommands(root) {
|
|
8289
8309
|
const cmd = root.command("work").description("Work envelopes inside an ACCEPTED delegation: request / respond");
|
|
@@ -8297,7 +8317,7 @@ function registerRequest(parent) {
|
|
|
8297
8317
|
).option(
|
|
8298
8318
|
"--params-file <path>",
|
|
8299
8319
|
"Read the JSON payload from a file. Mutually exclusive with --params. Use this for any payload large or quote-heavy enough that `--params '{...}'` would fight your shell."
|
|
8300
|
-
).option("--ttl <seconds>", `Envelope TTL in seconds (max ${
|
|
8320
|
+
).option("--ttl <seconds>", `Envelope TTL in seconds (max ${import_sdk32.MAX_ENVELOPE_TTL_SECONDS} = 24h)`, "3600").option("--verbose", "Print the full envelope before sending and the full server response. Mutually exclusive with --json.", false).option(
|
|
8301
8321
|
"--json",
|
|
8302
8322
|
'Machine-readable mode \u2014 emit a single JSON object on stdout ({ok, action:"work_request", requestId, delegationId, eventId, relationshipId, relationshipEventIndex, serverTimestamp, serverEventHash}). Prelude + reply hints move to stderr; on failure stderr carries `{code, message}`. Mutually exclusive with --verbose.',
|
|
8303
8323
|
false
|
|
@@ -8324,11 +8344,11 @@ async function runRequest(recipientDid, delegationId, opts) {
|
|
|
8324
8344
|
params
|
|
8325
8345
|
};
|
|
8326
8346
|
const body = { type: "work_request", content };
|
|
8327
|
-
progress(opts.json,
|
|
8328
|
-
progress(opts.json,
|
|
8329
|
-
progress(opts.json,
|
|
8330
|
-
progress(opts.json,
|
|
8331
|
-
progress(opts.json,
|
|
8347
|
+
progress(opts.json, import_chalk39.default.dim(`Server: ${api.serverUrl}`));
|
|
8348
|
+
progress(opts.json, import_chalk39.default.dim(`Sender: ${sender.did}`));
|
|
8349
|
+
progress(opts.json, import_chalk39.default.dim(`Recipient: ${recipientDid}`));
|
|
8350
|
+
progress(opts.json, import_chalk39.default.dim(`Delegation: ${delegationId}`));
|
|
8351
|
+
progress(opts.json, import_chalk39.default.dim(`Request id: ${requestId}`));
|
|
8332
8352
|
const result = await sendWorkEnvelope({ api, sender, recipientDid, body, ttlSeconds, verbose: opts.verbose, server: opts.server });
|
|
8333
8353
|
if (opts.json) {
|
|
8334
8354
|
jsonOut({
|
|
@@ -8345,10 +8365,10 @@ async function runRequest(recipientDid, delegationId, opts) {
|
|
|
8345
8365
|
});
|
|
8346
8366
|
} else {
|
|
8347
8367
|
printIngestResult3(result);
|
|
8348
|
-
console.log(
|
|
8368
|
+
console.log(import_chalk39.default.dim(`
|
|
8349
8369
|
The payee can reply with:`));
|
|
8350
|
-
console.log(
|
|
8351
|
-
console.log(
|
|
8370
|
+
console.log(import_chalk39.default.dim(` heyarp work respond ${result.relationshipId} ${delegationId} ${requestId} --output '<json>'`));
|
|
8371
|
+
console.log(import_chalk39.default.dim(` heyarp work respond ${result.relationshipId} ${delegationId} ${requestId} --error CODE:message`));
|
|
8352
8372
|
}
|
|
8353
8373
|
}
|
|
8354
8374
|
function registerRespond(parent) {
|
|
@@ -8383,13 +8403,13 @@ async function runRespond(relationshipId, delegationId, requestId, opts) {
|
|
|
8383
8403
|
...responsePayload
|
|
8384
8404
|
};
|
|
8385
8405
|
const body = { type: "work_response", content };
|
|
8386
|
-
progress(opts.json,
|
|
8387
|
-
progress(opts.json,
|
|
8388
|
-
progress(opts.json,
|
|
8389
|
-
progress(opts.json,
|
|
8390
|
-
progress(opts.json,
|
|
8391
|
-
progress(opts.json,
|
|
8392
|
-
progress(opts.json,
|
|
8406
|
+
progress(opts.json, import_chalk39.default.dim(`Server: ${api.serverUrl}`));
|
|
8407
|
+
progress(opts.json, import_chalk39.default.dim(`Sender: ${sender.did}`));
|
|
8408
|
+
progress(opts.json, import_chalk39.default.dim(`Recipient: ${recipientDid}`));
|
|
8409
|
+
progress(opts.json, import_chalk39.default.dim(`Relationship: ${relationshipId}`));
|
|
8410
|
+
progress(opts.json, import_chalk39.default.dim(`Delegation: ${delegationId}`));
|
|
8411
|
+
progress(opts.json, import_chalk39.default.dim(`Request id: ${requestId}`));
|
|
8412
|
+
progress(opts.json, import_chalk39.default.dim(`Outcome: ${responsePayload.output ? "success" : "error"}`));
|
|
8393
8413
|
const result = await sendWorkEnvelope({ api, sender, recipientDid, body, ttlSeconds, verbose: opts.verbose, server: opts.server });
|
|
8394
8414
|
if (opts.json) {
|
|
8395
8415
|
jsonOut({
|
|
@@ -8411,26 +8431,26 @@ async function runRespond(relationshipId, delegationId, requestId, opts) {
|
|
|
8411
8431
|
async function sendWorkEnvelope(args) {
|
|
8412
8432
|
const nextSequence = (args.sender.lastSenderSequence ?? 0) + 1;
|
|
8413
8433
|
const protectedBlock = {
|
|
8414
|
-
protocol_version:
|
|
8415
|
-
purpose:
|
|
8416
|
-
message_id: (0,
|
|
8434
|
+
protocol_version: import_sdk32.CURRENT_PROTOCOL_VERSION,
|
|
8435
|
+
purpose: import_sdk32.Purpose.ENVELOPE,
|
|
8436
|
+
message_id: (0, import_sdk32.uuidV4)(),
|
|
8417
8437
|
sender_did: args.sender.did,
|
|
8418
8438
|
recipient_did: args.recipientDid,
|
|
8419
8439
|
relationship_id: null,
|
|
8420
8440
|
sender_sequence: nextSequence,
|
|
8421
|
-
sender_nonce: (0,
|
|
8422
|
-
timestamp: (0,
|
|
8423
|
-
expires_at: (0,
|
|
8441
|
+
sender_nonce: (0, import_sdk32.senderNonce)(),
|
|
8442
|
+
timestamp: (0, import_sdk32.rfc3339)(),
|
|
8443
|
+
expires_at: (0, import_sdk32.expiresAt)(args.ttlSeconds),
|
|
8424
8444
|
delivery_id: null
|
|
8425
8445
|
};
|
|
8426
8446
|
const signer = makeSigner(args.sender);
|
|
8427
|
-
const envelope = (0,
|
|
8447
|
+
const envelope = (0, import_sdk32.signEnvelope)({
|
|
8428
8448
|
protected: protectedBlock,
|
|
8429
8449
|
body: args.body,
|
|
8430
8450
|
identitySecretKey: signer.identitySecretKey
|
|
8431
8451
|
});
|
|
8432
8452
|
if (args.verbose) {
|
|
8433
|
-
console.log(
|
|
8453
|
+
console.log(import_chalk39.default.bold("\nEnvelope (pre-send):"));
|
|
8434
8454
|
console.log(formatJson(envelope));
|
|
8435
8455
|
}
|
|
8436
8456
|
try {
|
|
@@ -8438,7 +8458,7 @@ async function sendWorkEnvelope(args) {
|
|
|
8438
8458
|
updateAgentLocal(args.server, args.sender.did, { lastSenderSequence: nextSequence });
|
|
8439
8459
|
return result;
|
|
8440
8460
|
} catch (err) {
|
|
8441
|
-
if (err instanceof ApiError && (0,
|
|
8461
|
+
if (err instanceof ApiError && (0, import_sdk32.isPostCommitErrorCode)(err.payload.code)) {
|
|
8442
8462
|
updateAgentLocal(args.server, args.sender.did, { lastSenderSequence: nextSequence });
|
|
8443
8463
|
}
|
|
8444
8464
|
throw err;
|
|
@@ -8450,7 +8470,7 @@ async function resolveResponseRecipient(cmdName, api, signer, args) {
|
|
|
8450
8470
|
const page = await api.listWorkLogs(args.relationshipId, signer, { delegationId: args.delegationId, limit: 100, after });
|
|
8451
8471
|
const row = page.find((w) => w.requestId === args.requestId);
|
|
8452
8472
|
if (row) {
|
|
8453
|
-
if (row.state !==
|
|
8473
|
+
if (row.state !== import_sdk32.WorkLogStates.REQUESTED) {
|
|
8454
8474
|
throw new Error(
|
|
8455
8475
|
`${cmdName}: work_request ${args.requestId} for delegation ${args.delegationId} is already in state '${row.state}' \u2014 only requests in state 'requested' can be responded to.`
|
|
8456
8476
|
);
|
|
@@ -8470,12 +8490,12 @@ async function resolveResponseRecipient(cmdName, api, signer, args) {
|
|
|
8470
8490
|
);
|
|
8471
8491
|
}
|
|
8472
8492
|
function printIngestResult3(result) {
|
|
8473
|
-
console.log(
|
|
8474
|
-
console.log(`${
|
|
8475
|
-
console.log(`${
|
|
8476
|
-
console.log(`${
|
|
8477
|
-
console.log(`${
|
|
8478
|
-
console.log(`${
|
|
8493
|
+
console.log(import_chalk39.default.green("\nDelivered."));
|
|
8494
|
+
console.log(`${import_chalk39.default.bold("Event id")}: ${import_chalk39.default.cyan(result.eventId)}`);
|
|
8495
|
+
console.log(`${import_chalk39.default.bold("Relationship id")}: ${import_chalk39.default.cyan(result.relationshipId)}`);
|
|
8496
|
+
console.log(`${import_chalk39.default.bold("Chain index")}: ${import_chalk39.default.cyan(String(result.relationshipEventIndex))}`);
|
|
8497
|
+
console.log(`${import_chalk39.default.bold("Server timestamp")}: ${import_chalk39.default.cyan(result.serverTimestamp)}`);
|
|
8498
|
+
console.log(`${import_chalk39.default.bold("Server event hash")}: ${import_chalk39.default.cyan(result.serverEventHash)}`);
|
|
8479
8499
|
}
|
|
8480
8500
|
function parseJsonObject(cmdName, flagName, raw) {
|
|
8481
8501
|
let parsed;
|
|
@@ -8567,7 +8587,7 @@ function parseTtl5(cmdName, raw) {
|
|
|
8567
8587
|
}
|
|
8568
8588
|
function parseRequestId(cmdName, raw) {
|
|
8569
8589
|
if (raw === void 0 || raw === "") {
|
|
8570
|
-
return (0,
|
|
8590
|
+
return (0, import_sdk32.uuidV4)();
|
|
8571
8591
|
}
|
|
8572
8592
|
if (raw.length === 0) {
|
|
8573
8593
|
throw new Error(`${cmdName}: --request-id must be a non-empty string`);
|
|
@@ -8576,10 +8596,10 @@ function parseRequestId(cmdName, raw) {
|
|
|
8576
8596
|
}
|
|
8577
8597
|
|
|
8578
8598
|
// src/commands/work-list.ts
|
|
8579
|
-
var
|
|
8580
|
-
var
|
|
8599
|
+
var import_sdk33 = require("@heyanon-arp/sdk");
|
|
8600
|
+
var import_chalk40 = __toESM(require("chalk"));
|
|
8581
8601
|
init_api();
|
|
8582
|
-
var ALLOWED_STATES3 = new Set(
|
|
8602
|
+
var ALLOWED_STATES3 = new Set(import_sdk33.WORK_LOG_STATES);
|
|
8583
8603
|
function registerWorkListCommand(root) {
|
|
8584
8604
|
root.command("work-list").description("List work-log rows for a relationship (one row per (delegationId, requestId), oldest-first)").argument("<relationship-id>", "Relationship UUID").option("--server <url>", "Override ARP server base URL").option("--state <s>", "Filter by exact state (requested|responded)").option("--delegation-id <uuid>", "Narrow to work-logs operating under a specific delegation id").option("--after <id>", "Cursor: pass the previous page's last `id` to fetch the next page").option("--limit <n>", "Max rows to return (1..100)", "20").option("--from-did <did>", "Signer DID \u2014 required only if multiple agents are registered against this server").option("--from <name>", "Signer agent NAME (handle) \u2014 alternative to --from-did, resolved against your local agents").option(
|
|
8585
8605
|
"--verbose",
|
|
@@ -8599,14 +8619,14 @@ async function runWorkList(relationshipId, opts) {
|
|
|
8599
8619
|
"work-list: --verbose and --json are mutually exclusive. --json already emits the full payload; --verbose adds the framed dump on top of the human summary."
|
|
8600
8620
|
);
|
|
8601
8621
|
}
|
|
8602
|
-
const limit =
|
|
8622
|
+
const limit = parseLimit8(opts.limit);
|
|
8603
8623
|
const state = parseState3(opts.state);
|
|
8604
8624
|
const api = new ArpApiClient(opts.server);
|
|
8605
8625
|
const sender = resolveSenderAgent("work-list", opts.server, opts.fromDid, opts.from);
|
|
8606
8626
|
if (!opts.json) {
|
|
8607
|
-
console.log(
|
|
8608
|
-
console.log(
|
|
8609
|
-
console.log(
|
|
8627
|
+
console.log(import_chalk40.default.dim(`Server: ${api.serverUrl}`));
|
|
8628
|
+
console.log(import_chalk40.default.dim(`Signer: ${sender.did}`));
|
|
8629
|
+
console.log(import_chalk40.default.dim(`Relationship: ${relationshipId}`));
|
|
8610
8630
|
}
|
|
8611
8631
|
const query = { limit };
|
|
8612
8632
|
if (state) query.state = state;
|
|
@@ -8619,7 +8639,7 @@ async function runWorkList(relationshipId, opts) {
|
|
|
8619
8639
|
return;
|
|
8620
8640
|
}
|
|
8621
8641
|
if (rows.length === 0) {
|
|
8622
|
-
console.log(
|
|
8642
|
+
console.log(import_chalk40.default.dim("\n(no work-logs for this relationship)"));
|
|
8623
8643
|
return;
|
|
8624
8644
|
}
|
|
8625
8645
|
console.log("");
|
|
@@ -8636,36 +8656,36 @@ async function runWorkList(relationshipId, opts) {
|
|
|
8636
8656
|
}));
|
|
8637
8657
|
}
|
|
8638
8658
|
const lastId = rows[rows.length - 1].id;
|
|
8639
|
-
console.log(
|
|
8659
|
+
console.log(import_chalk40.default.dim(`
|
|
8640
8660
|
${rows.length} work-log row(s). Paginate with --after ${lastId}.`));
|
|
8641
8661
|
}
|
|
8642
8662
|
function formatWorkLogLine(w, selfDid, opts = {}) {
|
|
8643
8663
|
const delegationPart = opts.fullIds ? w.delegationId : idHead3(w.delegationId);
|
|
8644
8664
|
const requestPart = opts.fullIds ? w.requestId : truncate3(w.requestId, 16);
|
|
8645
|
-
const id =
|
|
8665
|
+
const id = import_chalk40.default.bold(`${delegationPart}/${requestPart}`);
|
|
8646
8666
|
const state = colorState2(w.state).padEnd(stateColumnWidth2());
|
|
8647
8667
|
const peerCallerHead = opts.fullIds ? w.callerDid : didHead5(w.callerDid);
|
|
8648
8668
|
const peerPayeeHead = opts.fullIds ? w.payeeDid : didHead5(w.payeeDid);
|
|
8649
|
-
const direction = w.callerDid === selfDid ? `${
|
|
8669
|
+
const direction = w.callerDid === selfDid ? `${import_chalk40.default.bold("me")} \u2192 ${import_chalk40.default.dim(peerPayeeHead)}` : `${import_chalk40.default.dim(peerCallerHead)} \u2192 ${import_chalk40.default.bold("me")}`;
|
|
8650
8670
|
const outcome = formatOutcome(w);
|
|
8651
8671
|
return `${id} ${state} ${direction} ${outcome}`;
|
|
8652
8672
|
}
|
|
8653
8673
|
function colorState2(s) {
|
|
8654
8674
|
switch (s) {
|
|
8655
|
-
case
|
|
8656
|
-
return
|
|
8657
|
-
case
|
|
8658
|
-
return
|
|
8675
|
+
case import_sdk33.WorkLogStates.REQUESTED:
|
|
8676
|
+
return import_chalk40.default.yellow("requested");
|
|
8677
|
+
case import_sdk33.WorkLogStates.RESPONDED:
|
|
8678
|
+
return import_chalk40.default.green("responded");
|
|
8659
8679
|
}
|
|
8660
8680
|
}
|
|
8661
8681
|
function stateColumnWidth2() {
|
|
8662
8682
|
return 9;
|
|
8663
8683
|
}
|
|
8664
8684
|
function formatOutcome(w) {
|
|
8665
|
-
if (w.state ===
|
|
8666
|
-
if (w.responseError) return
|
|
8667
|
-
if (w.responseOutput) return
|
|
8668
|
-
return
|
|
8685
|
+
if (w.state === import_sdk33.WorkLogStates.REQUESTED) return import_chalk40.default.dim("(in flight)");
|
|
8686
|
+
if (w.responseError) return import_chalk40.default.red(`error ${w.responseError.code}: ${truncate3(w.responseError.message, 32)}`);
|
|
8687
|
+
if (w.responseOutput) return import_chalk40.default.cyan("ok");
|
|
8688
|
+
return import_chalk40.default.dim("(empty response)");
|
|
8669
8689
|
}
|
|
8670
8690
|
function idHead3(id) {
|
|
8671
8691
|
if (id.length <= 12) return id;
|
|
@@ -8686,7 +8706,7 @@ function parseState3(raw) {
|
|
|
8686
8706
|
}
|
|
8687
8707
|
return raw;
|
|
8688
8708
|
}
|
|
8689
|
-
function
|
|
8709
|
+
function parseLimit8(raw) {
|
|
8690
8710
|
if (raw === void 0) return 20;
|
|
8691
8711
|
const n = Number(raw);
|
|
8692
8712
|
if (!Number.isFinite(n) || !Number.isInteger(n) || n < 1 || n > 100) {
|
|
@@ -8863,6 +8883,7 @@ async function main() {
|
|
|
8863
8883
|
registerEnvelopeCommand(program);
|
|
8864
8884
|
registerDelegationCommands(program);
|
|
8865
8885
|
registerDelegationsCommand(program);
|
|
8886
|
+
registerTasksCommand(program);
|
|
8866
8887
|
registerWorkCommands(program);
|
|
8867
8888
|
registerWorkListCommand(program);
|
|
8868
8889
|
registerReceiptCommands(program);
|
|
@@ -8870,7 +8891,7 @@ async function main() {
|
|
|
8870
8891
|
registerReputationCommand(program);
|
|
8871
8892
|
registerStatsCommand(program);
|
|
8872
8893
|
registerWalletCommands(program);
|
|
8873
|
-
(0,
|
|
8894
|
+
(0, import_shield4.installMiddleware)(program);
|
|
8874
8895
|
try {
|
|
8875
8896
|
await program.parseAsync(process.argv);
|
|
8876
8897
|
} catch (err) {
|