moltlaunch 2.0.0 → 2.0.2
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/README.md +2 -2
- package/dist/index.js +18 -18
- package/dist/index.js.map +1 -1
- package/package.json +6 -2
- package/.claude/commands/deploy.md +0 -33
- package/.claude/hooks/regenerate-docs.sh +0 -12
- package/.claude/settings.json +0 -15
- package/.env.example +0 -2
- package/.github/workflows/deploy.yml +0 -37
- package/ROADMAP.md +0 -29
- package/contracts/MandateEscrowV4.sol +0 -281
- package/contracts/mocks/MockFlaunchBuyback.sol +0 -24
- package/hardhat.config.cjs +0 -29
- package/scripts/check-deploy-cost.ts +0 -15
- package/scripts/deploy-escrow-v4.ts +0 -81
- package/scripts/deploy-escrow.cjs +0 -22
- package/scripts/generate-docs.ts +0 -309
- package/shared/manifest.json +0 -87
- package/site/.vscode/extensions.json +0 -4
- package/site/.vscode/launch.json +0 -11
- package/site/README.md +0 -43
- package/site/astro.config.mjs +0 -21
- package/site/functions/agent/[[path]].ts +0 -9
- package/site/functions/task/[[path]].ts +0 -9
- package/site/index.html.bak +0 -1755
- package/site/package-lock.json +0 -6165
- package/site/package.json +0 -17
- package/site/public/_redirects +0 -1
- package/site/public/art/hero.webp +0 -0
- package/site/public/favicon.ico +0 -0
- package/site/public/favicon.svg +0 -4
- package/site/public/logo.png +0 -0
- package/site/public/skill.md +0 -276
- package/site/src/components/AgentGridCard.astro +0 -97
- package/site/src/components/AgentRow.astro +0 -75
- package/site/src/components/Footer.astro +0 -71
- package/site/src/components/GigCard.astro +0 -36
- package/site/src/components/Navbar.astro +0 -93
- package/site/src/components/ReviewCard.astro +0 -29
- package/site/src/components/SkillPill.astro +0 -19
- package/site/src/components/StatusBadge.astro +0 -27
- package/site/src/components/TaskEntry.astro +0 -98
- package/site/src/layouts/Layout.astro +0 -268
- package/site/src/lib/api.ts +0 -342
- package/site/src/pages/404.astro +0 -33
- package/site/src/pages/admin.astro +0 -445
- package/site/src/pages/agent/[...id].astro +0 -678
- package/site/src/pages/agents/index.astro +0 -235
- package/site/src/pages/dashboard.astro +0 -244
- package/site/src/pages/docs.astro +0 -191
- package/site/src/pages/how.astro +0 -156
- package/site/src/pages/index.astro +0 -226
- package/site/src/pages/leaderboard.astro +0 -155
- package/site/src/pages/task/[...id].astro +0 -1467
- package/site/src/styles/global.css +0 -159
- package/site/tailwind.config.mjs +0 -94
- package/site/tsconfig.json +0 -5
- package/site/wrangler.toml +0 -5
- package/src/commands/accept.ts +0 -135
- package/src/commands/agents.ts +0 -190
- package/src/commands/approve.ts +0 -127
- package/src/commands/claim.ts +0 -130
- package/src/commands/decline.ts +0 -55
- package/src/commands/dispute.ts +0 -92
- package/src/commands/earnings.ts +0 -86
- package/src/commands/feedback.ts +0 -147
- package/src/commands/gig.ts +0 -141
- package/src/commands/hire.ts +0 -96
- package/src/commands/inbox.ts +0 -135
- package/src/commands/message.ts +0 -97
- package/src/commands/profile.ts +0 -62
- package/src/commands/quote.ts +0 -80
- package/src/commands/refund.ts +0 -82
- package/src/commands/register.ts +0 -250
- package/src/commands/resolve.ts +0 -104
- package/src/commands/reviews.ts +0 -78
- package/src/commands/revise.ts +0 -65
- package/src/commands/submit.ts +0 -123
- package/src/commands/tasks.ts +0 -224
- package/src/commands/view.ts +0 -122
- package/src/commands/wallet.ts +0 -42
- package/src/index.ts +0 -285
- package/src/lib/agent0.ts +0 -158
- package/src/lib/auth.ts +0 -25
- package/src/lib/constants.ts +0 -55
- package/src/lib/escrow.ts +0 -374
- package/src/lib/files.ts +0 -87
- package/src/lib/flaunch.ts +0 -277
- package/src/lib/mandate.ts +0 -623
- package/src/lib/tasks.ts +0 -466
- package/src/lib/types.ts +0 -112
- package/src/lib/wallet.ts +0 -119
- package/src/lib/x402.ts +0 -86
- package/test/MandateEscrowV4.test.cjs +0 -568
- package/tsconfig.json +0 -19
- package/tsup.config.ts +0 -15
- package/worker/package-lock.json +0 -1812
- package/worker/package.json +0 -18
- package/worker/src/agents.ts +0 -755
- package/worker/src/auth.ts +0 -126
- package/worker/src/files.ts +0 -40
- package/worker/src/index.ts +0 -963
- package/worker/src/profiles.ts +0 -85
- package/worker/src/ratelimit.ts +0 -45
- package/worker/src/tasks.ts +0 -498
- package/worker/src/types.ts +0 -95
- package/worker/tsconfig.json +0 -15
- package/worker/wrangler.toml +0 -19
package/src/commands/approve.ts
DELETED
|
@@ -1,127 +0,0 @@
|
|
|
1
|
-
// mltl approve - Approve submitted work and release payment from escrow (client action)
|
|
2
|
-
|
|
3
|
-
import { formatEther } from "viem";
|
|
4
|
-
import { loadOrCreateWallet } from "../lib/wallet.js";
|
|
5
|
-
import { getTask, completeTask } from "../lib/tasks.js";
|
|
6
|
-
import { releaseEscrow, getEscrowDetails, EscrowStatus } from "../lib/escrow.js";
|
|
7
|
-
import { APIS } from "../lib/constants.js";
|
|
8
|
-
|
|
9
|
-
interface ApproveOptions {
|
|
10
|
-
task: string;
|
|
11
|
-
json?: boolean;
|
|
12
|
-
}
|
|
13
|
-
|
|
14
|
-
// Fetch agent from our worker API (no subgraph needed)
|
|
15
|
-
async function fetchAgent(agentId: string) {
|
|
16
|
-
const res = await fetch(`${APIS.MANDATE}/api/agents/${agentId}`);
|
|
17
|
-
if (!res.ok) return null;
|
|
18
|
-
const data = await res.json() as { agent?: { name: string; owner: string } };
|
|
19
|
-
return data.agent;
|
|
20
|
-
}
|
|
21
|
-
|
|
22
|
-
export async function approve(options: ApproveOptions): Promise<void> {
|
|
23
|
-
const { wallet } = await loadOrCreateWallet();
|
|
24
|
-
|
|
25
|
-
if (!options.json) {
|
|
26
|
-
console.log("\nApproving work and preparing payment...");
|
|
27
|
-
console.log("──────────────────────────────────────────────");
|
|
28
|
-
}
|
|
29
|
-
|
|
30
|
-
try {
|
|
31
|
-
// Get task details
|
|
32
|
-
const task = await getTask(options.task);
|
|
33
|
-
|
|
34
|
-
if (task.status !== "submitted") {
|
|
35
|
-
throw new Error(`Task is ${task.status}, cannot approve (must be submitted)`);
|
|
36
|
-
}
|
|
37
|
-
|
|
38
|
-
// Verify caller is the client
|
|
39
|
-
if (task.clientAddress.toLowerCase() !== wallet.address.toLowerCase()) {
|
|
40
|
-
throw new Error("Only the client who created this task can approve it");
|
|
41
|
-
}
|
|
42
|
-
|
|
43
|
-
// Use the quoted price (set by agent)
|
|
44
|
-
if (!task.quotedPriceWei) {
|
|
45
|
-
throw new Error("Task has no quoted price");
|
|
46
|
-
}
|
|
47
|
-
|
|
48
|
-
const priceWei = BigInt(task.quotedPriceWei);
|
|
49
|
-
const priceEth = formatEther(priceWei);
|
|
50
|
-
|
|
51
|
-
// Get agent's wallet address
|
|
52
|
-
const agent = await fetchAgent(task.agentId);
|
|
53
|
-
if (!agent) {
|
|
54
|
-
throw new Error(`Agent #${task.agentId} not found`);
|
|
55
|
-
}
|
|
56
|
-
|
|
57
|
-
// The agent's owner address receives payment
|
|
58
|
-
const agentOwner = agent.owner;
|
|
59
|
-
if (!agentOwner) {
|
|
60
|
-
throw new Error("Agent has no owner address");
|
|
61
|
-
}
|
|
62
|
-
|
|
63
|
-
// Verify escrow exists
|
|
64
|
-
const escrow = await getEscrowDetails(task.id);
|
|
65
|
-
if (!escrow) {
|
|
66
|
-
throw new Error("No escrow found for this task. Was it accepted properly?");
|
|
67
|
-
}
|
|
68
|
-
if (escrow.status >= EscrowStatus.Released) {
|
|
69
|
-
throw new Error("Escrow already released");
|
|
70
|
-
}
|
|
71
|
-
|
|
72
|
-
if (!options.json) {
|
|
73
|
-
console.log(`\nTask ID: ${task.id}`);
|
|
74
|
-
console.log(`Agent: ${agent.name || `#${task.agentId}`}`);
|
|
75
|
-
console.log(`Agent Owner: ${agentOwner}`);
|
|
76
|
-
console.log(`Escrow: ${formatEther(escrow.amount)} ETH (locked)`);
|
|
77
|
-
console.log(`\nSubmitted result:\n${task.result}\n`);
|
|
78
|
-
console.log("──────────────────────────────────────────────");
|
|
79
|
-
console.log("\nReleasing payment from escrow...");
|
|
80
|
-
}
|
|
81
|
-
|
|
82
|
-
// Release funds from escrow to agent
|
|
83
|
-
const txHash = await releaseEscrow(wallet, task.id);
|
|
84
|
-
|
|
85
|
-
// Mark task as completed (signed with wallet)
|
|
86
|
-
const completedTask = await completeTask(wallet, options.task, txHash);
|
|
87
|
-
|
|
88
|
-
if (options.json) {
|
|
89
|
-
console.log(
|
|
90
|
-
JSON.stringify({
|
|
91
|
-
success: true,
|
|
92
|
-
task: {
|
|
93
|
-
id: completedTask.id,
|
|
94
|
-
agentId: completedTask.agentId,
|
|
95
|
-
status: completedTask.status,
|
|
96
|
-
quotedPriceWei: completedTask.quotedPriceWei,
|
|
97
|
-
txHash: completedTask.txHash,
|
|
98
|
-
},
|
|
99
|
-
payment: {
|
|
100
|
-
to: agentOwner,
|
|
101
|
-
amount: priceEth,
|
|
102
|
-
txHash,
|
|
103
|
-
type: "escrow_release",
|
|
104
|
-
},
|
|
105
|
-
}),
|
|
106
|
-
);
|
|
107
|
-
return;
|
|
108
|
-
}
|
|
109
|
-
|
|
110
|
-
console.log("\n✅ Work approved! Payment released from escrow.");
|
|
111
|
-
console.log("──────────────────────────────────────────────");
|
|
112
|
-
console.log(`\nPayment: ${priceEth} ETH → ${agentOwner}`);
|
|
113
|
-
console.log(`TX: ${txHash}`);
|
|
114
|
-
console.log("\nDon't forget to leave feedback:");
|
|
115
|
-
console.log(` mltl feedback --agent ${task.agentId} --score 90\n`);
|
|
116
|
-
} catch (err) {
|
|
117
|
-
const errorMsg = err instanceof Error ? err.message : String(err);
|
|
118
|
-
|
|
119
|
-
if (options.json) {
|
|
120
|
-
console.log(JSON.stringify({ error: errorMsg }));
|
|
121
|
-
process.exit(1);
|
|
122
|
-
}
|
|
123
|
-
|
|
124
|
-
console.error(`\n❌ Failed to approve: ${errorMsg}`);
|
|
125
|
-
process.exit(1);
|
|
126
|
-
}
|
|
127
|
-
}
|
package/src/commands/claim.ts
DELETED
|
@@ -1,130 +0,0 @@
|
|
|
1
|
-
// mltl claim - Claim payment after timeout (agent protection)
|
|
2
|
-
|
|
3
|
-
import { formatEther } from "viem";
|
|
4
|
-
import { loadOrCreateWallet } from "../lib/wallet.js";
|
|
5
|
-
import { getTask, completeTask } from "../lib/tasks.js";
|
|
6
|
-
import {
|
|
7
|
-
releaseAfterTimeout,
|
|
8
|
-
getEscrowDetails,
|
|
9
|
-
isEscrowTimedOut,
|
|
10
|
-
getTimeUntilTimeout,
|
|
11
|
-
EscrowStatus,
|
|
12
|
-
} from "../lib/escrow.js";
|
|
13
|
-
|
|
14
|
-
interface ClaimOptions {
|
|
15
|
-
task: string;
|
|
16
|
-
json?: boolean;
|
|
17
|
-
}
|
|
18
|
-
|
|
19
|
-
export async function claim(options: ClaimOptions): Promise<void> {
|
|
20
|
-
const { wallet } = await loadOrCreateWallet();
|
|
21
|
-
|
|
22
|
-
if (!options.json) {
|
|
23
|
-
console.log("\nChecking claim eligibility...");
|
|
24
|
-
console.log("──────────────────────────────────────────────");
|
|
25
|
-
}
|
|
26
|
-
|
|
27
|
-
try {
|
|
28
|
-
// Get task details
|
|
29
|
-
const task = await getTask(options.task);
|
|
30
|
-
|
|
31
|
-
// Get escrow details
|
|
32
|
-
const escrow = await getEscrowDetails(options.task);
|
|
33
|
-
|
|
34
|
-
if (!escrow) {
|
|
35
|
-
throw new Error("No escrow found for this task");
|
|
36
|
-
}
|
|
37
|
-
|
|
38
|
-
if (escrow.status === EscrowStatus.Released || escrow.status === EscrowStatus.Refunded) {
|
|
39
|
-
throw new Error("Payment already released or refunded");
|
|
40
|
-
}
|
|
41
|
-
|
|
42
|
-
if (escrow.status !== EscrowStatus.Submitted) {
|
|
43
|
-
throw new Error("Work not yet submitted. Run 'mltl submit' first.");
|
|
44
|
-
}
|
|
45
|
-
|
|
46
|
-
if (escrow.status === EscrowStatus.Disputed) {
|
|
47
|
-
throw new Error("Task is disputed. Cannot claim until dispute is resolved.");
|
|
48
|
-
}
|
|
49
|
-
|
|
50
|
-
const priceEth = formatEther(escrow.amount);
|
|
51
|
-
|
|
52
|
-
// Check if timeout reached
|
|
53
|
-
const timedOut = await isEscrowTimedOut(options.task);
|
|
54
|
-
|
|
55
|
-
if (!timedOut) {
|
|
56
|
-
const secondsLeft = await getTimeUntilTimeout(options.task);
|
|
57
|
-
const hoursLeft = Number(secondsLeft) / 3600;
|
|
58
|
-
|
|
59
|
-
if (options.json) {
|
|
60
|
-
console.log(
|
|
61
|
-
JSON.stringify({
|
|
62
|
-
error: "Timeout not reached",
|
|
63
|
-
timeRemaining: {
|
|
64
|
-
seconds: Number(secondsLeft),
|
|
65
|
-
hours: hoursLeft.toFixed(2),
|
|
66
|
-
},
|
|
67
|
-
}),
|
|
68
|
-
);
|
|
69
|
-
process.exit(1);
|
|
70
|
-
}
|
|
71
|
-
|
|
72
|
-
console.log(`\n⏳ Timeout not reached yet.`);
|
|
73
|
-
console.log(`\nTime remaining: ${hoursLeft.toFixed(1)} hours`);
|
|
74
|
-
console.log(`\nThe client can still approve the work.`);
|
|
75
|
-
console.log(`If they don't respond, you can claim after the timeout.\n`);
|
|
76
|
-
return;
|
|
77
|
-
}
|
|
78
|
-
|
|
79
|
-
if (!options.json) {
|
|
80
|
-
console.log(`\nTask ID: ${task.id}`);
|
|
81
|
-
console.log(`Amount: ${priceEth} ETH`);
|
|
82
|
-
console.log(`Status: Timeout reached - claiming payment...`);
|
|
83
|
-
}
|
|
84
|
-
|
|
85
|
-
// Release after timeout
|
|
86
|
-
const txHash = await releaseAfterTimeout(wallet, options.task);
|
|
87
|
-
|
|
88
|
-
// Sync completion to worker KV
|
|
89
|
-
try {
|
|
90
|
-
await completeTask(wallet, options.task, txHash);
|
|
91
|
-
} catch {
|
|
92
|
-
// Non-fatal: onchain release succeeded, KV sync is best-effort
|
|
93
|
-
}
|
|
94
|
-
|
|
95
|
-
if (options.json) {
|
|
96
|
-
console.log(
|
|
97
|
-
JSON.stringify({
|
|
98
|
-
success: true,
|
|
99
|
-
task: {
|
|
100
|
-
id: task.id,
|
|
101
|
-
agentId: task.agentId,
|
|
102
|
-
},
|
|
103
|
-
payment: {
|
|
104
|
-
amount: priceEth,
|
|
105
|
-
txHash,
|
|
106
|
-
type: "timeout_release",
|
|
107
|
-
},
|
|
108
|
-
}),
|
|
109
|
-
);
|
|
110
|
-
return;
|
|
111
|
-
}
|
|
112
|
-
|
|
113
|
-
console.log("\n✅ Payment claimed!");
|
|
114
|
-
console.log("──────────────────────────────────────────────");
|
|
115
|
-
console.log(`\nAmount: ${priceEth} ETH`);
|
|
116
|
-
console.log(`TX: ${txHash}`);
|
|
117
|
-
console.log(`\nThe client did not respond within 24 hours.`);
|
|
118
|
-
console.log(`Funds have been released to your wallet.\n`);
|
|
119
|
-
} catch (err) {
|
|
120
|
-
const errorMsg = err instanceof Error ? err.message : String(err);
|
|
121
|
-
|
|
122
|
-
if (options.json) {
|
|
123
|
-
console.log(JSON.stringify({ error: errorMsg }));
|
|
124
|
-
process.exit(1);
|
|
125
|
-
}
|
|
126
|
-
|
|
127
|
-
console.error(`\n❌ Failed to claim: ${errorMsg}`);
|
|
128
|
-
process.exit(1);
|
|
129
|
-
}
|
|
130
|
-
}
|
package/src/commands/decline.ts
DELETED
|
@@ -1,55 +0,0 @@
|
|
|
1
|
-
// mltl decline - Decline a task request (agent action)
|
|
2
|
-
|
|
3
|
-
import { loadOrCreateWallet } from "../lib/wallet.js";
|
|
4
|
-
import { declineTask, getTask } from "../lib/tasks.js";
|
|
5
|
-
|
|
6
|
-
interface DeclineOptions {
|
|
7
|
-
task: string;
|
|
8
|
-
json?: boolean;
|
|
9
|
-
}
|
|
10
|
-
|
|
11
|
-
export async function decline(options: DeclineOptions): Promise<void> {
|
|
12
|
-
const { wallet } = await loadOrCreateWallet();
|
|
13
|
-
|
|
14
|
-
if (!options.json) {
|
|
15
|
-
console.log("\nDeclining task...");
|
|
16
|
-
}
|
|
17
|
-
|
|
18
|
-
try {
|
|
19
|
-
// First verify task exists
|
|
20
|
-
const taskBefore = await getTask(options.task);
|
|
21
|
-
|
|
22
|
-
if (!["requested", "quoted"].includes(taskBefore.status)) {
|
|
23
|
-
throw new Error(`Task is ${taskBefore.status}, cannot decline`);
|
|
24
|
-
}
|
|
25
|
-
|
|
26
|
-
// Decline the task (signed with wallet)
|
|
27
|
-
const task = await declineTask(wallet, options.task);
|
|
28
|
-
|
|
29
|
-
if (options.json) {
|
|
30
|
-
console.log(
|
|
31
|
-
JSON.stringify({
|
|
32
|
-
success: true,
|
|
33
|
-
task: {
|
|
34
|
-
id: task.id,
|
|
35
|
-
status: task.status,
|
|
36
|
-
},
|
|
37
|
-
}),
|
|
38
|
-
);
|
|
39
|
-
return;
|
|
40
|
-
}
|
|
41
|
-
|
|
42
|
-
console.log(`\n✅ Task ${task.id} declined.`);
|
|
43
|
-
console.log("\nThe client will be notified.\n");
|
|
44
|
-
} catch (err) {
|
|
45
|
-
const errorMsg = err instanceof Error ? err.message : String(err);
|
|
46
|
-
|
|
47
|
-
if (options.json) {
|
|
48
|
-
console.log(JSON.stringify({ error: errorMsg }));
|
|
49
|
-
process.exit(1);
|
|
50
|
-
}
|
|
51
|
-
|
|
52
|
-
console.error(`\n❌ Failed to decline task: ${errorMsg}`);
|
|
53
|
-
process.exit(1);
|
|
54
|
-
}
|
|
55
|
-
}
|
package/src/commands/dispute.ts
DELETED
|
@@ -1,92 +0,0 @@
|
|
|
1
|
-
// mltl dispute - Dispute submitted work and freeze timeout (client action)
|
|
2
|
-
|
|
3
|
-
import { formatEther } from "viem";
|
|
4
|
-
import { loadOrCreateWallet } from "../lib/wallet.js";
|
|
5
|
-
import { getTask } from "../lib/tasks.js";
|
|
6
|
-
import { getEscrowDetails, getDisputeFee, disputeEscrow, EscrowStatus } from "../lib/escrow.js";
|
|
7
|
-
import { signAction } from "../lib/auth.js";
|
|
8
|
-
import { APIS } from "../lib/constants.js";
|
|
9
|
-
|
|
10
|
-
interface DisputeOptions {
|
|
11
|
-
task: string;
|
|
12
|
-
json?: boolean;
|
|
13
|
-
}
|
|
14
|
-
|
|
15
|
-
export async function dispute(options: DisputeOptions): Promise<void> {
|
|
16
|
-
const { wallet } = await loadOrCreateWallet();
|
|
17
|
-
|
|
18
|
-
if (!options.json) {
|
|
19
|
-
console.log("\nDisputing submitted work...");
|
|
20
|
-
console.log("──────────────────────────────────────────────");
|
|
21
|
-
}
|
|
22
|
-
|
|
23
|
-
try {
|
|
24
|
-
const task = await getTask(options.task);
|
|
25
|
-
|
|
26
|
-
if (task.status !== "submitted") {
|
|
27
|
-
throw new Error(`Task is ${task.status}, cannot dispute (must be submitted)`);
|
|
28
|
-
}
|
|
29
|
-
|
|
30
|
-
if (task.clientAddress.toLowerCase() !== wallet.address.toLowerCase()) {
|
|
31
|
-
throw new Error("Only the client who created this task can dispute it");
|
|
32
|
-
}
|
|
33
|
-
|
|
34
|
-
const escrow = await getEscrowDetails(task.id);
|
|
35
|
-
if (!escrow) {
|
|
36
|
-
throw new Error("No escrow found for this task");
|
|
37
|
-
}
|
|
38
|
-
if (escrow.status !== EscrowStatus.Submitted) {
|
|
39
|
-
throw new Error("Escrow is not in submitted state");
|
|
40
|
-
}
|
|
41
|
-
|
|
42
|
-
const feeWei = await getDisputeFee(task.id);
|
|
43
|
-
const feeEth = formatEther(feeWei);
|
|
44
|
-
|
|
45
|
-
if (!options.json) {
|
|
46
|
-
console.log(`\nTask ID: ${task.id}`);
|
|
47
|
-
console.log(`Escrow: ${formatEther(escrow.amount)} ETH`);
|
|
48
|
-
console.log(`Dispute fee: ${feeEth} ETH (10% of escrow)`);
|
|
49
|
-
console.log("\nOpening dispute...");
|
|
50
|
-
}
|
|
51
|
-
|
|
52
|
-
const txHash = await disputeEscrow(wallet, task.id, feeWei);
|
|
53
|
-
|
|
54
|
-
// Sign and notify worker
|
|
55
|
-
const { signature, timestamp, nonce } = await signAction(wallet, "dispute", task.id);
|
|
56
|
-
|
|
57
|
-
await fetch(`${APIS.MANDATE}/api/tasks/${task.id}/dispute`, {
|
|
58
|
-
method: "POST",
|
|
59
|
-
headers: { "Content-Type": "application/json" },
|
|
60
|
-
body: JSON.stringify({ txHash, signature, timestamp, nonce }),
|
|
61
|
-
});
|
|
62
|
-
|
|
63
|
-
if (options.json) {
|
|
64
|
-
console.log(
|
|
65
|
-
JSON.stringify({
|
|
66
|
-
success: true,
|
|
67
|
-
taskId: task.id,
|
|
68
|
-
disputeFee: feeEth,
|
|
69
|
-
txHash,
|
|
70
|
-
})
|
|
71
|
-
);
|
|
72
|
-
return;
|
|
73
|
-
}
|
|
74
|
-
|
|
75
|
-
console.log("\nDispute opened! Timeout is now frozen.");
|
|
76
|
-
console.log("──────────────────────────────────────────────");
|
|
77
|
-
console.log(`\nFee paid: ${feeEth} ETH`);
|
|
78
|
-
console.log(`TX: ${txHash}`);
|
|
79
|
-
console.log("\nAn admin will review and resolve the dispute.");
|
|
80
|
-
console.log("If you win, you get your escrow + fee back.\n");
|
|
81
|
-
} catch (err) {
|
|
82
|
-
const errorMsg = err instanceof Error ? err.message : String(err);
|
|
83
|
-
|
|
84
|
-
if (options.json) {
|
|
85
|
-
console.log(JSON.stringify({ error: errorMsg }));
|
|
86
|
-
process.exit(1);
|
|
87
|
-
}
|
|
88
|
-
|
|
89
|
-
console.error(`\n❌ Failed to dispute: ${errorMsg}`);
|
|
90
|
-
process.exit(1);
|
|
91
|
-
}
|
|
92
|
-
}
|
package/src/commands/earnings.ts
DELETED
|
@@ -1,86 +0,0 @@
|
|
|
1
|
-
// mltl earnings - View your earnings from being hired
|
|
2
|
-
|
|
3
|
-
import { formatEther } from "viem";
|
|
4
|
-
import { loadOrCreateWallet, getWalletBalance } from "../lib/wallet.js";
|
|
5
|
-
import { getAgentByOwner, getReputationSummary } from "../lib/mandate.js";
|
|
6
|
-
import { CHAIN } from "../lib/constants.js";
|
|
7
|
-
|
|
8
|
-
interface EarningsOptions {
|
|
9
|
-
json?: boolean;
|
|
10
|
-
}
|
|
11
|
-
|
|
12
|
-
export async function earnings(options: EarningsOptions): Promise<void> {
|
|
13
|
-
const { wallet } = await loadOrCreateWallet();
|
|
14
|
-
|
|
15
|
-
if (!options.json) {
|
|
16
|
-
console.log("\nMANDATE Earnings");
|
|
17
|
-
console.log("══════════════════════════════════════════════════════════════════\n");
|
|
18
|
-
}
|
|
19
|
-
|
|
20
|
-
try {
|
|
21
|
-
const balance = await getWalletBalance(wallet.address);
|
|
22
|
-
const agentId = await getAgentByOwner(wallet.address);
|
|
23
|
-
|
|
24
|
-
if (options.json) {
|
|
25
|
-
const result: Record<string, unknown> = {
|
|
26
|
-
wallet: wallet.address,
|
|
27
|
-
balance,
|
|
28
|
-
agent: null as Record<string, unknown> | null,
|
|
29
|
-
};
|
|
30
|
-
|
|
31
|
-
if (agentId && agentId > 0n) {
|
|
32
|
-
const rep = await getReputationSummary(agentId);
|
|
33
|
-
result.agent = {
|
|
34
|
-
agentId: agentId.toString(),
|
|
35
|
-
reputation: {
|
|
36
|
-
count: Number(rep.count),
|
|
37
|
-
summaryValue: Number(rep.summaryValue),
|
|
38
|
-
},
|
|
39
|
-
};
|
|
40
|
-
}
|
|
41
|
-
|
|
42
|
-
console.log(JSON.stringify(result));
|
|
43
|
-
return;
|
|
44
|
-
}
|
|
45
|
-
|
|
46
|
-
console.log(`Wallet: ${wallet.address}`);
|
|
47
|
-
console.log(`Balance: ${balance} ETH`);
|
|
48
|
-
console.log("");
|
|
49
|
-
|
|
50
|
-
if (!agentId || agentId <= 0n) {
|
|
51
|
-
console.log("No registered agent found for this wallet.");
|
|
52
|
-
console.log("Register one with: mltl register --name <name> --description <desc> --skills <skills> --image <path>");
|
|
53
|
-
return;
|
|
54
|
-
}
|
|
55
|
-
|
|
56
|
-
console.log(`Agent ID: ${agentId.toString()}`);
|
|
57
|
-
console.log(`Explorer: ${CHAIN.explorer}/token/${agentId.toString()}`);
|
|
58
|
-
console.log("");
|
|
59
|
-
console.log("──────────────────────────────────────────────");
|
|
60
|
-
console.log("Reputation (ERC-8004):");
|
|
61
|
-
console.log("──────────────────────────────────────────────");
|
|
62
|
-
|
|
63
|
-
const rep = await getReputationSummary(agentId);
|
|
64
|
-
const feedbackCount = Number(rep.count);
|
|
65
|
-
const avgScore = feedbackCount > 0 ? Number(rep.summaryValue) / feedbackCount : 0;
|
|
66
|
-
|
|
67
|
-
console.log(` Feedback received: ${feedbackCount}`);
|
|
68
|
-
console.log(` Average score: ${avgScore > 0 ? avgScore.toFixed(1) + "/100" : "N/A"}`);
|
|
69
|
-
console.log("");
|
|
70
|
-
console.log("Earnings are distributed via buyback-and-burn on your Flaunch token.");
|
|
71
|
-
console.log("Each completed task burns tokens, increasing token value for holders.");
|
|
72
|
-
|
|
73
|
-
} catch (err) {
|
|
74
|
-
if (options.json) {
|
|
75
|
-
console.log(
|
|
76
|
-
JSON.stringify({
|
|
77
|
-
error: err instanceof Error ? err.message : String(err),
|
|
78
|
-
})
|
|
79
|
-
);
|
|
80
|
-
process.exit(1);
|
|
81
|
-
}
|
|
82
|
-
|
|
83
|
-
console.error(`\n❌ Failed to fetch earnings: ${err instanceof Error ? err.message : err}`);
|
|
84
|
-
process.exit(1);
|
|
85
|
-
}
|
|
86
|
-
}
|
package/src/commands/feedback.ts
DELETED
|
@@ -1,147 +0,0 @@
|
|
|
1
|
-
// mltl feedback - Submit verified feedback for an agent after completing a task
|
|
2
|
-
// Uses ERC-8004 Reputation Registry with full field utilization:
|
|
3
|
-
// - feedbackHash: keccak256(taskId) — links to escrow record
|
|
4
|
-
// - feedbackURI: "moltlaunch:task:<taskId>" — human-readable reference
|
|
5
|
-
// - tag1: "mandate" — platform identifier
|
|
6
|
-
// - tag2: agent contract address (CA)
|
|
7
|
-
|
|
8
|
-
import { loadOrCreateWallet } from "../lib/wallet.js";
|
|
9
|
-
import { giveFeedback, getAgent } from "../lib/mandate.js";
|
|
10
|
-
import { getTask, rateTask } from "../lib/tasks.js";
|
|
11
|
-
|
|
12
|
-
interface FeedbackOptions {
|
|
13
|
-
agent?: string;
|
|
14
|
-
task?: string;
|
|
15
|
-
score: string;
|
|
16
|
-
comment?: string;
|
|
17
|
-
json?: boolean;
|
|
18
|
-
}
|
|
19
|
-
|
|
20
|
-
export async function feedback(options: FeedbackOptions): Promise<void> {
|
|
21
|
-
const { wallet } = await loadOrCreateWallet();
|
|
22
|
-
|
|
23
|
-
const score = parseInt(options.score, 10);
|
|
24
|
-
|
|
25
|
-
if (score < 0 || score > 100) {
|
|
26
|
-
if (options.json) {
|
|
27
|
-
console.log(JSON.stringify({ error: "Score must be between 0 and 100" }));
|
|
28
|
-
process.exit(1);
|
|
29
|
-
}
|
|
30
|
-
console.error("Score must be between 0 and 100");
|
|
31
|
-
process.exit(1);
|
|
32
|
-
}
|
|
33
|
-
|
|
34
|
-
if (!options.agent && !options.task) {
|
|
35
|
-
if (options.json) {
|
|
36
|
-
console.log(JSON.stringify({ error: "Provide --agent or --task" }));
|
|
37
|
-
process.exit(1);
|
|
38
|
-
}
|
|
39
|
-
console.error("Provide --agent <id> or --task <taskId>");
|
|
40
|
-
process.exit(1);
|
|
41
|
-
}
|
|
42
|
-
|
|
43
|
-
let agentIdStr = options.agent || "";
|
|
44
|
-
let taskId = options.task;
|
|
45
|
-
|
|
46
|
-
// If --task provided, resolve agent from task and verify caller is the client
|
|
47
|
-
if (taskId) {
|
|
48
|
-
try {
|
|
49
|
-
const task = await getTask(taskId);
|
|
50
|
-
|
|
51
|
-
if (task.status !== "completed") {
|
|
52
|
-
const msg = `Task ${taskId} is not completed (status: ${task.status})`;
|
|
53
|
-
if (options.json) {
|
|
54
|
-
console.log(JSON.stringify({ error: msg }));
|
|
55
|
-
process.exit(1);
|
|
56
|
-
}
|
|
57
|
-
console.error(msg);
|
|
58
|
-
process.exit(1);
|
|
59
|
-
}
|
|
60
|
-
|
|
61
|
-
if (task.clientAddress.toLowerCase() !== wallet.address.toLowerCase()) {
|
|
62
|
-
const msg = "Only the task client can leave feedback";
|
|
63
|
-
if (options.json) {
|
|
64
|
-
console.log(JSON.stringify({ error: msg }));
|
|
65
|
-
process.exit(1);
|
|
66
|
-
}
|
|
67
|
-
console.error(msg);
|
|
68
|
-
process.exit(1);
|
|
69
|
-
}
|
|
70
|
-
|
|
71
|
-
agentIdStr = task.agentId;
|
|
72
|
-
} catch (err) {
|
|
73
|
-
const msg = err instanceof Error ? err.message : String(err);
|
|
74
|
-
if (options.json) {
|
|
75
|
-
console.log(JSON.stringify({ error: msg }));
|
|
76
|
-
process.exit(1);
|
|
77
|
-
}
|
|
78
|
-
console.error(`Failed to fetch task: ${msg}`);
|
|
79
|
-
process.exit(1);
|
|
80
|
-
}
|
|
81
|
-
}
|
|
82
|
-
|
|
83
|
-
const agentId = BigInt(agentIdStr.startsWith("0x") ? agentIdStr : agentIdStr);
|
|
84
|
-
|
|
85
|
-
if (!options.json) {
|
|
86
|
-
console.log("\nSubmitting verified feedback...");
|
|
87
|
-
console.log("──────────────────────────────────────────────");
|
|
88
|
-
console.log(`Agent: #${agentIdStr}`);
|
|
89
|
-
console.log(`Score: ${score}/100`);
|
|
90
|
-
if (taskId) console.log(`Task: ${taskId}`);
|
|
91
|
-
console.log(`Tag1: mandate`);
|
|
92
|
-
console.log("──────────────────────────────────────────────\n");
|
|
93
|
-
}
|
|
94
|
-
|
|
95
|
-
try {
|
|
96
|
-
// Resolve agent's contract address for tag2
|
|
97
|
-
const agent = await getAgent(agentId);
|
|
98
|
-
const agentCA = agent?.owner || "";
|
|
99
|
-
|
|
100
|
-
const txHash = await giveFeedback(wallet, agentId, score, {
|
|
101
|
-
taskId,
|
|
102
|
-
agentContractAddress: agentCA,
|
|
103
|
-
});
|
|
104
|
-
|
|
105
|
-
// Sync rating to worker KV for verified reputation tracking
|
|
106
|
-
if (taskId) {
|
|
107
|
-
try {
|
|
108
|
-
await rateTask(wallet, taskId, txHash, score, options.comment);
|
|
109
|
-
} catch {
|
|
110
|
-
// Non-fatal: onchain feedback succeeded, KV sync is best-effort
|
|
111
|
-
}
|
|
112
|
-
}
|
|
113
|
-
|
|
114
|
-
if (options.json) {
|
|
115
|
-
console.log(
|
|
116
|
-
JSON.stringify({
|
|
117
|
-
success: true,
|
|
118
|
-
agentId: agentIdStr,
|
|
119
|
-
score,
|
|
120
|
-
taskId: taskId || null,
|
|
121
|
-
feedbackHash: taskId ? `keccak256(${taskId})` : null,
|
|
122
|
-
txHash,
|
|
123
|
-
})
|
|
124
|
-
);
|
|
125
|
-
return;
|
|
126
|
-
}
|
|
127
|
-
|
|
128
|
-
console.log("Feedback submitted!\n");
|
|
129
|
-
console.log(`Transaction: ${txHash}`);
|
|
130
|
-
console.log(`View on Basescan: https://basescan.org/tx/${txHash}`);
|
|
131
|
-
if (taskId) {
|
|
132
|
-
console.log(`Linked to task: ${taskId}`);
|
|
133
|
-
}
|
|
134
|
-
} catch (err) {
|
|
135
|
-
if (options.json) {
|
|
136
|
-
console.log(
|
|
137
|
-
JSON.stringify({
|
|
138
|
-
error: err instanceof Error ? err.message : String(err),
|
|
139
|
-
})
|
|
140
|
-
);
|
|
141
|
-
process.exit(1);
|
|
142
|
-
}
|
|
143
|
-
|
|
144
|
-
console.error(`\nFeedback failed: ${err instanceof Error ? err.message : err}`);
|
|
145
|
-
process.exit(1);
|
|
146
|
-
}
|
|
147
|
-
}
|