@openclawcash/mcp-server 0.1.2 → 0.1.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +5 -1
- package/openclawcash-mcp.mjs +696 -20
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -58,6 +58,8 @@ Set one of these environment variables:
|
|
|
58
58
|
- `OPENCLAWCASH_AGENT_KEY`
|
|
59
59
|
- `AGENTWALLETAPI_KEY`
|
|
60
60
|
|
|
61
|
+
All MCP tools require an OpenClawCash agent key because they call the authenticated agent API, including read tools such as `swap_quote` and `supported_tokens_list`.
|
|
62
|
+
|
|
61
63
|
Optional base URL override:
|
|
62
64
|
|
|
63
65
|
- `OPENCLAWCASH_BASE_URL`
|
|
@@ -217,8 +219,10 @@ The MCP server itself does not hold approval memory. The MCP client or agent run
|
|
|
217
219
|
|
|
218
220
|
## Notes
|
|
219
221
|
|
|
220
|
-
- `swap_quote` is read-only.
|
|
222
|
+
- `swap_quote` is read-only, but still requires an agent key.
|
|
223
|
+
- `supported_tokens_list` is read-only, but still requires an agent key.
|
|
221
224
|
- `transfer_send`, `swap_execute`, `approve_token`, `wallet_create`, and `wallet_import` are write tools.
|
|
225
|
+
- For `wallet_get`, `transactions_list`, `supported_tokens_list`, and `swap_quote`, pass at most one wallet selector when using `walletId`, `walletLabel`, or `walletAddress`.
|
|
222
226
|
- The server uses stdio transport and is intended for MCP-compatible desktop or agent clients.
|
|
223
227
|
|
|
224
228
|
## Standalone Packaging Notes
|
package/openclawcash-mcp.mjs
CHANGED
|
@@ -7,7 +7,7 @@ import { fileURLToPath } from "node:url";
|
|
|
7
7
|
import { z } from "zod";
|
|
8
8
|
|
|
9
9
|
const SERVER_NAME = "openclawcash";
|
|
10
|
-
const SERVER_VERSION = "0.1.
|
|
10
|
+
const SERVER_VERSION = "0.1.6";
|
|
11
11
|
const PROTOCOL_VERSION = "2024-11-05";
|
|
12
12
|
const DEFAULT_BASE_URL = "https://openclawcash.com";
|
|
13
13
|
|
|
@@ -130,13 +130,16 @@ const transferArgsSchema = walletSelectorBaseSchema
|
|
|
130
130
|
message: "Provide exactly one of amount or value.",
|
|
131
131
|
});
|
|
132
132
|
|
|
133
|
-
const swapQuoteArgsSchema =
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
})
|
|
133
|
+
const swapQuoteArgsSchema = walletSelectorBaseSchema
|
|
134
|
+
.extend({
|
|
135
|
+
network: z.string().min(1),
|
|
136
|
+
tokenIn: z.string().min(1),
|
|
137
|
+
tokenOut: z.string().min(1),
|
|
138
|
+
amountIn: z.string().min(1),
|
|
139
|
+
})
|
|
140
|
+
.refine((data) => [data.walletId, data.walletLabel, data.walletAddress].filter((value) => value !== undefined).length <= 1, {
|
|
141
|
+
message: selectorDescription(),
|
|
142
|
+
});
|
|
140
143
|
|
|
141
144
|
const swapExecuteArgsSchema = z
|
|
142
145
|
.object({
|
|
@@ -165,14 +168,17 @@ const approveArgsSchema = z
|
|
|
165
168
|
message: "Provide exactly one of walletId or walletAddress.",
|
|
166
169
|
});
|
|
167
170
|
|
|
168
|
-
const supportedTokensArgsSchema =
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
})
|
|
171
|
+
const supportedTokensArgsSchema = walletSelectorBaseSchema
|
|
172
|
+
.extend({
|
|
173
|
+
network: z.string().min(1).optional(),
|
|
174
|
+
})
|
|
175
|
+
.refine((data) => [data.walletId, data.walletLabel, data.walletAddress].filter((value) => value !== undefined).length <= 1, {
|
|
176
|
+
message: selectorDescription(),
|
|
177
|
+
});
|
|
172
178
|
|
|
173
179
|
const createWalletArgsSchema = z.object({
|
|
174
180
|
label: z.string().min(1),
|
|
175
|
-
network: z.enum(["sepolia", "mainnet", "solana-devnet", "solana-testnet", "solana-mainnet"]).optional(),
|
|
181
|
+
network: z.enum(["sepolia", "mainnet", "polygon-mainnet", "solana-devnet", "solana-testnet", "solana-mainnet"]).optional(),
|
|
176
182
|
exportPassphrase: z.string().trim().min(12),
|
|
177
183
|
exportPassphraseStorageType: z.enum(["env", "secret_manager", "vault", "other"]),
|
|
178
184
|
exportPassphraseStorageRef: z.string().trim().min(3),
|
|
@@ -181,10 +187,154 @@ const createWalletArgsSchema = z.object({
|
|
|
181
187
|
|
|
182
188
|
const importWalletArgsSchema = z.object({
|
|
183
189
|
label: z.string().min(1),
|
|
184
|
-
network: z.enum(["mainnet", "solana-mainnet"]),
|
|
190
|
+
network: z.enum(["mainnet", "polygon-mainnet", "solana-mainnet"]),
|
|
185
191
|
privateKey: z.string().min(1),
|
|
186
192
|
});
|
|
187
193
|
|
|
194
|
+
const userTagSetArgsSchema = z.object({
|
|
195
|
+
userTag: z
|
|
196
|
+
.string()
|
|
197
|
+
.trim()
|
|
198
|
+
.toLowerCase()
|
|
199
|
+
.min(3)
|
|
200
|
+
.max(64)
|
|
201
|
+
.regex(/^[a-z0-9][a-z0-9._-]{2,63}$/),
|
|
202
|
+
});
|
|
203
|
+
|
|
204
|
+
const polymarketLimitArgsSchema = z
|
|
205
|
+
.object({
|
|
206
|
+
walletId: z.union([z.number().int().positive(), z.string().min(1)]).optional(),
|
|
207
|
+
walletAddress: z.string().min(1).optional(),
|
|
208
|
+
tokenId: z.string().min(1),
|
|
209
|
+
side: z.enum(["BUY", "SELL"]),
|
|
210
|
+
price: z.number().positive(),
|
|
211
|
+
size: z.number().positive(),
|
|
212
|
+
})
|
|
213
|
+
.refine((data) => [data.walletId, data.walletAddress].filter((v) => v !== undefined).length === 1, {
|
|
214
|
+
message: "Provide exactly one of walletId or walletAddress.",
|
|
215
|
+
});
|
|
216
|
+
|
|
217
|
+
const polymarketMarketArgsSchema = z
|
|
218
|
+
.object({
|
|
219
|
+
walletId: z.union([z.number().int().positive(), z.string().min(1)]).optional(),
|
|
220
|
+
walletAddress: z.string().min(1).optional(),
|
|
221
|
+
tokenId: z.string().min(1),
|
|
222
|
+
side: z.enum(["BUY", "SELL"]),
|
|
223
|
+
amount: z.number().positive(),
|
|
224
|
+
orderType: z.enum(["FAK", "FOK", "GTC"]).optional(),
|
|
225
|
+
worstPrice: z.number().min(0).max(1).optional(),
|
|
226
|
+
})
|
|
227
|
+
.refine((data) => [data.walletId, data.walletAddress].filter((v) => v !== undefined).length === 1, {
|
|
228
|
+
message: "Provide exactly one of walletId or walletAddress.",
|
|
229
|
+
});
|
|
230
|
+
|
|
231
|
+
const polymarketReadArgsSchema = z
|
|
232
|
+
.object({
|
|
233
|
+
walletId: z.union([z.number().int().positive(), z.string().min(1)]).optional(),
|
|
234
|
+
walletAddress: z.string().min(1).optional(),
|
|
235
|
+
status: z.string().min(1).optional(),
|
|
236
|
+
limit: z.number().int().positive().max(200).optional(),
|
|
237
|
+
cursor: z.string().min(1).optional(),
|
|
238
|
+
})
|
|
239
|
+
.refine((data) => [data.walletId, data.walletAddress].filter((v) => v !== undefined).length === 1, {
|
|
240
|
+
message: "Provide exactly one of walletId or walletAddress.",
|
|
241
|
+
});
|
|
242
|
+
|
|
243
|
+
const polymarketCancelArgsSchema = z
|
|
244
|
+
.object({
|
|
245
|
+
walletId: z.union([z.number().int().positive(), z.string().min(1)]).optional(),
|
|
246
|
+
walletAddress: z.string().min(1).optional(),
|
|
247
|
+
orderId: z.string().min(1),
|
|
248
|
+
})
|
|
249
|
+
.refine((data) => [data.walletId, data.walletAddress].filter((v) => v !== undefined).length === 1, {
|
|
250
|
+
message: "Provide exactly one of walletId or walletAddress.",
|
|
251
|
+
});
|
|
252
|
+
|
|
253
|
+
const checkoutEscrowIdArgsSchema = z.object({
|
|
254
|
+
id: z.string().min(1),
|
|
255
|
+
});
|
|
256
|
+
|
|
257
|
+
const checkoutPayreqIdArgsSchema = z.object({
|
|
258
|
+
id: z.string().min(1),
|
|
259
|
+
});
|
|
260
|
+
|
|
261
|
+
const checkoutWalletSelectorArgsSchema = z
|
|
262
|
+
.object({
|
|
263
|
+
id: z.string().min(1),
|
|
264
|
+
walletId: z.union([z.number().int().positive(), z.string().min(1)]).optional(),
|
|
265
|
+
walletAddress: z.string().min(1).optional(),
|
|
266
|
+
})
|
|
267
|
+
.refine((data) => [data.walletId, data.walletAddress].filter((v) => v !== undefined).length === 1, {
|
|
268
|
+
message: "Provide exactly one of walletId or walletAddress.",
|
|
269
|
+
});
|
|
270
|
+
|
|
271
|
+
const checkoutCreatePayreqArgsSchema = z
|
|
272
|
+
.object({
|
|
273
|
+
walletId: z.union([z.number().int().positive(), z.string().min(1)]).optional(),
|
|
274
|
+
walletAddress: z.string().min(1).optional(),
|
|
275
|
+
amount: z.string().min(1),
|
|
276
|
+
expiresInSeconds: z.number().int().positive().optional(),
|
|
277
|
+
autoReleaseSeconds: z.number().int().positive().optional(),
|
|
278
|
+
disputeWindowSeconds: z.number().int().positive().optional(),
|
|
279
|
+
metadata: z.record(z.unknown()).optional(),
|
|
280
|
+
})
|
|
281
|
+
.refine((data) => [data.walletId, data.walletAddress].filter((v) => v !== undefined).length === 1, {
|
|
282
|
+
message: "Provide exactly one of walletId or walletAddress.",
|
|
283
|
+
});
|
|
284
|
+
|
|
285
|
+
const checkoutFundingConfirmArgsSchema = z.object({
|
|
286
|
+
id: z.string().min(1),
|
|
287
|
+
txHash: z.string().min(1),
|
|
288
|
+
minConfirmations: z.number().int().positive().optional(),
|
|
289
|
+
});
|
|
290
|
+
|
|
291
|
+
const checkoutAcceptArgsSchema = z.object({
|
|
292
|
+
id: z.string().min(1),
|
|
293
|
+
});
|
|
294
|
+
|
|
295
|
+
const checkoutProofArgsSchema = z.object({
|
|
296
|
+
id: z.string().min(1),
|
|
297
|
+
proofHash: z.string().trim().min(1).max(128),
|
|
298
|
+
proofUrl: z.string().url().optional(),
|
|
299
|
+
});
|
|
300
|
+
|
|
301
|
+
const checkoutDisputeArgsSchema = z.object({
|
|
302
|
+
id: z.string().min(1),
|
|
303
|
+
reasonCode: z.string().trim().min(3).max(64),
|
|
304
|
+
details: z.record(z.unknown()).optional(),
|
|
305
|
+
});
|
|
306
|
+
|
|
307
|
+
const checkoutSwapAndPayArgsSchema = z
|
|
308
|
+
.object({
|
|
309
|
+
id: z.string().min(1),
|
|
310
|
+
walletId: z.union([z.number().int().positive(), z.string().min(1)]).optional(),
|
|
311
|
+
walletAddress: z.string().min(1).optional(),
|
|
312
|
+
confirm: z.boolean().optional(),
|
|
313
|
+
slippage: z.number().positive().max(5).optional(),
|
|
314
|
+
})
|
|
315
|
+
.refine((data) => [data.walletId, data.walletAddress].filter((v) => v !== undefined).length === 1, {
|
|
316
|
+
message: "Provide exactly one of walletId or walletAddress.",
|
|
317
|
+
});
|
|
318
|
+
|
|
319
|
+
const checkoutWebhookCreateArgsSchema = z.object({
|
|
320
|
+
url: z.string().url(),
|
|
321
|
+
eventTypes: z.array(z.string().min(1)).optional(),
|
|
322
|
+
enabled: z.boolean().optional(),
|
|
323
|
+
});
|
|
324
|
+
|
|
325
|
+
const checkoutWebhookUpdateArgsSchema = z.object({
|
|
326
|
+
id: z.union([z.number().int().positive(), z.string().min(1)]),
|
|
327
|
+
url: z.string().url().optional(),
|
|
328
|
+
eventTypes: z.array(z.string().min(1)).optional(),
|
|
329
|
+
enabled: z.boolean().optional(),
|
|
330
|
+
}).refine((data) => data.url !== undefined || data.eventTypes !== undefined || data.enabled !== undefined, {
|
|
331
|
+
message: "Provide at least one of url, eventTypes, or enabled.",
|
|
332
|
+
});
|
|
333
|
+
|
|
334
|
+
const checkoutWebhookDeleteArgsSchema = z.object({
|
|
335
|
+
id: z.union([z.number().int().positive(), z.string().min(1)]),
|
|
336
|
+
});
|
|
337
|
+
|
|
188
338
|
function queryString(params) {
|
|
189
339
|
const search = new URLSearchParams();
|
|
190
340
|
for (const [key, value] of Object.entries(params)) {
|
|
@@ -226,6 +376,9 @@ async function callAgentApi({ method, pathName, query, body, requireAuth = true
|
|
|
226
376
|
if (requireAuth) {
|
|
227
377
|
headers["X-Agent-Key"] = requireAgentKey();
|
|
228
378
|
}
|
|
379
|
+
if (["POST", "PATCH", "DELETE"].includes(String(method || "").toUpperCase())) {
|
|
380
|
+
headers["Idempotency-Key"] = `mcp-${Date.now()}-${Math.random().toString(16).slice(2)}`;
|
|
381
|
+
}
|
|
229
382
|
|
|
230
383
|
const url = `${getBaseUrl()}${pathName}${queryString(query || {})}`;
|
|
231
384
|
const response = await fetch(url, {
|
|
@@ -354,6 +507,9 @@ const tools = [
|
|
|
354
507
|
properties: {
|
|
355
508
|
network: { type: "string", description: "Example: mainnet, sepolia, solana-mainnet." },
|
|
356
509
|
chain: { type: "string", enum: ["evm", "solana"] },
|
|
510
|
+
walletId: { oneOf: [{ type: "integer" }, { type: "string" }], description: "Optional wallet selector for history-linked activity." },
|
|
511
|
+
walletLabel: { type: "string", description: "Optional wallet selector for history-linked activity." },
|
|
512
|
+
walletAddress: { type: "string", description: "Optional wallet selector for history-linked activity." },
|
|
357
513
|
},
|
|
358
514
|
additionalProperties: false,
|
|
359
515
|
},
|
|
@@ -363,7 +519,6 @@ const tools = [
|
|
|
363
519
|
method: "GET",
|
|
364
520
|
pathName: "/api/agent/supported-tokens",
|
|
365
521
|
query: args,
|
|
366
|
-
requireAuth: false,
|
|
367
522
|
}),
|
|
368
523
|
},
|
|
369
524
|
{
|
|
@@ -400,6 +555,9 @@ const tools = [
|
|
|
400
555
|
type: "object",
|
|
401
556
|
properties: {
|
|
402
557
|
network: { type: "string" },
|
|
558
|
+
walletId: { oneOf: [{ type: "integer" }, { type: "string" }], description: "Optional wallet selector for history-linked activity." },
|
|
559
|
+
walletLabel: { type: "string", description: "Optional wallet selector for history-linked activity." },
|
|
560
|
+
walletAddress: { type: "string", description: "Optional wallet selector for history-linked activity." },
|
|
403
561
|
tokenIn: { type: "string" },
|
|
404
562
|
tokenOut: { type: "string" },
|
|
405
563
|
amountIn: { type: "string" },
|
|
@@ -416,7 +574,6 @@ const tools = [
|
|
|
416
574
|
pathName: "/api/agent/quote",
|
|
417
575
|
query: { network },
|
|
418
576
|
body,
|
|
419
|
-
requireAuth: false,
|
|
420
577
|
});
|
|
421
578
|
},
|
|
422
579
|
},
|
|
@@ -478,7 +635,7 @@ const tools = [
|
|
|
478
635
|
label: { type: "string" },
|
|
479
636
|
network: {
|
|
480
637
|
type: "string",
|
|
481
|
-
enum: ["sepolia", "mainnet", "solana-devnet", "solana-testnet", "solana-mainnet"],
|
|
638
|
+
enum: ["sepolia", "mainnet", "polygon-mainnet", "solana-devnet", "solana-testnet", "solana-mainnet"],
|
|
482
639
|
},
|
|
483
640
|
exportPassphrase: { type: "string", minLength: 12 },
|
|
484
641
|
exportPassphraseStorageType: { type: "string", enum: ["env", "secret_manager", "vault", "other"] },
|
|
@@ -514,12 +671,12 @@ const tools = [
|
|
|
514
671
|
},
|
|
515
672
|
{
|
|
516
673
|
name: "wallet_import",
|
|
517
|
-
description: withWriteSafety("Import a mainnet or Solana mainnet wallet under the configured agent key."),
|
|
674
|
+
description: withWriteSafety("Import a mainnet, polygon-mainnet, or Solana mainnet wallet under the configured agent key."),
|
|
518
675
|
inputSchema: {
|
|
519
676
|
type: "object",
|
|
520
677
|
properties: {
|
|
521
678
|
label: { type: "string" },
|
|
522
|
-
network: { type: "string", enum: ["mainnet", "solana-mainnet"] },
|
|
679
|
+
network: { type: "string", enum: ["mainnet", "polygon-mainnet", "solana-mainnet"] },
|
|
523
680
|
privateKey: { type: "string" },
|
|
524
681
|
},
|
|
525
682
|
required: ["label", "network", "privateKey"],
|
|
@@ -533,6 +690,524 @@ const tools = [
|
|
|
533
690
|
body: args,
|
|
534
691
|
}),
|
|
535
692
|
},
|
|
693
|
+
{
|
|
694
|
+
name: "user_tag_get",
|
|
695
|
+
description: "Read global checkout user tag for the API key owner.",
|
|
696
|
+
inputSchema: {
|
|
697
|
+
type: "object",
|
|
698
|
+
properties: {},
|
|
699
|
+
additionalProperties: false,
|
|
700
|
+
},
|
|
701
|
+
parse: (args) => z.object({}).parse(args ?? {}),
|
|
702
|
+
execute: async () =>
|
|
703
|
+
callAgentApi({
|
|
704
|
+
method: "GET",
|
|
705
|
+
pathName: "/api/agent/user-tag",
|
|
706
|
+
}),
|
|
707
|
+
},
|
|
708
|
+
{
|
|
709
|
+
name: "user_tag_set",
|
|
710
|
+
description: withWriteSafety("Set global checkout user tag once (immutable after set)."),
|
|
711
|
+
inputSchema: {
|
|
712
|
+
type: "object",
|
|
713
|
+
properties: {
|
|
714
|
+
userTag: { type: "string" },
|
|
715
|
+
},
|
|
716
|
+
required: ["userTag"],
|
|
717
|
+
additionalProperties: false,
|
|
718
|
+
},
|
|
719
|
+
parse: (args) => userTagSetArgsSchema.parse(args ?? {}),
|
|
720
|
+
execute: async (args) =>
|
|
721
|
+
callAgentApi({
|
|
722
|
+
method: "PUT",
|
|
723
|
+
pathName: "/api/agent/user-tag",
|
|
724
|
+
body: args,
|
|
725
|
+
}),
|
|
726
|
+
},
|
|
727
|
+
{
|
|
728
|
+
name: "checkout_payreq_create",
|
|
729
|
+
description: withWriteSafety("Create a checkout pay request and escrow."),
|
|
730
|
+
inputSchema: {
|
|
731
|
+
type: "object",
|
|
732
|
+
properties: {
|
|
733
|
+
walletId: { oneOf: [{ type: "integer" }, { type: "string" }] },
|
|
734
|
+
walletAddress: { type: "string" },
|
|
735
|
+
amount: { type: "string" },
|
|
736
|
+
expiresInSeconds: { type: "integer" },
|
|
737
|
+
autoReleaseSeconds: { type: "integer" },
|
|
738
|
+
disputeWindowSeconds: { type: "integer" },
|
|
739
|
+
metadata: { type: "object", additionalProperties: true },
|
|
740
|
+
},
|
|
741
|
+
required: ["amount"],
|
|
742
|
+
additionalProperties: false,
|
|
743
|
+
},
|
|
744
|
+
parse: (args) => checkoutCreatePayreqArgsSchema.parse(args ?? {}),
|
|
745
|
+
execute: async (args) =>
|
|
746
|
+
callAgentApi({
|
|
747
|
+
method: "POST",
|
|
748
|
+
pathName: "/api/agent/checkout/payreq",
|
|
749
|
+
body: args,
|
|
750
|
+
}),
|
|
751
|
+
},
|
|
752
|
+
{
|
|
753
|
+
name: "checkout_payreq_get",
|
|
754
|
+
description: "Get checkout pay request details by id.",
|
|
755
|
+
inputSchema: {
|
|
756
|
+
type: "object",
|
|
757
|
+
properties: { id: { type: "string" } },
|
|
758
|
+
required: ["id"],
|
|
759
|
+
additionalProperties: false,
|
|
760
|
+
},
|
|
761
|
+
parse: (args) => checkoutPayreqIdArgsSchema.parse(args ?? {}),
|
|
762
|
+
execute: async (args) =>
|
|
763
|
+
callAgentApi({
|
|
764
|
+
method: "GET",
|
|
765
|
+
pathName: `/api/agent/checkout/payreq/${encodeURIComponent(args.id)}`,
|
|
766
|
+
}),
|
|
767
|
+
},
|
|
768
|
+
{
|
|
769
|
+
name: "checkout_escrow_get",
|
|
770
|
+
description: "Get checkout escrow details by escrow id.",
|
|
771
|
+
inputSchema: {
|
|
772
|
+
type: "object",
|
|
773
|
+
properties: { id: { type: "string" } },
|
|
774
|
+
required: ["id"],
|
|
775
|
+
additionalProperties: false,
|
|
776
|
+
},
|
|
777
|
+
parse: (args) => checkoutEscrowIdArgsSchema.parse(args ?? {}),
|
|
778
|
+
execute: async (args) =>
|
|
779
|
+
callAgentApi({
|
|
780
|
+
method: "GET",
|
|
781
|
+
pathName: `/api/agent/checkout/escrows/${encodeURIComponent(args.id)}`,
|
|
782
|
+
}),
|
|
783
|
+
},
|
|
784
|
+
{
|
|
785
|
+
name: "checkout_funding_confirm",
|
|
786
|
+
description: withWriteSafety("Confirm checkout escrow funding transaction."),
|
|
787
|
+
inputSchema: {
|
|
788
|
+
type: "object",
|
|
789
|
+
properties: {
|
|
790
|
+
id: { type: "string" },
|
|
791
|
+
txHash: { type: "string" },
|
|
792
|
+
minConfirmations: { type: "integer" },
|
|
793
|
+
},
|
|
794
|
+
required: ["id", "txHash"],
|
|
795
|
+
additionalProperties: false,
|
|
796
|
+
},
|
|
797
|
+
parse: (args) => checkoutFundingConfirmArgsSchema.parse(args ?? {}),
|
|
798
|
+
execute: async (args) => {
|
|
799
|
+
const { id, ...body } = args;
|
|
800
|
+
return callAgentApi({
|
|
801
|
+
method: "POST",
|
|
802
|
+
pathName: `/api/agent/checkout/escrows/${encodeURIComponent(id)}/funding-confirm`,
|
|
803
|
+
body,
|
|
804
|
+
});
|
|
805
|
+
},
|
|
806
|
+
},
|
|
807
|
+
{
|
|
808
|
+
name: "checkout_accept",
|
|
809
|
+
description: withWriteSafety("Accept escrow as buyer."),
|
|
810
|
+
inputSchema: {
|
|
811
|
+
type: "object",
|
|
812
|
+
properties: {
|
|
813
|
+
id: { type: "string" },
|
|
814
|
+
},
|
|
815
|
+
required: ["id"],
|
|
816
|
+
additionalProperties: false,
|
|
817
|
+
},
|
|
818
|
+
parse: (args) => checkoutAcceptArgsSchema.parse(args ?? {}),
|
|
819
|
+
execute: async (args) => {
|
|
820
|
+
const { id, ...body } = args;
|
|
821
|
+
return callAgentApi({
|
|
822
|
+
method: "POST",
|
|
823
|
+
pathName: `/api/agent/checkout/escrows/${encodeURIComponent(id)}/accept`,
|
|
824
|
+
body,
|
|
825
|
+
});
|
|
826
|
+
},
|
|
827
|
+
},
|
|
828
|
+
{
|
|
829
|
+
name: "checkout_proof_submit",
|
|
830
|
+
description: withWriteSafety("Submit checkout proof."),
|
|
831
|
+
inputSchema: {
|
|
832
|
+
type: "object",
|
|
833
|
+
properties: {
|
|
834
|
+
id: { type: "string" },
|
|
835
|
+
proofHash: { type: "string" },
|
|
836
|
+
proofUrl: { type: "string" },
|
|
837
|
+
},
|
|
838
|
+
required: ["id", "proofHash"],
|
|
839
|
+
additionalProperties: false,
|
|
840
|
+
},
|
|
841
|
+
parse: (args) => checkoutProofArgsSchema.parse(args ?? {}),
|
|
842
|
+
execute: async (args) => {
|
|
843
|
+
const { id, ...body } = args;
|
|
844
|
+
return callAgentApi({
|
|
845
|
+
method: "POST",
|
|
846
|
+
pathName: `/api/agent/checkout/escrows/${encodeURIComponent(id)}/proof`,
|
|
847
|
+
body,
|
|
848
|
+
});
|
|
849
|
+
},
|
|
850
|
+
},
|
|
851
|
+
{
|
|
852
|
+
name: "checkout_dispute_open",
|
|
853
|
+
description: withWriteSafety("Open checkout dispute."),
|
|
854
|
+
inputSchema: {
|
|
855
|
+
type: "object",
|
|
856
|
+
properties: {
|
|
857
|
+
id: { type: "string" },
|
|
858
|
+
reasonCode: { type: "string" },
|
|
859
|
+
details: { type: "object", additionalProperties: true },
|
|
860
|
+
},
|
|
861
|
+
required: ["id", "reasonCode"],
|
|
862
|
+
additionalProperties: false,
|
|
863
|
+
},
|
|
864
|
+
parse: (args) => checkoutDisputeArgsSchema.parse(args ?? {}),
|
|
865
|
+
execute: async (args) => {
|
|
866
|
+
const { id, ...body } = args;
|
|
867
|
+
return callAgentApi({
|
|
868
|
+
method: "POST",
|
|
869
|
+
pathName: `/api/agent/checkout/escrows/${encodeURIComponent(id)}/dispute`,
|
|
870
|
+
body,
|
|
871
|
+
});
|
|
872
|
+
},
|
|
873
|
+
},
|
|
874
|
+
{
|
|
875
|
+
name: "checkout_quick_pay",
|
|
876
|
+
description: withWriteSafety("Directly fund checkout escrow from buyer wallet."),
|
|
877
|
+
inputSchema: {
|
|
878
|
+
type: "object",
|
|
879
|
+
properties: {
|
|
880
|
+
id: { type: "string" },
|
|
881
|
+
walletId: { oneOf: [{ type: "integer" }, { type: "string" }] },
|
|
882
|
+
walletAddress: { type: "string" },
|
|
883
|
+
},
|
|
884
|
+
required: ["id"],
|
|
885
|
+
additionalProperties: false,
|
|
886
|
+
},
|
|
887
|
+
parse: (args) => checkoutWalletSelectorArgsSchema.parse(args ?? {}),
|
|
888
|
+
execute: async (args) => {
|
|
889
|
+
const { id, ...body } = args;
|
|
890
|
+
return callAgentApi({
|
|
891
|
+
method: "POST",
|
|
892
|
+
pathName: `/api/agent/checkout/escrows/${encodeURIComponent(id)}/quick-pay`,
|
|
893
|
+
body,
|
|
894
|
+
});
|
|
895
|
+
},
|
|
896
|
+
},
|
|
897
|
+
{
|
|
898
|
+
name: "checkout_swap_and_pay",
|
|
899
|
+
description: withWriteSafety("Swap source asset and fund checkout escrow."),
|
|
900
|
+
inputSchema: {
|
|
901
|
+
type: "object",
|
|
902
|
+
properties: {
|
|
903
|
+
id: { type: "string" },
|
|
904
|
+
walletId: { oneOf: [{ type: "integer" }, { type: "string" }] },
|
|
905
|
+
walletAddress: { type: "string" },
|
|
906
|
+
confirm: { type: "boolean" },
|
|
907
|
+
slippage: { type: "number" },
|
|
908
|
+
},
|
|
909
|
+
required: ["id"],
|
|
910
|
+
additionalProperties: false,
|
|
911
|
+
},
|
|
912
|
+
parse: (args) => checkoutSwapAndPayArgsSchema.parse(args ?? {}),
|
|
913
|
+
execute: async (args) => {
|
|
914
|
+
const { id, ...body } = args;
|
|
915
|
+
return callAgentApi({
|
|
916
|
+
method: "POST",
|
|
917
|
+
pathName: `/api/agent/checkout/escrows/${encodeURIComponent(id)}/swap-and-pay`,
|
|
918
|
+
body,
|
|
919
|
+
});
|
|
920
|
+
},
|
|
921
|
+
},
|
|
922
|
+
{
|
|
923
|
+
name: "checkout_release",
|
|
924
|
+
description: withWriteSafety("Release checkout escrow to seller."),
|
|
925
|
+
inputSchema: {
|
|
926
|
+
type: "object",
|
|
927
|
+
properties: {
|
|
928
|
+
id: { type: "string" },
|
|
929
|
+
force: { type: "boolean" },
|
|
930
|
+
},
|
|
931
|
+
required: ["id"],
|
|
932
|
+
additionalProperties: false,
|
|
933
|
+
},
|
|
934
|
+
parse: (args) => checkoutEscrowIdArgsSchema.extend({ force: z.boolean().optional() }).parse(args ?? {}),
|
|
935
|
+
execute: async (args) => {
|
|
936
|
+
const { id, ...body } = args;
|
|
937
|
+
return callAgentApi({
|
|
938
|
+
method: "POST",
|
|
939
|
+
pathName: `/api/agent/checkout/escrows/${encodeURIComponent(id)}/release`,
|
|
940
|
+
body,
|
|
941
|
+
});
|
|
942
|
+
},
|
|
943
|
+
},
|
|
944
|
+
{
|
|
945
|
+
name: "checkout_refund",
|
|
946
|
+
description: withWriteSafety("Refund checkout escrow to buyer."),
|
|
947
|
+
inputSchema: {
|
|
948
|
+
type: "object",
|
|
949
|
+
properties: {
|
|
950
|
+
id: { type: "string" },
|
|
951
|
+
force: { type: "boolean" },
|
|
952
|
+
},
|
|
953
|
+
required: ["id"],
|
|
954
|
+
additionalProperties: false,
|
|
955
|
+
},
|
|
956
|
+
parse: (args) => checkoutEscrowIdArgsSchema.extend({ force: z.boolean().optional() }).parse(args ?? {}),
|
|
957
|
+
execute: async (args) => {
|
|
958
|
+
const { id, ...body } = args;
|
|
959
|
+
return callAgentApi({
|
|
960
|
+
method: "POST",
|
|
961
|
+
pathName: `/api/agent/checkout/escrows/${encodeURIComponent(id)}/refund`,
|
|
962
|
+
body,
|
|
963
|
+
});
|
|
964
|
+
},
|
|
965
|
+
},
|
|
966
|
+
{
|
|
967
|
+
name: "checkout_cancel",
|
|
968
|
+
description: withWriteSafety("Cancel checkout escrow."),
|
|
969
|
+
inputSchema: {
|
|
970
|
+
type: "object",
|
|
971
|
+
properties: {
|
|
972
|
+
id: { type: "string" },
|
|
973
|
+
},
|
|
974
|
+
required: ["id"],
|
|
975
|
+
additionalProperties: false,
|
|
976
|
+
},
|
|
977
|
+
parse: (args) => checkoutEscrowIdArgsSchema.parse(args ?? {}),
|
|
978
|
+
execute: async (args) =>
|
|
979
|
+
callAgentApi({
|
|
980
|
+
method: "POST",
|
|
981
|
+
pathName: `/api/agent/checkout/escrows/${encodeURIComponent(args.id)}/cancel`,
|
|
982
|
+
body: {},
|
|
983
|
+
}),
|
|
984
|
+
},
|
|
985
|
+
{
|
|
986
|
+
name: "checkout_webhooks_list",
|
|
987
|
+
description: "List checkout webhook subscriptions.",
|
|
988
|
+
inputSchema: { type: "object", properties: {}, additionalProperties: false },
|
|
989
|
+
parse: (args) => z.object({}).parse(args ?? {}),
|
|
990
|
+
execute: async () =>
|
|
991
|
+
callAgentApi({
|
|
992
|
+
method: "GET",
|
|
993
|
+
pathName: "/api/agent/checkout/webhooks",
|
|
994
|
+
}),
|
|
995
|
+
},
|
|
996
|
+
{
|
|
997
|
+
name: "checkout_webhook_create",
|
|
998
|
+
description: withWriteSafety("Create checkout webhook subscription."),
|
|
999
|
+
inputSchema: {
|
|
1000
|
+
type: "object",
|
|
1001
|
+
properties: {
|
|
1002
|
+
url: { type: "string" },
|
|
1003
|
+
eventTypes: { type: "array", items: { type: "string" } },
|
|
1004
|
+
enabled: { type: "boolean" },
|
|
1005
|
+
},
|
|
1006
|
+
required: ["url"],
|
|
1007
|
+
additionalProperties: false,
|
|
1008
|
+
},
|
|
1009
|
+
parse: (args) => checkoutWebhookCreateArgsSchema.parse(args ?? {}),
|
|
1010
|
+
execute: async (args) =>
|
|
1011
|
+
callAgentApi({
|
|
1012
|
+
method: "POST",
|
|
1013
|
+
pathName: "/api/agent/checkout/webhooks",
|
|
1014
|
+
body: args,
|
|
1015
|
+
}),
|
|
1016
|
+
},
|
|
1017
|
+
{
|
|
1018
|
+
name: "checkout_webhook_update",
|
|
1019
|
+
description: withWriteSafety("Update checkout webhook subscription."),
|
|
1020
|
+
inputSchema: {
|
|
1021
|
+
type: "object",
|
|
1022
|
+
properties: {
|
|
1023
|
+
id: { oneOf: [{ type: "integer" }, { type: "string" }] },
|
|
1024
|
+
url: { type: "string" },
|
|
1025
|
+
eventTypes: { type: "array", items: { type: "string" } },
|
|
1026
|
+
enabled: { type: "boolean" },
|
|
1027
|
+
},
|
|
1028
|
+
required: ["id"],
|
|
1029
|
+
additionalProperties: false,
|
|
1030
|
+
},
|
|
1031
|
+
parse: (args) => checkoutWebhookUpdateArgsSchema.parse(args ?? {}),
|
|
1032
|
+
execute: async (args) => {
|
|
1033
|
+
const { id, ...body } = args;
|
|
1034
|
+
return callAgentApi({
|
|
1035
|
+
method: "PATCH",
|
|
1036
|
+
pathName: `/api/agent/checkout/webhooks/${encodeURIComponent(String(id))}`,
|
|
1037
|
+
body,
|
|
1038
|
+
});
|
|
1039
|
+
},
|
|
1040
|
+
},
|
|
1041
|
+
{
|
|
1042
|
+
name: "checkout_webhook_delete",
|
|
1043
|
+
description: withWriteSafety("Delete checkout webhook subscription."),
|
|
1044
|
+
inputSchema: {
|
|
1045
|
+
type: "object",
|
|
1046
|
+
properties: {
|
|
1047
|
+
id: { oneOf: [{ type: "integer" }, { type: "string" }] },
|
|
1048
|
+
},
|
|
1049
|
+
required: ["id"],
|
|
1050
|
+
additionalProperties: false,
|
|
1051
|
+
},
|
|
1052
|
+
parse: (args) => checkoutWebhookDeleteArgsSchema.parse(args ?? {}),
|
|
1053
|
+
execute: async (args) =>
|
|
1054
|
+
callAgentApi({
|
|
1055
|
+
method: "DELETE",
|
|
1056
|
+
pathName: `/api/agent/checkout/webhooks/${encodeURIComponent(String(args.id))}`,
|
|
1057
|
+
}),
|
|
1058
|
+
},
|
|
1059
|
+
{
|
|
1060
|
+
name: "polymarket_order_limit",
|
|
1061
|
+
description: withWriteSafety("Place a Polymarket limit order from a configured polygon-mainnet wallet."),
|
|
1062
|
+
inputSchema: {
|
|
1063
|
+
type: "object",
|
|
1064
|
+
properties: {
|
|
1065
|
+
walletId: { oneOf: [{ type: "integer" }, { type: "string" }] },
|
|
1066
|
+
walletAddress: { type: "string" },
|
|
1067
|
+
tokenId: { type: "string" },
|
|
1068
|
+
side: { type: "string", enum: ["BUY", "SELL"] },
|
|
1069
|
+
price: { type: "number" },
|
|
1070
|
+
size: { type: "number" },
|
|
1071
|
+
},
|
|
1072
|
+
required: ["tokenId", "side", "price", "size"],
|
|
1073
|
+
additionalProperties: false,
|
|
1074
|
+
},
|
|
1075
|
+
parse: (args) => polymarketLimitArgsSchema.parse(args ?? {}),
|
|
1076
|
+
execute: async (args) =>
|
|
1077
|
+
callAgentApi({
|
|
1078
|
+
method: "POST",
|
|
1079
|
+
pathName: "/api/agent/venues/polymarket/orders/limit",
|
|
1080
|
+
body: args,
|
|
1081
|
+
}),
|
|
1082
|
+
},
|
|
1083
|
+
{
|
|
1084
|
+
name: "polymarket_order_market",
|
|
1085
|
+
description: withWriteSafety("Place a Polymarket market order from a configured polygon-mainnet wallet."),
|
|
1086
|
+
inputSchema: {
|
|
1087
|
+
type: "object",
|
|
1088
|
+
properties: {
|
|
1089
|
+
walletId: { oneOf: [{ type: "integer" }, { type: "string" }] },
|
|
1090
|
+
walletAddress: { type: "string" },
|
|
1091
|
+
tokenId: { type: "string" },
|
|
1092
|
+
side: { type: "string", enum: ["BUY", "SELL"] },
|
|
1093
|
+
amount: { type: "number" },
|
|
1094
|
+
orderType: { type: "string", enum: ["FAK", "FOK", "GTC"] },
|
|
1095
|
+
worstPrice: { type: "number" },
|
|
1096
|
+
},
|
|
1097
|
+
required: ["tokenId", "side", "amount"],
|
|
1098
|
+
additionalProperties: false,
|
|
1099
|
+
},
|
|
1100
|
+
parse: (args) => polymarketMarketArgsSchema.parse(args ?? {}),
|
|
1101
|
+
execute: async (args) =>
|
|
1102
|
+
callAgentApi({
|
|
1103
|
+
method: "POST",
|
|
1104
|
+
pathName: "/api/agent/venues/polymarket/orders/market",
|
|
1105
|
+
body: args,
|
|
1106
|
+
}),
|
|
1107
|
+
},
|
|
1108
|
+
{
|
|
1109
|
+
name: "polymarket_account",
|
|
1110
|
+
description: "Read Polymarket account summary for a configured polygon-mainnet wallet.",
|
|
1111
|
+
inputSchema: {
|
|
1112
|
+
type: "object",
|
|
1113
|
+
properties: {
|
|
1114
|
+
walletId: { oneOf: [{ type: "integer" }, { type: "string" }] },
|
|
1115
|
+
walletAddress: { type: "string" },
|
|
1116
|
+
},
|
|
1117
|
+
additionalProperties: false,
|
|
1118
|
+
},
|
|
1119
|
+
parse: (args) => polymarketReadArgsSchema.parse(args ?? {}),
|
|
1120
|
+
execute: async (args) =>
|
|
1121
|
+
callAgentApi({
|
|
1122
|
+
method: "GET",
|
|
1123
|
+
pathName: "/api/agent/venues/polymarket/account",
|
|
1124
|
+
query: args,
|
|
1125
|
+
}),
|
|
1126
|
+
},
|
|
1127
|
+
{
|
|
1128
|
+
name: "polymarket_orders",
|
|
1129
|
+
description: "List Polymarket open orders for a configured polygon-mainnet wallet.",
|
|
1130
|
+
inputSchema: {
|
|
1131
|
+
type: "object",
|
|
1132
|
+
properties: {
|
|
1133
|
+
walletId: { oneOf: [{ type: "integer" }, { type: "string" }] },
|
|
1134
|
+
walletAddress: { type: "string" },
|
|
1135
|
+
status: { type: "string" },
|
|
1136
|
+
limit: { type: "integer" },
|
|
1137
|
+
cursor: { type: "string" },
|
|
1138
|
+
},
|
|
1139
|
+
additionalProperties: false,
|
|
1140
|
+
},
|
|
1141
|
+
parse: (args) => polymarketReadArgsSchema.parse(args ?? {}),
|
|
1142
|
+
execute: async (args) =>
|
|
1143
|
+
callAgentApi({
|
|
1144
|
+
method: "GET",
|
|
1145
|
+
pathName: "/api/agent/venues/polymarket/orders",
|
|
1146
|
+
query: args,
|
|
1147
|
+
}),
|
|
1148
|
+
},
|
|
1149
|
+
{
|
|
1150
|
+
name: "polymarket_cancel_order",
|
|
1151
|
+
description: withWriteSafety("Cancel a Polymarket order for a configured polygon-mainnet wallet."),
|
|
1152
|
+
inputSchema: {
|
|
1153
|
+
type: "object",
|
|
1154
|
+
properties: {
|
|
1155
|
+
walletId: { oneOf: [{ type: "integer" }, { type: "string" }] },
|
|
1156
|
+
walletAddress: { type: "string" },
|
|
1157
|
+
orderId: { type: "string" },
|
|
1158
|
+
},
|
|
1159
|
+
required: ["orderId"],
|
|
1160
|
+
additionalProperties: false,
|
|
1161
|
+
},
|
|
1162
|
+
parse: (args) => polymarketCancelArgsSchema.parse(args ?? {}),
|
|
1163
|
+
execute: async (args) =>
|
|
1164
|
+
callAgentApi({
|
|
1165
|
+
method: "POST",
|
|
1166
|
+
pathName: "/api/agent/venues/polymarket/orders/cancel",
|
|
1167
|
+
body: args,
|
|
1168
|
+
}),
|
|
1169
|
+
},
|
|
1170
|
+
{
|
|
1171
|
+
name: "polymarket_activity",
|
|
1172
|
+
description: "List Polymarket trade activity for a configured polygon-mainnet wallet.",
|
|
1173
|
+
inputSchema: {
|
|
1174
|
+
type: "object",
|
|
1175
|
+
properties: {
|
|
1176
|
+
walletId: { oneOf: [{ type: "integer" }, { type: "string" }] },
|
|
1177
|
+
walletAddress: { type: "string" },
|
|
1178
|
+
limit: { type: "integer" },
|
|
1179
|
+
cursor: { type: "string" },
|
|
1180
|
+
},
|
|
1181
|
+
additionalProperties: false,
|
|
1182
|
+
},
|
|
1183
|
+
parse: (args) => polymarketReadArgsSchema.parse(args ?? {}),
|
|
1184
|
+
execute: async (args) =>
|
|
1185
|
+
callAgentApi({
|
|
1186
|
+
method: "GET",
|
|
1187
|
+
pathName: "/api/agent/venues/polymarket/activity",
|
|
1188
|
+
query: args,
|
|
1189
|
+
}),
|
|
1190
|
+
},
|
|
1191
|
+
{
|
|
1192
|
+
name: "polymarket_positions",
|
|
1193
|
+
description: "List Polymarket open positions (open-market filtered) for a configured polygon-mainnet wallet, including position PnL fields.",
|
|
1194
|
+
inputSchema: {
|
|
1195
|
+
type: "object",
|
|
1196
|
+
properties: {
|
|
1197
|
+
walletId: { oneOf: [{ type: "integer" }, { type: "string" }] },
|
|
1198
|
+
walletAddress: { type: "string" },
|
|
1199
|
+
limit: { type: "integer" },
|
|
1200
|
+
},
|
|
1201
|
+
additionalProperties: false,
|
|
1202
|
+
},
|
|
1203
|
+
parse: (args) => polymarketReadArgsSchema.parse(args ?? {}),
|
|
1204
|
+
execute: async (args) =>
|
|
1205
|
+
callAgentApi({
|
|
1206
|
+
method: "GET",
|
|
1207
|
+
pathName: "/api/agent/venues/polymarket/positions",
|
|
1208
|
+
query: args,
|
|
1209
|
+
}),
|
|
1210
|
+
},
|
|
536
1211
|
];
|
|
537
1212
|
|
|
538
1213
|
const resources = [
|
|
@@ -561,6 +1236,7 @@ const resources = [
|
|
|
561
1236
|
"3. Use `wallet_get` or `balances_get` before write actions.",
|
|
562
1237
|
"4. For writes, establish approval mode once per session.",
|
|
563
1238
|
"5. Use `swap_quote` before `swap_execute`.",
|
|
1239
|
+
"6. For Polymarket: ask your human to complete setup in dashboard (/venues/polymarket), then place/cancel orders and inspect account/activity/positions via polymarket tools.",
|
|
564
1240
|
].join("\n"),
|
|
565
1241
|
},
|
|
566
1242
|
];
|
|
@@ -666,7 +1342,7 @@ async function runSelfTest() {
|
|
|
666
1342
|
capabilities: {},
|
|
667
1343
|
clientInfo: {
|
|
668
1344
|
name: "openclawcash-self-test",
|
|
669
|
-
version:
|
|
1345
|
+
version: SERVER_VERSION,
|
|
670
1346
|
},
|
|
671
1347
|
},
|
|
672
1348
|
};
|
package/package.json
CHANGED