@wiimdy/openfunderse-agents 0.1.1
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/.env.example +51 -0
- package/README.md +252 -0
- package/dist/clawbot-cli.d.ts +1 -0
- package/dist/clawbot-cli.js +114 -0
- package/dist/index.d.ts +10 -0
- package/dist/index.js +34 -0
- package/dist/lib/aa-client.d.ts +67 -0
- package/dist/lib/aa-client.js +353 -0
- package/dist/lib/relayer-client.d.ts +171 -0
- package/dist/lib/relayer-client.js +486 -0
- package/dist/lib/signer.d.ts +38 -0
- package/dist/lib/signer.js +103 -0
- package/dist/participant-cli.d.ts +1 -0
- package/dist/participant-cli.js +399 -0
- package/dist/reddit-mvp.d.ts +1 -0
- package/dist/reddit-mvp.js +546 -0
- package/dist/skills/participant/index.d.ts +116 -0
- package/dist/skills/participant/index.js +462 -0
- package/dist/skills/strategy/index.d.ts +117 -0
- package/dist/skills/strategy/index.js +879 -0
- package/dist/strategy-cli.d.ts +1 -0
- package/dist/strategy-cli.js +867 -0
- package/package.json +42 -0
|
@@ -0,0 +1,353 @@
|
|
|
1
|
+
import { concatHex, createPublicClient, defineChain, encodeFunctionData, http, padHex, parseAbi, toHex } from 'viem';
|
|
2
|
+
import { privateKeyToAccount } from 'viem/accounts';
|
|
3
|
+
const ENTRYPOINT_V07_ABI = parseAbi([
|
|
4
|
+
'function getNonce(address sender, uint192 key) view returns (uint256)',
|
|
5
|
+
'function getUserOpHash((address sender,uint256 nonce,bytes initCode,bytes callData,bytes32 accountGasLimits,uint256 preVerificationGas,bytes32 gasFees,bytes paymasterAndData,bytes signature) userOp) view returns (bytes32)'
|
|
6
|
+
]);
|
|
7
|
+
const ENTRYPOINT_V06_ABI = parseAbi([
|
|
8
|
+
'function getNonce(address sender, uint192 key) view returns (uint256)',
|
|
9
|
+
'function getUserOpHash((address sender,uint256 nonce,bytes initCode,bytes callData,uint256 callGasLimit,uint256 verificationGasLimit,uint256 preVerificationGas,uint256 maxFeePerGas,uint256 maxPriorityFeePerGas,bytes paymasterAndData,bytes signature) userOp) view returns (bytes32)'
|
|
10
|
+
]);
|
|
11
|
+
const SIMPLE_ACCOUNT_ABI = parseAbi([
|
|
12
|
+
'function execute(address dest, uint256 value, bytes data)'
|
|
13
|
+
]);
|
|
14
|
+
const DEFAULT_CALL_GAS_LIMIT = 400000n;
|
|
15
|
+
const DEFAULT_VERIFICATION_GAS_LIMIT = 300000n;
|
|
16
|
+
const DEFAULT_PRE_VERIFICATION_GAS_V07 = 60000n;
|
|
17
|
+
const DEFAULT_PRE_VERIFICATION_GAS_V06 = 2000000n;
|
|
18
|
+
const DEFAULT_POLL_INTERVAL_MS = 3_000;
|
|
19
|
+
const DEFAULT_TIMEOUT_MS = 120_000;
|
|
20
|
+
const toU128Hex = (value) => {
|
|
21
|
+
if (value < 0n) {
|
|
22
|
+
throw new Error('u128 value must be non-negative');
|
|
23
|
+
}
|
|
24
|
+
return padHex(toHex(value), { size: 16 });
|
|
25
|
+
};
|
|
26
|
+
const packU128 = (left, right) => {
|
|
27
|
+
return concatHex([toU128Hex(left), toU128Hex(right)]);
|
|
28
|
+
};
|
|
29
|
+
export class StrategyAaClient {
|
|
30
|
+
config;
|
|
31
|
+
publicClient;
|
|
32
|
+
owner;
|
|
33
|
+
constructor(config) {
|
|
34
|
+
this.config = config;
|
|
35
|
+
this.owner = privateKeyToAccount(config.ownerPrivateKey);
|
|
36
|
+
const chain = defineChain({
|
|
37
|
+
id: config.chainId,
|
|
38
|
+
name: `strategy-aa-${config.chainId}`,
|
|
39
|
+
nativeCurrency: { name: 'MON', symbol: 'MON', decimals: 18 },
|
|
40
|
+
rpcUrls: {
|
|
41
|
+
default: { http: [config.rpcUrl] },
|
|
42
|
+
public: { http: [config.rpcUrl] }
|
|
43
|
+
}
|
|
44
|
+
});
|
|
45
|
+
this.publicClient = createPublicClient({
|
|
46
|
+
chain,
|
|
47
|
+
transport: http(config.rpcUrl)
|
|
48
|
+
});
|
|
49
|
+
}
|
|
50
|
+
static fromEnv(overrides = {}) {
|
|
51
|
+
const chainIdRaw = process.env.CHAIN_ID ?? '10143';
|
|
52
|
+
const envChainId = Number(chainIdRaw);
|
|
53
|
+
const chainId = overrides.chainId ?? envChainId;
|
|
54
|
+
const rpcUrl = overrides.rpcUrl ?? process.env.STRATEGY_AA_RPC_URL ?? process.env.RPC_URL ?? '';
|
|
55
|
+
const bundlerUrl = overrides.bundlerUrl ?? process.env.STRATEGY_AA_BUNDLER_URL ?? '';
|
|
56
|
+
const entryPoint = overrides.entryPoint ?? process.env.STRATEGY_AA_ENTRYPOINT_ADDRESS ?? '';
|
|
57
|
+
const smartAccount = overrides.smartAccount ?? process.env.STRATEGY_AA_ACCOUNT_ADDRESS ?? '';
|
|
58
|
+
const ownerPrivateKey = overrides.ownerPrivateKey ??
|
|
59
|
+
process.env.STRATEGY_AA_OWNER_PRIVATE_KEY ??
|
|
60
|
+
process.env.STRATEGY_PRIVATE_KEY ??
|
|
61
|
+
'';
|
|
62
|
+
const rawUserOpVersion = (overrides.userOpVersion ?? process.env.STRATEGY_AA_USER_OP_VERSION ?? 'v07')
|
|
63
|
+
.toLowerCase();
|
|
64
|
+
if (rawUserOpVersion !== 'v06' && rawUserOpVersion !== 'v07') {
|
|
65
|
+
throw new Error('STRATEGY_AA_USER_OP_VERSION must be one of: v06, v07');
|
|
66
|
+
}
|
|
67
|
+
if (!rpcUrl)
|
|
68
|
+
throw new Error('STRATEGY_AA_RPC_URL (or RPC_URL) is required');
|
|
69
|
+
if (!bundlerUrl)
|
|
70
|
+
throw new Error('STRATEGY_AA_BUNDLER_URL is required');
|
|
71
|
+
if (!entryPoint)
|
|
72
|
+
throw new Error('STRATEGY_AA_ENTRYPOINT_ADDRESS is required');
|
|
73
|
+
if (!smartAccount)
|
|
74
|
+
throw new Error('STRATEGY_AA_ACCOUNT_ADDRESS is required');
|
|
75
|
+
if (!ownerPrivateKey) {
|
|
76
|
+
throw new Error('STRATEGY_AA_OWNER_PRIVATE_KEY (or STRATEGY_PRIVATE_KEY) is required');
|
|
77
|
+
}
|
|
78
|
+
if (!Number.isFinite(chainId) || chainId <= 0) {
|
|
79
|
+
throw new Error('CHAIN_ID must be a positive number');
|
|
80
|
+
}
|
|
81
|
+
const parseBigIntEnv = (name) => {
|
|
82
|
+
const raw = process.env[name];
|
|
83
|
+
if (!raw || raw.trim().length === 0)
|
|
84
|
+
return undefined;
|
|
85
|
+
return BigInt(raw);
|
|
86
|
+
};
|
|
87
|
+
const parseNumberEnv = (name) => {
|
|
88
|
+
const raw = process.env[name];
|
|
89
|
+
if (!raw || raw.trim().length === 0)
|
|
90
|
+
return undefined;
|
|
91
|
+
const value = Number(raw);
|
|
92
|
+
if (!Number.isFinite(value) || value <= 0) {
|
|
93
|
+
throw new Error(`${name} must be a positive number`);
|
|
94
|
+
}
|
|
95
|
+
return Math.trunc(value);
|
|
96
|
+
};
|
|
97
|
+
return new StrategyAaClient({
|
|
98
|
+
chainId: Math.trunc(chainId),
|
|
99
|
+
rpcUrl,
|
|
100
|
+
bundlerUrl,
|
|
101
|
+
entryPoint: entryPoint,
|
|
102
|
+
smartAccount: smartAccount,
|
|
103
|
+
ownerPrivateKey: ownerPrivateKey,
|
|
104
|
+
initCode: overrides.initCode ??
|
|
105
|
+
(process.env.STRATEGY_AA_INIT_CODE ?? '0x'),
|
|
106
|
+
callGasLimit: overrides.callGasLimit ?? parseBigIntEnv('STRATEGY_AA_CALL_GAS_LIMIT'),
|
|
107
|
+
verificationGasLimit: overrides.verificationGasLimit ?? parseBigIntEnv('STRATEGY_AA_VERIFICATION_GAS_LIMIT'),
|
|
108
|
+
preVerificationGas: overrides.preVerificationGas ?? parseBigIntEnv('STRATEGY_AA_PRE_VERIFICATION_GAS'),
|
|
109
|
+
maxPriorityFeePerGas: overrides.maxPriorityFeePerGas ?? parseBigIntEnv('STRATEGY_AA_MAX_PRIORITY_FEE_PER_GAS'),
|
|
110
|
+
maxFeePerGas: overrides.maxFeePerGas ?? parseBigIntEnv('STRATEGY_AA_MAX_FEE_PER_GAS'),
|
|
111
|
+
pollIntervalMs: overrides.pollIntervalMs ?? parseNumberEnv('STRATEGY_AA_POLL_INTERVAL_MS'),
|
|
112
|
+
timeoutMs: overrides.timeoutMs ?? parseNumberEnv('STRATEGY_AA_TIMEOUT_MS'),
|
|
113
|
+
userOpVersion: rawUserOpVersion
|
|
114
|
+
});
|
|
115
|
+
}
|
|
116
|
+
async sendExecute(input) {
|
|
117
|
+
const callData = encodeFunctionData({
|
|
118
|
+
abi: SIMPLE_ACCOUNT_ABI,
|
|
119
|
+
functionName: 'execute',
|
|
120
|
+
args: [input.target, input.value ?? 0n, input.data]
|
|
121
|
+
});
|
|
122
|
+
return this.sendUserOperation(callData);
|
|
123
|
+
}
|
|
124
|
+
async sendUserOperation(callData) {
|
|
125
|
+
if (this.userOpVersion() === 'v06') {
|
|
126
|
+
const userOp = await this.buildSignedUserOperationV06(callData);
|
|
127
|
+
const rpcUserOp = this.toRpcUserOperationV06(userOp);
|
|
128
|
+
return this.submitUserOperation(rpcUserOp);
|
|
129
|
+
}
|
|
130
|
+
const userOp = await this.buildSignedUserOperationV07(callData);
|
|
131
|
+
const rpcUserOp = this.toRpcUserOperationV07(userOp);
|
|
132
|
+
return this.submitUserOperation(rpcUserOp);
|
|
133
|
+
}
|
|
134
|
+
async waitForUserOperationReceipt(userOpHash) {
|
|
135
|
+
const pollIntervalMs = this.config.pollIntervalMs ?? DEFAULT_POLL_INTERVAL_MS;
|
|
136
|
+
const timeoutMs = this.config.timeoutMs ?? DEFAULT_TIMEOUT_MS;
|
|
137
|
+
const deadline = Date.now() + timeoutMs;
|
|
138
|
+
while (Date.now() <= deadline) {
|
|
139
|
+
const receipt = await this.callBundler('eth_getUserOperationReceipt', [userOpHash]);
|
|
140
|
+
if (receipt) {
|
|
141
|
+
return receipt;
|
|
142
|
+
}
|
|
143
|
+
await new Promise((resolve) => setTimeout(resolve, pollIntervalMs));
|
|
144
|
+
}
|
|
145
|
+
throw new Error(`UserOperation receipt timeout after ${timeoutMs}ms: ${userOpHash}`);
|
|
146
|
+
}
|
|
147
|
+
userOpVersion() {
|
|
148
|
+
return this.config.userOpVersion ?? 'v07';
|
|
149
|
+
}
|
|
150
|
+
async submitUserOperation(rpcUserOp) {
|
|
151
|
+
const userOpHash = await this.callBundler('eth_sendUserOperation', [
|
|
152
|
+
rpcUserOp,
|
|
153
|
+
this.config.entryPoint
|
|
154
|
+
]);
|
|
155
|
+
const receipt = await this.waitForUserOperationReceipt(userOpHash);
|
|
156
|
+
const maybeTxHash = receipt?.receipt
|
|
157
|
+
?.transactionHash;
|
|
158
|
+
const transactionHash = typeof maybeTxHash === 'string' && /^0x[0-9a-fA-F]{64}$/.test(maybeTxHash)
|
|
159
|
+
? maybeTxHash
|
|
160
|
+
: null;
|
|
161
|
+
return {
|
|
162
|
+
userOpHash,
|
|
163
|
+
receipt,
|
|
164
|
+
transactionHash
|
|
165
|
+
};
|
|
166
|
+
}
|
|
167
|
+
async resolveGasFees(preferBundlerGasRpc) {
|
|
168
|
+
let maxPriorityFeePerGas = this.config.maxPriorityFeePerGas;
|
|
169
|
+
let maxFeePerGas = this.config.maxFeePerGas;
|
|
170
|
+
if (preferBundlerGasRpc && (maxPriorityFeePerGas === undefined || maxFeePerGas === undefined)) {
|
|
171
|
+
const bundlerGas = await this.tryResolveBundlerGasFees();
|
|
172
|
+
if (bundlerGas) {
|
|
173
|
+
maxPriorityFeePerGas = maxPriorityFeePerGas ?? bundlerGas.maxPriorityFeePerGas;
|
|
174
|
+
maxFeePerGas = maxFeePerGas ?? bundlerGas.maxFeePerGas;
|
|
175
|
+
}
|
|
176
|
+
}
|
|
177
|
+
if (maxPriorityFeePerGas === undefined || maxFeePerGas === undefined) {
|
|
178
|
+
try {
|
|
179
|
+
const fee = await this.publicClient.estimateFeesPerGas();
|
|
180
|
+
const fallback = fee.gasPrice ?? 1n;
|
|
181
|
+
maxPriorityFeePerGas = maxPriorityFeePerGas ?? fee.maxPriorityFeePerGas ?? fallback;
|
|
182
|
+
maxFeePerGas = maxFeePerGas ?? fee.maxFeePerGas ?? fallback;
|
|
183
|
+
}
|
|
184
|
+
catch {
|
|
185
|
+
const gasPrice = await this.publicClient.getGasPrice();
|
|
186
|
+
maxPriorityFeePerGas = maxPriorityFeePerGas ?? gasPrice;
|
|
187
|
+
maxFeePerGas = maxFeePerGas ?? gasPrice;
|
|
188
|
+
}
|
|
189
|
+
}
|
|
190
|
+
return { maxPriorityFeePerGas, maxFeePerGas };
|
|
191
|
+
}
|
|
192
|
+
parseBigIntLike(raw) {
|
|
193
|
+
if (typeof raw === 'bigint') {
|
|
194
|
+
return raw;
|
|
195
|
+
}
|
|
196
|
+
if (typeof raw === 'number') {
|
|
197
|
+
if (!Number.isFinite(raw) || raw < 0)
|
|
198
|
+
return null;
|
|
199
|
+
return BigInt(Math.trunc(raw));
|
|
200
|
+
}
|
|
201
|
+
if (typeof raw === 'string' && raw.trim().length > 0) {
|
|
202
|
+
try {
|
|
203
|
+
return BigInt(raw);
|
|
204
|
+
}
|
|
205
|
+
catch {
|
|
206
|
+
return null;
|
|
207
|
+
}
|
|
208
|
+
}
|
|
209
|
+
return null;
|
|
210
|
+
}
|
|
211
|
+
async tryResolveBundlerGasFees() {
|
|
212
|
+
try {
|
|
213
|
+
const response = await this.callBundler('pimlico_getUserOperationGasPrice', []);
|
|
214
|
+
const level = response.standard ?? response.fast ?? response.slow;
|
|
215
|
+
if (!level)
|
|
216
|
+
return null;
|
|
217
|
+
const maxFeePerGas = this.parseBigIntLike(level.maxFeePerGas);
|
|
218
|
+
const maxPriorityFeePerGas = this.parseBigIntLike(level.maxPriorityFeePerGas);
|
|
219
|
+
if (maxFeePerGas === null || maxPriorityFeePerGas === null) {
|
|
220
|
+
return null;
|
|
221
|
+
}
|
|
222
|
+
return { maxPriorityFeePerGas, maxFeePerGas };
|
|
223
|
+
}
|
|
224
|
+
catch {
|
|
225
|
+
return null;
|
|
226
|
+
}
|
|
227
|
+
}
|
|
228
|
+
async buildSignedUserOperationV07(callData) {
|
|
229
|
+
const nonce = await this.publicClient.readContract({
|
|
230
|
+
address: this.config.entryPoint,
|
|
231
|
+
abi: ENTRYPOINT_V07_ABI,
|
|
232
|
+
functionName: 'getNonce',
|
|
233
|
+
args: [this.config.smartAccount, 0n]
|
|
234
|
+
});
|
|
235
|
+
const { maxPriorityFeePerGas, maxFeePerGas } = await this.resolveGasFees(false);
|
|
236
|
+
const callGasLimit = this.config.callGasLimit ?? DEFAULT_CALL_GAS_LIMIT;
|
|
237
|
+
const verificationGasLimit = this.config.verificationGasLimit ?? DEFAULT_VERIFICATION_GAS_LIMIT;
|
|
238
|
+
const preVerificationGas = this.config.preVerificationGas ?? DEFAULT_PRE_VERIFICATION_GAS_V07;
|
|
239
|
+
const draft = {
|
|
240
|
+
sender: this.config.smartAccount,
|
|
241
|
+
nonce,
|
|
242
|
+
initCode: this.config.initCode ?? '0x',
|
|
243
|
+
callData,
|
|
244
|
+
accountGasLimits: packU128(verificationGasLimit, callGasLimit),
|
|
245
|
+
preVerificationGas,
|
|
246
|
+
gasFees: packU128(maxPriorityFeePerGas, maxFeePerGas),
|
|
247
|
+
paymasterAndData: '0x',
|
|
248
|
+
signature: '0x'
|
|
249
|
+
};
|
|
250
|
+
const userOpHash = await this.publicClient.readContract({
|
|
251
|
+
address: this.config.entryPoint,
|
|
252
|
+
abi: ENTRYPOINT_V07_ABI,
|
|
253
|
+
functionName: 'getUserOpHash',
|
|
254
|
+
args: [draft]
|
|
255
|
+
});
|
|
256
|
+
const signature = await this.owner.signMessage({
|
|
257
|
+
message: { raw: userOpHash }
|
|
258
|
+
});
|
|
259
|
+
return {
|
|
260
|
+
...draft,
|
|
261
|
+
signature
|
|
262
|
+
};
|
|
263
|
+
}
|
|
264
|
+
async buildSignedUserOperationV06(callData) {
|
|
265
|
+
const nonce = await this.publicClient.readContract({
|
|
266
|
+
address: this.config.entryPoint,
|
|
267
|
+
abi: ENTRYPOINT_V06_ABI,
|
|
268
|
+
functionName: 'getNonce',
|
|
269
|
+
args: [this.config.smartAccount, 0n]
|
|
270
|
+
});
|
|
271
|
+
const { maxPriorityFeePerGas, maxFeePerGas } = await this.resolveGasFees(true);
|
|
272
|
+
const callGasLimit = this.config.callGasLimit ?? DEFAULT_CALL_GAS_LIMIT;
|
|
273
|
+
const verificationGasLimit = this.config.verificationGasLimit ?? DEFAULT_VERIFICATION_GAS_LIMIT;
|
|
274
|
+
const preVerificationGas = this.config.preVerificationGas ?? DEFAULT_PRE_VERIFICATION_GAS_V06;
|
|
275
|
+
const draft = {
|
|
276
|
+
sender: this.config.smartAccount,
|
|
277
|
+
nonce,
|
|
278
|
+
initCode: this.config.initCode ?? '0x',
|
|
279
|
+
callData,
|
|
280
|
+
callGasLimit,
|
|
281
|
+
verificationGasLimit,
|
|
282
|
+
preVerificationGas,
|
|
283
|
+
maxFeePerGas,
|
|
284
|
+
maxPriorityFeePerGas,
|
|
285
|
+
paymasterAndData: '0x',
|
|
286
|
+
signature: '0x'
|
|
287
|
+
};
|
|
288
|
+
const userOpHash = await this.publicClient.readContract({
|
|
289
|
+
address: this.config.entryPoint,
|
|
290
|
+
abi: ENTRYPOINT_V06_ABI,
|
|
291
|
+
functionName: 'getUserOpHash',
|
|
292
|
+
args: [draft]
|
|
293
|
+
});
|
|
294
|
+
const signature = await this.owner.signMessage({
|
|
295
|
+
message: { raw: userOpHash }
|
|
296
|
+
});
|
|
297
|
+
return {
|
|
298
|
+
...draft,
|
|
299
|
+
signature
|
|
300
|
+
};
|
|
301
|
+
}
|
|
302
|
+
toRpcUserOperationV07(userOp) {
|
|
303
|
+
return {
|
|
304
|
+
sender: userOp.sender,
|
|
305
|
+
nonce: toHex(userOp.nonce),
|
|
306
|
+
initCode: userOp.initCode,
|
|
307
|
+
callData: userOp.callData,
|
|
308
|
+
accountGasLimits: userOp.accountGasLimits,
|
|
309
|
+
preVerificationGas: toHex(userOp.preVerificationGas),
|
|
310
|
+
gasFees: userOp.gasFees,
|
|
311
|
+
paymasterAndData: userOp.paymasterAndData,
|
|
312
|
+
signature: userOp.signature
|
|
313
|
+
};
|
|
314
|
+
}
|
|
315
|
+
toRpcUserOperationV06(userOp) {
|
|
316
|
+
return {
|
|
317
|
+
sender: userOp.sender,
|
|
318
|
+
nonce: toHex(userOp.nonce),
|
|
319
|
+
initCode: userOp.initCode,
|
|
320
|
+
callData: userOp.callData,
|
|
321
|
+
callGasLimit: toHex(userOp.callGasLimit),
|
|
322
|
+
verificationGasLimit: toHex(userOp.verificationGasLimit),
|
|
323
|
+
preVerificationGas: toHex(userOp.preVerificationGas),
|
|
324
|
+
maxFeePerGas: toHex(userOp.maxFeePerGas),
|
|
325
|
+
maxPriorityFeePerGas: toHex(userOp.maxPriorityFeePerGas),
|
|
326
|
+
paymasterAndData: userOp.paymasterAndData,
|
|
327
|
+
signature: userOp.signature
|
|
328
|
+
};
|
|
329
|
+
}
|
|
330
|
+
async callBundler(method, params) {
|
|
331
|
+
const payload = {
|
|
332
|
+
jsonrpc: '2.0',
|
|
333
|
+
id: Date.now(),
|
|
334
|
+
method,
|
|
335
|
+
params
|
|
336
|
+
};
|
|
337
|
+
const response = await fetch(this.config.bundlerUrl, {
|
|
338
|
+
method: 'POST',
|
|
339
|
+
headers: {
|
|
340
|
+
'Content-Type': 'application/json'
|
|
341
|
+
},
|
|
342
|
+
body: JSON.stringify(payload)
|
|
343
|
+
});
|
|
344
|
+
if (!response.ok) {
|
|
345
|
+
throw new Error(`Bundler request failed (${response.status}): ${response.statusText}`);
|
|
346
|
+
}
|
|
347
|
+
const json = (await response.json());
|
|
348
|
+
if ('error' in json) {
|
|
349
|
+
throw new Error(`Bundler RPC error ${json.error.code}: ${json.error.message}${json.error.data ? ` (${JSON.stringify(json.error.data)})` : ''}`);
|
|
350
|
+
}
|
|
351
|
+
return json.result;
|
|
352
|
+
}
|
|
353
|
+
}
|
|
@@ -0,0 +1,171 @@
|
|
|
1
|
+
import { type Address, type ClaimPayload, type Hex, type IntentExecutionRouteInput, type TradeIntent } from '@claw/protocol-sdk';
|
|
2
|
+
export interface ClaimTemplateInput {
|
|
3
|
+
templateType: string;
|
|
4
|
+
sourceRef: string;
|
|
5
|
+
raw: unknown;
|
|
6
|
+
observedAt?: bigint | number | string;
|
|
7
|
+
meta?: Record<string, unknown>;
|
|
8
|
+
sourceType?: string;
|
|
9
|
+
selector?: string;
|
|
10
|
+
extractedType?: string;
|
|
11
|
+
evidenceType?: string;
|
|
12
|
+
evidenceURI?: string;
|
|
13
|
+
notes?: string;
|
|
14
|
+
crawler?: Address;
|
|
15
|
+
}
|
|
16
|
+
export interface ClaimQuery {
|
|
17
|
+
status?: 'PENDING' | 'APPROVED' | 'REJECTED';
|
|
18
|
+
epochId?: bigint | number | string;
|
|
19
|
+
limit?: number;
|
|
20
|
+
offset?: number;
|
|
21
|
+
}
|
|
22
|
+
export interface ClaimAttestationInput {
|
|
23
|
+
claimHash: Hex;
|
|
24
|
+
epochId: bigint | number | string;
|
|
25
|
+
verifier: Address;
|
|
26
|
+
expiresAt: bigint | number | string;
|
|
27
|
+
nonce: bigint | number | string;
|
|
28
|
+
signature: Hex;
|
|
29
|
+
}
|
|
30
|
+
export interface IntentAttestationInput {
|
|
31
|
+
intentHash: Hex;
|
|
32
|
+
verifier: Address;
|
|
33
|
+
expiresAt: bigint | number | string;
|
|
34
|
+
nonce: bigint | number | string;
|
|
35
|
+
signature: Hex;
|
|
36
|
+
}
|
|
37
|
+
export interface RelayerProposeIntentInput {
|
|
38
|
+
intent: TradeIntent;
|
|
39
|
+
executionRoute: IntentExecutionRouteInput;
|
|
40
|
+
maxNotional?: bigint | number | string;
|
|
41
|
+
intentURI?: string;
|
|
42
|
+
}
|
|
43
|
+
export interface RelayerClientOptions {
|
|
44
|
+
baseUrl?: string;
|
|
45
|
+
botId?: string;
|
|
46
|
+
botApiKey?: string;
|
|
47
|
+
botAddress?: Address;
|
|
48
|
+
requestTimeoutMs?: number;
|
|
49
|
+
maxRetries?: number;
|
|
50
|
+
retryBaseDelayMs?: number;
|
|
51
|
+
authOnRead?: boolean;
|
|
52
|
+
defaultHeaders?: Record<string, string>;
|
|
53
|
+
}
|
|
54
|
+
export interface RelayerHttpErrorShape {
|
|
55
|
+
endpoint: string;
|
|
56
|
+
status: number | null;
|
|
57
|
+
code: string;
|
|
58
|
+
message: string;
|
|
59
|
+
retryable: boolean;
|
|
60
|
+
requestId: string;
|
|
61
|
+
details?: unknown;
|
|
62
|
+
}
|
|
63
|
+
export declare class RelayerHttpError extends Error implements RelayerHttpErrorShape {
|
|
64
|
+
endpoint: string;
|
|
65
|
+
status: number | null;
|
|
66
|
+
code: string;
|
|
67
|
+
retryable: boolean;
|
|
68
|
+
requestId: string;
|
|
69
|
+
details?: unknown;
|
|
70
|
+
constructor(shape: RelayerHttpErrorShape);
|
|
71
|
+
}
|
|
72
|
+
export interface SseEvent<TType extends string = string, TData = unknown> {
|
|
73
|
+
type: TType;
|
|
74
|
+
id: string;
|
|
75
|
+
data: TData;
|
|
76
|
+
}
|
|
77
|
+
export interface SseHandlers<TType extends string> {
|
|
78
|
+
onOpen?: () => void;
|
|
79
|
+
onEvent?: (event: SseEvent<TType>) => void;
|
|
80
|
+
onError?: (error: unknown) => void;
|
|
81
|
+
}
|
|
82
|
+
export interface SseSubscription {
|
|
83
|
+
close: () => void;
|
|
84
|
+
}
|
|
85
|
+
type ClaimEventType = 'claim:attested' | 'snapshot:finalized';
|
|
86
|
+
type IntentEventType = 'intent:attested';
|
|
87
|
+
interface SubmitClaimResponse {
|
|
88
|
+
claimHash: Hex;
|
|
89
|
+
}
|
|
90
|
+
export interface IntentOnchainBundleItem {
|
|
91
|
+
verifier: Address;
|
|
92
|
+
expiresAt: string;
|
|
93
|
+
nonce: string;
|
|
94
|
+
signature: Hex;
|
|
95
|
+
}
|
|
96
|
+
export interface IntentOnchainBundleResponse {
|
|
97
|
+
intentHash: Hex;
|
|
98
|
+
subjectState: 'PENDING' | 'READY_FOR_ONCHAIN' | 'APPROVED' | 'REJECTED';
|
|
99
|
+
thresholdWeight: string;
|
|
100
|
+
attestedWeight: string;
|
|
101
|
+
thresholdReached: boolean;
|
|
102
|
+
verifiers: Address[];
|
|
103
|
+
signatures: Hex[];
|
|
104
|
+
attestations: IntentOnchainBundleItem[];
|
|
105
|
+
}
|
|
106
|
+
export interface ReadyExecutionPayloadItem {
|
|
107
|
+
jobId: number;
|
|
108
|
+
intentHash: Hex;
|
|
109
|
+
jobStatus: string;
|
|
110
|
+
attemptCount: number;
|
|
111
|
+
nextRunAt: number;
|
|
112
|
+
maxNotional: string;
|
|
113
|
+
deadline: string;
|
|
114
|
+
intent: TradeIntent;
|
|
115
|
+
executionRoute: IntentExecutionRouteInput;
|
|
116
|
+
}
|
|
117
|
+
export interface SyncFundDeploymentInput {
|
|
118
|
+
fundId: string;
|
|
119
|
+
fundName: string;
|
|
120
|
+
strategyBotId: string;
|
|
121
|
+
strategyBotAddress: Address;
|
|
122
|
+
txHash: Hex;
|
|
123
|
+
verifierThresholdWeight?: bigint | number | string;
|
|
124
|
+
intentThresholdWeight?: bigint | number | string;
|
|
125
|
+
strategyPolicyUri?: string;
|
|
126
|
+
telegramRoomId?: string;
|
|
127
|
+
telegramHandle?: string;
|
|
128
|
+
}
|
|
129
|
+
export declare class RelayerClient {
|
|
130
|
+
private readonly baseUrl;
|
|
131
|
+
private readonly botId;
|
|
132
|
+
private readonly botApiKey;
|
|
133
|
+
private readonly botAddress;
|
|
134
|
+
private readonly requestTimeoutMs;
|
|
135
|
+
private readonly maxRetries;
|
|
136
|
+
private readonly retryBaseDelayMs;
|
|
137
|
+
private readonly authOnRead;
|
|
138
|
+
private readonly defaultHeaders;
|
|
139
|
+
constructor(options?: RelayerClientOptions);
|
|
140
|
+
submitClaim(fundId: string, claimPayload: ClaimPayload, epochId: bigint | number | string): Promise<SubmitClaimResponse & Record<string, unknown>>;
|
|
141
|
+
submitClaimTemplate(fundId: string, template: ClaimTemplateInput, epochId: bigint | number | string): Promise<SubmitClaimResponse & Record<string, unknown> & {
|
|
142
|
+
localClaimHash: Hex;
|
|
143
|
+
canonicalPayload: ClaimPayload;
|
|
144
|
+
}>;
|
|
145
|
+
getClaims(fundId: string, query?: ClaimQuery): Promise<Record<string, unknown>>;
|
|
146
|
+
submitClaimAttestation(fundId: string, attestation: ClaimAttestationInput): Promise<Record<string, unknown>>;
|
|
147
|
+
getLatestSnapshot(fundId: string): Promise<Record<string, unknown>>;
|
|
148
|
+
proposeIntent(fundId: string, input: RelayerProposeIntentInput): Promise<Record<string, unknown>>;
|
|
149
|
+
submitIntentAttestations(fundId: string, attestations: IntentAttestationInput[]): Promise<Record<string, unknown>>;
|
|
150
|
+
getIntentOnchainBundle(fundId: string, intentHash: Hex): Promise<IntentOnchainBundleResponse & Record<string, unknown>>;
|
|
151
|
+
markIntentOnchainAttested(fundId: string, intentHash: Hex, txHash: Hex): Promise<Record<string, unknown>>;
|
|
152
|
+
listReadyExecutionPayloads(fundId: string, query?: {
|
|
153
|
+
limit?: number;
|
|
154
|
+
offset?: number;
|
|
155
|
+
}): Promise<Record<string, unknown> & {
|
|
156
|
+
total: number;
|
|
157
|
+
items: ReadyExecutionPayloadItem[];
|
|
158
|
+
}>;
|
|
159
|
+
markIntentOnchainExecuted(fundId: string, intentHash: Hex, txHash: Hex): Promise<Record<string, unknown>>;
|
|
160
|
+
markIntentOnchainFailed(fundId: string, intentHash: Hex, error: string, retryDelayMs?: number): Promise<Record<string, unknown>>;
|
|
161
|
+
getFundStatus(fundId: string): Promise<Record<string, unknown>>;
|
|
162
|
+
syncFundDeployment(input: SyncFundDeploymentInput): Promise<Record<string, unknown>>;
|
|
163
|
+
subscribeClaimEvents(fundId: string, handlers: SseHandlers<ClaimEventType>): SseSubscription;
|
|
164
|
+
subscribeIntentEvents(fundId: string, handlers: SseHandlers<IntentEventType>): SseSubscription;
|
|
165
|
+
buildClaimPayloadFromTemplate(template: ClaimTemplateInput): ClaimPayload;
|
|
166
|
+
private subscribeToEvents;
|
|
167
|
+
private request;
|
|
168
|
+
private buildHeaders;
|
|
169
|
+
}
|
|
170
|
+
export declare const createRelayerClient: (options?: RelayerClientOptions) => RelayerClient;
|
|
171
|
+
export {};
|