@sudobility/contracts 1.12.0 → 1.13.0
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/evm/src/evm/{mailer-client.d.ts → evm-mailer-client.d.ts} +146 -50
- package/dist/evm/src/evm/evm-mailer-client.d.ts.map +1 -0
- package/dist/evm/src/evm/evm-mailer-client.js +924 -0
- package/dist/evm/src/evm/evm-mailer-client.js.map +1 -0
- package/dist/evm/src/evm/index.d.ts +1 -1
- package/dist/evm/src/evm/index.d.ts.map +1 -1
- package/dist/evm/src/evm/index.js +4 -4
- package/dist/evm/src/evm/index.js.map +1 -1
- package/dist/solana/solana/index.d.ts +1 -1
- package/dist/solana/solana/index.d.ts.map +1 -1
- package/dist/solana/solana/index.js +4 -3
- package/dist/solana/solana/index.js.map +1 -1
- package/dist/solana/solana/solana-mailer-client.d.ts +209 -0
- package/dist/solana/solana/solana-mailer-client.d.ts.map +1 -0
- package/dist/solana/solana/solana-mailer-client.js +1004 -0
- package/dist/solana/solana/solana-mailer-client.js.map +1 -0
- package/dist/solana/solana/types.d.ts +3 -2
- package/dist/solana/solana/types.d.ts.map +1 -1
- package/dist/solana/solana/types.js.map +1 -1
- package/dist/{unified-esm/src/evm/mailer-client.d.ts → unified/src/evm/evm-mailer-client.d.ts} +146 -50
- package/dist/unified/src/evm/evm-mailer-client.d.ts.map +1 -0
- package/dist/unified/src/evm/evm-mailer-client.js +924 -0
- package/dist/unified/src/evm/evm-mailer-client.js.map +1 -0
- package/dist/unified/src/evm/index.d.ts +1 -1
- package/dist/unified/src/evm/index.d.ts.map +1 -1
- package/dist/unified/src/evm/index.js +4 -4
- package/dist/unified/src/evm/index.js.map +1 -1
- package/dist/unified/src/react/context/MailerProvider.d.ts +26 -20
- package/dist/unified/src/react/context/MailerProvider.d.ts.map +1 -1
- package/dist/unified/src/react/context/MailerProvider.js +26 -26
- package/dist/unified/src/react/context/MailerProvider.js.map +1 -1
- package/dist/unified/src/react/hooks/useMailerMutations.d.ts +225 -192
- package/dist/unified/src/react/hooks/useMailerMutations.d.ts.map +1 -1
- package/dist/unified/src/react/hooks/useMailerMutations.js +263 -266
- package/dist/unified/src/react/hooks/useMailerMutations.js.map +1 -1
- package/dist/unified/src/react/hooks/useMailerQueries.d.ts +117 -63
- package/dist/unified/src/react/hooks/useMailerQueries.d.ts.map +1 -1
- package/dist/unified/src/react/hooks/useMailerQueries.js +239 -104
- package/dist/unified/src/react/hooks/useMailerQueries.js.map +1 -1
- package/dist/unified/src/react/index.d.ts +5 -3
- package/dist/unified/src/react/index.d.ts.map +1 -1
- package/dist/unified/src/react/index.js +41 -26
- package/dist/unified/src/react/index.js.map +1 -1
- package/dist/unified/src/solana/index.d.ts +1 -1
- package/dist/unified/src/solana/index.d.ts.map +1 -1
- package/dist/unified/src/solana/index.js +4 -3
- package/dist/unified/src/solana/index.js.map +1 -1
- package/dist/unified/src/solana/solana-mailer-client.d.ts +209 -0
- package/dist/unified/src/solana/solana-mailer-client.d.ts.map +1 -0
- package/dist/unified/src/solana/solana-mailer-client.js +1004 -0
- package/dist/unified/src/solana/solana-mailer-client.js.map +1 -0
- package/dist/unified/src/solana/types.d.ts +3 -2
- package/dist/unified/src/solana/types.d.ts.map +1 -1
- package/dist/unified/src/solana/types.js.map +1 -1
- package/dist/unified/src/unified/index.d.ts +1 -1
- package/dist/unified/src/unified/index.d.ts.map +1 -1
- package/dist/unified/src/unified/onchain-mailer-client.d.ts +187 -268
- package/dist/unified/src/unified/onchain-mailer-client.d.ts.map +1 -1
- package/dist/unified/src/unified/onchain-mailer-client.js +539 -1614
- package/dist/unified/src/unified/onchain-mailer-client.js.map +1 -1
- package/dist/unified/src/unified/types.d.ts +23 -6
- package/dist/unified/src/unified/types.d.ts.map +1 -1
- package/dist/{unified/src/evm/mailer-client.d.ts → unified-esm/src/evm/evm-mailer-client.d.ts} +146 -50
- package/dist/unified-esm/src/evm/evm-mailer-client.d.ts.map +1 -0
- package/dist/unified-esm/src/evm/evm-mailer-client.js +920 -0
- package/dist/unified-esm/src/evm/evm-mailer-client.js.map +1 -0
- package/dist/unified-esm/src/evm/index.d.ts +1 -1
- package/dist/unified-esm/src/evm/index.d.ts.map +1 -1
- package/dist/unified-esm/src/evm/index.js +2 -2
- package/dist/unified-esm/src/evm/index.js.map +1 -1
- package/dist/unified-esm/src/react/context/MailerProvider.d.ts +26 -20
- package/dist/unified-esm/src/react/context/MailerProvider.d.ts.map +1 -1
- package/dist/unified-esm/src/react/context/MailerProvider.js +25 -26
- package/dist/unified-esm/src/react/context/MailerProvider.js.map +1 -1
- package/dist/unified-esm/src/react/hooks/useMailerMutations.d.ts +225 -192
- package/dist/unified-esm/src/react/hooks/useMailerMutations.d.ts.map +1 -1
- package/dist/unified-esm/src/react/hooks/useMailerMutations.js +254 -262
- package/dist/unified-esm/src/react/hooks/useMailerMutations.js.map +1 -1
- package/dist/unified-esm/src/react/hooks/useMailerQueries.d.ts +117 -63
- package/dist/unified-esm/src/react/hooks/useMailerQueries.d.ts.map +1 -1
- package/dist/unified-esm/src/react/hooks/useMailerQueries.js +232 -102
- package/dist/unified-esm/src/react/hooks/useMailerQueries.js.map +1 -1
- package/dist/unified-esm/src/react/index.d.ts +5 -3
- package/dist/unified-esm/src/react/index.d.ts.map +1 -1
- package/dist/unified-esm/src/react/index.js +9 -5
- package/dist/unified-esm/src/react/index.js.map +1 -1
- package/dist/unified-esm/src/solana/index.d.ts +1 -1
- package/dist/unified-esm/src/solana/index.d.ts.map +1 -1
- package/dist/unified-esm/src/solana/index.js +2 -1
- package/dist/unified-esm/src/solana/index.js.map +1 -1
- package/dist/unified-esm/src/solana/solana-mailer-client.d.ts +209 -0
- package/dist/unified-esm/src/solana/solana-mailer-client.d.ts.map +1 -0
- package/dist/unified-esm/src/solana/solana-mailer-client.js +1000 -0
- package/dist/unified-esm/src/solana/solana-mailer-client.js.map +1 -0
- package/dist/unified-esm/src/solana/types.d.ts +3 -2
- package/dist/unified-esm/src/solana/types.d.ts.map +1 -1
- package/dist/unified-esm/src/solana/types.js.map +1 -1
- package/dist/unified-esm/src/unified/index.d.ts +1 -1
- package/dist/unified-esm/src/unified/index.d.ts.map +1 -1
- package/dist/unified-esm/src/unified/onchain-mailer-client.d.ts +187 -268
- package/dist/unified-esm/src/unified/onchain-mailer-client.d.ts.map +1 -1
- package/dist/unified-esm/src/unified/onchain-mailer-client.js +539 -1614
- package/dist/unified-esm/src/unified/onchain-mailer-client.js.map +1 -1
- package/dist/unified-esm/src/unified/types.d.ts +23 -6
- package/dist/unified-esm/src/unified/types.d.ts.map +1 -1
- package/package.json +5 -4
- package/programs/mailer/Cargo.toml +1 -1
- package/dist/evm/src/evm/mailer-client.d.ts.map +0 -1
- package/dist/evm/src/evm/mailer-client.js +0 -619
- package/dist/evm/src/evm/mailer-client.js.map +0 -1
- package/dist/solana/solana/mailer-client.d.ts +0 -282
- package/dist/solana/solana/mailer-client.d.ts.map +0 -1
- package/dist/solana/solana/mailer-client.js +0 -989
- package/dist/solana/solana/mailer-client.js.map +0 -1
- package/dist/unified/src/evm/mailer-client.d.ts.map +0 -1
- package/dist/unified/src/evm/mailer-client.js +0 -619
- package/dist/unified/src/evm/mailer-client.js.map +0 -1
- package/dist/unified/src/solana/mailer-client.d.ts +0 -282
- package/dist/unified/src/solana/mailer-client.d.ts.map +0 -1
- package/dist/unified/src/solana/mailer-client.js +0 -989
- package/dist/unified/src/solana/mailer-client.js.map +0 -1
- package/dist/unified-esm/src/evm/mailer-client.d.ts.map +0 -1
- package/dist/unified-esm/src/evm/mailer-client.js +0 -615
- package/dist/unified-esm/src/evm/mailer-client.js.map +0 -1
- package/dist/unified-esm/src/solana/mailer-client.d.ts +0 -282
- package/dist/unified-esm/src/solana/mailer-client.d.ts.map +0 -1
- package/dist/unified-esm/src/solana/mailer-client.js +0 -985
- package/dist/unified-esm/src/solana/mailer-client.js.map +0 -1
|
@@ -37,1807 +37,732 @@ exports.OnchainMailerClient = void 0;
|
|
|
37
37
|
/* eslint-disable @typescript-eslint/ban-ts-comment */
|
|
38
38
|
// @ts-nocheck - Suppress false TypeScript errors with ESNext modules accessing class properties
|
|
39
39
|
const types_1 = require("@sudobility/types");
|
|
40
|
-
const wallet_detector_js_1 = require("./wallet-detector");
|
|
41
40
|
/**
|
|
42
|
-
* OnchainMailerClient -
|
|
41
|
+
* OnchainMailerClient - Stateless multi-chain messaging client
|
|
43
42
|
*
|
|
44
|
-
* This
|
|
45
|
-
*
|
|
46
|
-
* wallet types and routes operations to the appropriate chain implementation.
|
|
43
|
+
* This version uses stateless EVM and Solana clients underneath.
|
|
44
|
+
* All wallet connections and chain information are passed as parameters to each method.
|
|
47
45
|
*
|
|
48
|
-
* @example
|
|
46
|
+
* @example EVM Usage
|
|
49
47
|
* ```typescript
|
|
50
|
-
*
|
|
51
|
-
*
|
|
52
|
-
*
|
|
53
|
-
* evm: {
|
|
54
|
-
* rpc: 'https://eth-mainnet.alchemyapi.io/v2/your-key',
|
|
55
|
-
* chainId: 1,
|
|
56
|
-
* contracts: {
|
|
57
|
-
* mailer: '0x456...',
|
|
58
|
-
* usdc: '0x789...'
|
|
59
|
-
* }
|
|
60
|
-
* }
|
|
61
|
-
* };
|
|
62
|
-
* const evmClient = new OnchainMailerClient(evmWallet, evmConfig);
|
|
48
|
+
* import { createWalletClient, createPublicClient, http } from 'viem';
|
|
49
|
+
* import { RpcHelpers } from '@sudobility/configs';
|
|
50
|
+
* import { Chain } from '@sudobility/types';
|
|
63
51
|
*
|
|
64
|
-
*
|
|
65
|
-
* const
|
|
66
|
-
*
|
|
67
|
-
*
|
|
68
|
-
*
|
|
69
|
-
* programs: {
|
|
70
|
-
* mailer: '9FLkBDGpZBcR8LMsQ7MwwV6X9P4TDFgN3DeRh5qYyHJF'
|
|
71
|
-
* },
|
|
72
|
-
* usdcMint: 'EPjFWdd5AufqSSqeM2qN1xzybapC8G4wEGGkZwyTDt1v'
|
|
73
|
-
* }
|
|
74
|
-
* };
|
|
75
|
-
* const solanaClient = new OnchainMailerClient(solanaWallet, solanaConfig);
|
|
52
|
+
* const chainInfo = RpcHelpers.getChainInfo(Chain.ETH_MAINNET);
|
|
53
|
+
* const walletClient = createWalletClient({
|
|
54
|
+
* chain: mainnet,
|
|
55
|
+
* transport: http()
|
|
56
|
+
* });
|
|
76
57
|
*
|
|
77
|
-
*
|
|
78
|
-
*
|
|
79
|
-
*
|
|
58
|
+
* const client = new OnchainMailerClient();
|
|
59
|
+
* await client.sendMessage(
|
|
60
|
+
* 'Subject',
|
|
61
|
+
* 'Body',
|
|
62
|
+
* { walletClient },
|
|
63
|
+
* chainInfo,
|
|
64
|
+
* { priority: true }
|
|
65
|
+
* );
|
|
80
66
|
* ```
|
|
81
67
|
*
|
|
82
|
-
* @example
|
|
68
|
+
* @example Solana Usage
|
|
83
69
|
* ```typescript
|
|
84
|
-
*
|
|
85
|
-
*
|
|
86
|
-
*
|
|
87
|
-
* }
|
|
88
|
-
*
|
|
89
|
-
*
|
|
90
|
-
*
|
|
91
|
-
* console.log('User cancelled transaction');
|
|
92
|
-
* } else {
|
|
93
|
-
* console.log('Unknown error:', error);
|
|
94
|
-
* }
|
|
95
|
-
* }
|
|
96
|
-
* ```
|
|
70
|
+
* import { useWallet } from '@solana/wallet-adapter-react';
|
|
71
|
+
* import { Connection } from '@solana/web3.js';
|
|
72
|
+
* import { RpcHelpers } from '@sudobility/configs';
|
|
73
|
+
* import { Chain } from '@sudobility/types';
|
|
74
|
+
*
|
|
75
|
+
* const chainInfo = RpcHelpers.getChainInfo(Chain.SOLANA_MAINNET);
|
|
76
|
+
* const wallet = useWallet();
|
|
97
77
|
*
|
|
98
|
-
*
|
|
99
|
-
*
|
|
100
|
-
*
|
|
78
|
+
* const client = new OnchainMailerClient();
|
|
79
|
+
* await client.sendMessage(
|
|
80
|
+
* 'Subject',
|
|
81
|
+
* 'Body',
|
|
82
|
+
* { wallet },
|
|
83
|
+
* chainInfo,
|
|
84
|
+
* { priority: true }
|
|
85
|
+
* );
|
|
86
|
+
* ```
|
|
101
87
|
*/
|
|
102
88
|
class OnchainMailerClient {
|
|
103
89
|
/**
|
|
104
|
-
*
|
|
105
|
-
*
|
|
106
|
-
* @param wallet - Wallet instance (EVM or Solana compatible)
|
|
107
|
-
* @param config - Chain configuration for EVM and/or Solana networks
|
|
108
|
-
*
|
|
109
|
-
* @throws {Error} When wallet type cannot be detected
|
|
110
|
-
* @throws {Error} When required configuration is missing
|
|
111
|
-
* @throws {Error} When wallet doesn't implement required methods
|
|
112
|
-
*
|
|
113
|
-
* @example
|
|
114
|
-
* ```typescript
|
|
115
|
-
* // EVM wallet initialization
|
|
116
|
-
* const wallet = window.ethereum;
|
|
117
|
-
* const config = {
|
|
118
|
-
* evm: { rpc: '...', chainId: 1, contracts: {...} }
|
|
119
|
-
* };
|
|
120
|
-
* const client = new OnchainMailerClient(wallet, config);
|
|
121
|
-
* ```
|
|
90
|
+
* Create a new stateless OnchainMailerClient
|
|
91
|
+
* No configuration needed in constructor
|
|
122
92
|
*/
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
try {
|
|
126
|
-
// Automatically detect whether this is an EVM or Solana wallet
|
|
127
|
-
this.chainType = wallet_detector_js_1.WalletDetector.detectWalletType(wallet);
|
|
128
|
-
// Normalize wallet interface for internal use
|
|
129
|
-
this.wallet = {
|
|
130
|
-
address: wallet.address || wallet.publicKey?.toString() || '',
|
|
131
|
-
chainType: this.chainType,
|
|
132
|
-
signTransaction: wallet.signTransaction?.bind(wallet),
|
|
133
|
-
publicKey: wallet.publicKey?.toString()
|
|
134
|
-
};
|
|
135
|
-
this.config = config;
|
|
136
|
-
// Ensure we have valid configuration for the detected chain type
|
|
137
|
-
this.validateConfiguration();
|
|
138
|
-
// Ensure wallet implements required methods for its chain type
|
|
139
|
-
this.validateWallet(wallet);
|
|
140
|
-
}
|
|
141
|
-
catch (error) {
|
|
142
|
-
throw new Error(`OnchainMailerClient initialization failed: ${error instanceof Error ? error.message : String(error)}`);
|
|
143
|
-
}
|
|
93
|
+
constructor() {
|
|
94
|
+
// Stateless - no initialization needed
|
|
144
95
|
}
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
throw new Error('Solana configuration required for Solana wallet');
|
|
151
|
-
}
|
|
152
|
-
// Validate EVM configuration
|
|
153
|
-
if (this.config.evm) {
|
|
154
|
-
if (!this.config.evm.rpc || !this.config.evm.chainId) {
|
|
155
|
-
throw new Error('EVM configuration missing required fields (rpc, chainId)');
|
|
156
|
-
}
|
|
157
|
-
if (!this.config.evm.contracts || !this.config.evm.contracts.mailer) {
|
|
158
|
-
console.warn('EVM contract addresses not configured - some functionality may fail');
|
|
159
|
-
}
|
|
160
|
-
}
|
|
161
|
-
// Validate Solana configuration
|
|
162
|
-
if (this.config.solana) {
|
|
163
|
-
if (!this.config.solana.rpc || !this.config.solana.usdcMint) {
|
|
164
|
-
throw new Error('Solana configuration missing required fields (rpc, usdcMint)');
|
|
165
|
-
}
|
|
166
|
-
if (!this.config.solana.programs || !this.config.solana.programs.mailer) {
|
|
167
|
-
console.warn('Solana program addresses not configured - some functionality may fail');
|
|
168
|
-
}
|
|
96
|
+
// Performance optimization: cache client imports
|
|
97
|
+
async getEVMClient() {
|
|
98
|
+
if (!OnchainMailerClient.evmClient) {
|
|
99
|
+
const { EVMMailerClient } = await Promise.resolve().then(() => __importStar(require('../evm/evm-mailer-client.js')));
|
|
100
|
+
OnchainMailerClient.evmClient = new EVMMailerClient();
|
|
169
101
|
}
|
|
102
|
+
return OnchainMailerClient.evmClient;
|
|
170
103
|
}
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
}
|
|
176
|
-
if (this.chainType === 'evm' && !wallet.address) {
|
|
177
|
-
throw new Error('EVM wallet must have address property');
|
|
178
|
-
}
|
|
179
|
-
if (this.chainType === 'solana' && !wallet.publicKey) {
|
|
180
|
-
throw new Error('Solana wallet must have publicKey property');
|
|
104
|
+
async getSolanaClient() {
|
|
105
|
+
if (!OnchainMailerClient.solanaClient) {
|
|
106
|
+
const { SolanaMailerClient } = await Promise.resolve().then(() => __importStar(require('../solana/solana-mailer-client.js')));
|
|
107
|
+
OnchainMailerClient.solanaClient = new SolanaMailerClient();
|
|
181
108
|
}
|
|
109
|
+
return OnchainMailerClient.solanaClient;
|
|
182
110
|
}
|
|
183
111
|
/**
|
|
184
|
-
* Send a message
|
|
185
|
-
*
|
|
186
|
-
* This method automatically routes to EVM or Solana based on the detected wallet type.
|
|
187
|
-
* Priority messages cost more but include revenue sharing for recipients.
|
|
188
|
-
*
|
|
112
|
+
* Send a message on the blockchain
|
|
189
113
|
* @param subject - Message subject (1-200 characters)
|
|
190
114
|
* @param body - Message body (1-10000 characters)
|
|
191
|
-
* @param
|
|
192
|
-
*
|
|
193
|
-
*
|
|
194
|
-
* @
|
|
195
|
-
*
|
|
196
|
-
* @returns Promise resolving to MessageResult with transaction details
|
|
197
|
-
*
|
|
198
|
-
* @throws {Error} When subject/body validation fails
|
|
199
|
-
* @throws {Error} When insufficient USDC balance
|
|
200
|
-
* @throws {Error} When user rejects transaction
|
|
201
|
-
* @throws {Error} When network connection fails
|
|
202
|
-
*
|
|
203
|
-
* @example Standard Message
|
|
204
|
-
* ```typescript
|
|
205
|
-
* const result = await client.sendMessage(
|
|
206
|
-
* "Meeting Reminder",
|
|
207
|
-
* "Don't forget our 3pm call today!",
|
|
208
|
-
* false, // Standard fee (10% of sendFee)
|
|
209
|
-
* false // Don't resolve sender to name
|
|
210
|
-
* );
|
|
211
|
-
* console.log('Sent in tx:', result.transactionHash);
|
|
212
|
-
* ```
|
|
213
|
-
*
|
|
214
|
-
* @example Priority Message with Revenue Share
|
|
215
|
-
* ```typescript
|
|
216
|
-
* const result = await client.sendMessage(
|
|
217
|
-
* "Important Update",
|
|
218
|
-
* "Urgent: Please review the attached proposal",
|
|
219
|
-
* true, // Priority fee (100% paid, 90% claimable by recipient)
|
|
220
|
-
* true // Resolve sender to name
|
|
221
|
-
* );
|
|
222
|
-
* console.log('Priority message fee:', result.fee);
|
|
223
|
-
* ```
|
|
115
|
+
* @param wallet - Wallet connection (EVM or Solana)
|
|
116
|
+
* @param chainInfo - Chain information including RPC endpoints and contract addresses
|
|
117
|
+
* @param options - Optional parameters
|
|
118
|
+
* @returns Transaction result
|
|
224
119
|
*/
|
|
225
|
-
async sendMessage(
|
|
226
|
-
//
|
|
227
|
-
if (
|
|
228
|
-
|
|
120
|
+
async sendMessage(connectedWallet, chainInfo, subject, body, options) {
|
|
121
|
+
// Validate message
|
|
122
|
+
if (!subject || subject.length > 200) {
|
|
123
|
+
throw new Error('Subject must be 1-200 characters');
|
|
124
|
+
}
|
|
125
|
+
if (!body || body.length > 10000) {
|
|
126
|
+
throw new Error('Body must be 1-10000 characters');
|
|
127
|
+
}
|
|
128
|
+
// Route to appropriate implementation based on chain type
|
|
129
|
+
if (chainInfo.chainType === types_1.ChainType.EVM) {
|
|
130
|
+
const evmClient = await this.getEVMClient();
|
|
131
|
+
const evmWallet = connectedWallet;
|
|
132
|
+
const [account] = await evmWallet.walletClient.getAddresses();
|
|
133
|
+
const to = options?.to || account;
|
|
134
|
+
const priority = options?.priority ?? false;
|
|
135
|
+
const resolveSenderToName = options?.resolveSenderToName ?? false;
|
|
136
|
+
const result = await evmClient.send(evmWallet, chainInfo, to, subject, body, account, // payer
|
|
137
|
+
priority, // revenueShareToReceiver
|
|
138
|
+
resolveSenderToName, options?.gasOptions);
|
|
139
|
+
return {
|
|
140
|
+
transactionHash: result.hash,
|
|
141
|
+
chainType: types_1.ChainType.EVM,
|
|
142
|
+
fee: BigInt(priority ? '100000' : '10000'),
|
|
143
|
+
gasUsed: result.gasUsed,
|
|
144
|
+
isPriority: priority,
|
|
145
|
+
success: true
|
|
146
|
+
};
|
|
147
|
+
}
|
|
148
|
+
else if (chainInfo.chainType === types_1.ChainType.SOLANA) {
|
|
149
|
+
const solanaClient = await this.getSolanaClient();
|
|
150
|
+
const solanaWallet = connectedWallet;
|
|
151
|
+
const to = options?.to || solanaWallet.wallet.publicKey.toBase58();
|
|
152
|
+
const priority = options?.priority ?? false;
|
|
153
|
+
const result = await solanaClient.send(solanaWallet, chainInfo, to, subject, body, priority, // revenueShareToReceiver
|
|
154
|
+
options?.computeOptions);
|
|
155
|
+
return {
|
|
156
|
+
transactionHash: result.transactionHash,
|
|
157
|
+
chainType: types_1.ChainType.SOLANA,
|
|
158
|
+
fee: BigInt(priority ? '100000' : '10000'),
|
|
159
|
+
isPriority: priority,
|
|
160
|
+
success: true
|
|
161
|
+
};
|
|
229
162
|
}
|
|
230
163
|
else {
|
|
231
|
-
|
|
164
|
+
throw new Error(`Unsupported chain type: ${chainInfo.chainType}`);
|
|
232
165
|
}
|
|
233
166
|
}
|
|
234
167
|
/**
|
|
235
|
-
*
|
|
236
|
-
* @param domain - Domain name to register
|
|
237
|
-
* @param isExtension - Whether this is extending an existing domain
|
|
238
|
-
* @returns Domain registration result
|
|
168
|
+
* Send a prepared message
|
|
239
169
|
*/
|
|
240
|
-
async
|
|
241
|
-
if (
|
|
242
|
-
|
|
170
|
+
async sendPrepared(connectedWallet, chainInfo, to, mailId, options) {
|
|
171
|
+
if (chainInfo.chainType === types_1.ChainType.EVM) {
|
|
172
|
+
const evmClient = await this.getEVMClient();
|
|
173
|
+
const evmWallet = connectedWallet;
|
|
174
|
+
const [account] = await evmWallet.walletClient.getAddresses();
|
|
175
|
+
const priority = options?.priority ?? false;
|
|
176
|
+
const resolveSenderToName = options?.resolveSenderToName ?? false;
|
|
177
|
+
const result = await evmClient.sendPrepared(evmWallet, chainInfo, to, mailId, account, // payer
|
|
178
|
+
priority, // revenueShareToReceiver
|
|
179
|
+
resolveSenderToName, options?.gasOptions);
|
|
180
|
+
return {
|
|
181
|
+
transactionHash: result.hash,
|
|
182
|
+
chainType: types_1.ChainType.EVM,
|
|
183
|
+
fee: BigInt(priority ? '100000' : '10000'),
|
|
184
|
+
gasUsed: result.gasUsed,
|
|
185
|
+
isPriority: priority,
|
|
186
|
+
success: true
|
|
187
|
+
};
|
|
188
|
+
}
|
|
189
|
+
else if (chainInfo.chainType === types_1.ChainType.SOLANA) {
|
|
190
|
+
const solanaClient = await this.getSolanaClient();
|
|
191
|
+
const solanaWallet = connectedWallet;
|
|
192
|
+
const priority = options?.priority ?? false;
|
|
193
|
+
const result = await solanaClient.sendPrepared(solanaWallet, chainInfo, to, mailId, priority, options?.computeOptions);
|
|
194
|
+
return {
|
|
195
|
+
transactionHash: result.transactionHash,
|
|
196
|
+
chainType: types_1.ChainType.SOLANA,
|
|
197
|
+
fee: BigInt(priority ? '100000' : '10000'),
|
|
198
|
+
isPriority: priority,
|
|
199
|
+
success: true
|
|
200
|
+
};
|
|
243
201
|
}
|
|
244
202
|
else {
|
|
245
|
-
|
|
203
|
+
throw new Error(`Unsupported chain type: ${chainInfo.chainType}`);
|
|
246
204
|
}
|
|
247
205
|
}
|
|
248
206
|
/**
|
|
249
|
-
*
|
|
250
|
-
* @param delegate - Address to delegate to
|
|
251
|
-
* @returns Delegation result
|
|
207
|
+
* Send through webhook
|
|
252
208
|
*/
|
|
253
|
-
async
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
209
|
+
async sendThroughWebhook(connectedWallet, chainInfo, to, webhookId, options) {
|
|
210
|
+
if (chainInfo.chainType === types_1.ChainType.EVM) {
|
|
211
|
+
const evmClient = await this.getEVMClient();
|
|
212
|
+
const evmWallet = connectedWallet;
|
|
213
|
+
const [account] = await evmWallet.walletClient.getAddresses();
|
|
214
|
+
const priority = options?.priority ?? false;
|
|
215
|
+
const result = await evmClient.sendThroughWebhook(to, subject, body, webhookId, account, // payer
|
|
216
|
+
priority, evmWallet, chainInfo, options?.gasOptions);
|
|
217
|
+
return {
|
|
218
|
+
transactionHash: result.hash,
|
|
219
|
+
chainType: types_1.ChainType.EVM,
|
|
220
|
+
fee: BigInt(priority ? '100000' : '10000'),
|
|
221
|
+
gasUsed: result.gasUsed,
|
|
222
|
+
isPriority: priority,
|
|
223
|
+
success: true
|
|
224
|
+
};
|
|
258
225
|
}
|
|
259
|
-
if (
|
|
260
|
-
|
|
226
|
+
else if (chainInfo.chainType === types_1.ChainType.SOLANA) {
|
|
227
|
+
const solanaClient = await this.getSolanaClient();
|
|
228
|
+
const solanaWallet = connectedWallet;
|
|
229
|
+
const priority = options?.priority ?? false;
|
|
230
|
+
const result = await solanaClient.sendThroughWebhook(solanaWallet, chainInfo, to, webhookId, priority, options?.computeOptions);
|
|
231
|
+
return {
|
|
232
|
+
transactionHash: result.transactionHash,
|
|
233
|
+
chainType: types_1.ChainType.SOLANA,
|
|
234
|
+
fee: BigInt(priority ? '100000' : '10000'),
|
|
235
|
+
isPriority: priority,
|
|
236
|
+
success: true
|
|
237
|
+
};
|
|
261
238
|
}
|
|
262
239
|
else {
|
|
263
|
-
|
|
240
|
+
throw new Error(`Unsupported chain type: ${chainInfo.chainType}`);
|
|
264
241
|
}
|
|
265
242
|
}
|
|
266
243
|
/**
|
|
267
|
-
*
|
|
244
|
+
* Delegate to another address
|
|
245
|
+
* @param delegate - Address to delegate to
|
|
246
|
+
* @param wallet - Wallet connection
|
|
247
|
+
* @param chainInfo - Chain information
|
|
268
248
|
* @returns Transaction result
|
|
269
249
|
*/
|
|
270
|
-
async
|
|
271
|
-
if (
|
|
272
|
-
|
|
273
|
-
|
|
274
|
-
else {
|
|
275
|
-
return this.claimSolanaRevenue();
|
|
276
|
-
}
|
|
277
|
-
}
|
|
278
|
-
// Performance optimization: cache module imports
|
|
279
|
-
async getEVMModules() {
|
|
280
|
-
if (!OnchainMailerClient.evmModules) {
|
|
281
|
-
try {
|
|
282
|
-
const [viemModule, evmModule] = await Promise.all([
|
|
283
|
-
Promise.resolve().then(() => __importStar(require('viem'))),
|
|
284
|
-
Promise.resolve().then(() => __importStar(require('../evm')))
|
|
285
|
-
]);
|
|
286
|
-
OnchainMailerClient.evmModules = {
|
|
287
|
-
viem: viemModule,
|
|
288
|
-
MailerClient: evmModule.MailerClient
|
|
289
|
-
};
|
|
290
|
-
}
|
|
291
|
-
catch (error) {
|
|
292
|
-
throw new Error(`Failed to load EVM modules: ${error instanceof Error ? error.message : String(error)}`);
|
|
293
|
-
}
|
|
294
|
-
}
|
|
295
|
-
return OnchainMailerClient.evmModules;
|
|
296
|
-
}
|
|
297
|
-
async getSolanaModules() {
|
|
298
|
-
if (!OnchainMailerClient.solanaModules) {
|
|
299
|
-
try {
|
|
300
|
-
const [solanaModule, web3Module] = await Promise.all([
|
|
301
|
-
Promise.resolve().then(() => __importStar(require('../solana'))),
|
|
302
|
-
Promise.resolve().then(() => __importStar(require('@solana/web3.js')))
|
|
303
|
-
]);
|
|
304
|
-
OnchainMailerClient.solanaModules = {
|
|
305
|
-
MailerClient: solanaModule.MailerClient,
|
|
306
|
-
PublicKey: web3Module.PublicKey,
|
|
307
|
-
Connection: web3Module.Connection
|
|
308
|
-
};
|
|
309
|
-
}
|
|
310
|
-
catch (error) {
|
|
311
|
-
throw new Error(`Failed to load Solana modules: ${error instanceof Error ? error.message : String(error)}`);
|
|
312
|
-
}
|
|
313
|
-
}
|
|
314
|
-
return OnchainMailerClient.solanaModules;
|
|
315
|
-
}
|
|
316
|
-
// Private methods for EVM implementation
|
|
317
|
-
async sendEVMMessage(subject, body, priority, resolveSenderToName = false) {
|
|
318
|
-
try {
|
|
319
|
-
const { viem, MailerClient } = await this.getEVMModules();
|
|
320
|
-
if (!this.config.evm) {
|
|
321
|
-
throw new Error('EVM configuration not provided');
|
|
322
|
-
}
|
|
323
|
-
if (!this.config.evm.contracts.mailer) {
|
|
324
|
-
throw new Error('EVM Mailer contract address not configured');
|
|
325
|
-
}
|
|
326
|
-
// Create clients
|
|
327
|
-
const publicClient = viem.createPublicClient({
|
|
328
|
-
transport: viem.http(this.config.evm.rpc),
|
|
329
|
-
chain: {
|
|
330
|
-
id: this.config.evm.chainId,
|
|
331
|
-
name: 'Custom Chain',
|
|
332
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
333
|
-
rpcUrls: {
|
|
334
|
-
default: { http: [this.config.evm.rpc] }
|
|
335
|
-
}
|
|
336
|
-
}
|
|
337
|
-
});
|
|
338
|
-
const walletClient = viem.createWalletClient({
|
|
339
|
-
transport: viem.http(this.config.evm.rpc),
|
|
340
|
-
chain: {
|
|
341
|
-
id: this.config.evm.chainId,
|
|
342
|
-
name: 'Custom Chain',
|
|
343
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
344
|
-
rpcUrls: {
|
|
345
|
-
default: { http: [this.config.evm.rpc] }
|
|
346
|
-
}
|
|
347
|
-
}
|
|
348
|
-
});
|
|
349
|
-
// Test connection
|
|
350
|
-
try {
|
|
351
|
-
await Promise.race([
|
|
352
|
-
publicClient.getChainId(),
|
|
353
|
-
new Promise((_, reject) => setTimeout(() => reject(new Error('Connection timeout')), 10000))
|
|
354
|
-
]);
|
|
355
|
-
}
|
|
356
|
-
catch (error) {
|
|
357
|
-
throw new Error(`Failed to connect to EVM network: ${error instanceof Error ? error.message : String(error)}`);
|
|
358
|
-
}
|
|
359
|
-
const client = new MailerClient(this.config.evm.contracts.mailer, publicClient);
|
|
360
|
-
// Validate message before sending
|
|
361
|
-
if (!subject || subject.length > 200) {
|
|
362
|
-
throw new Error('Subject must be 1-200 characters');
|
|
363
|
-
}
|
|
364
|
-
if (!body || body.length > 10000) {
|
|
365
|
-
throw new Error('Body must be 1-10000 characters');
|
|
366
|
-
}
|
|
367
|
-
let txHash;
|
|
368
|
-
try {
|
|
369
|
-
const payer = this.wallet.address;
|
|
370
|
-
txHash = await client.send(this.wallet.address, subject, body, payer, priority, resolveSenderToName, walletClient, this.wallet.address);
|
|
371
|
-
}
|
|
372
|
-
catch (error) {
|
|
373
|
-
const errorMessage = error instanceof Error ? error.message : String(error);
|
|
374
|
-
if (errorMessage.includes('insufficient funds')) {
|
|
375
|
-
throw new Error('Insufficient USDC balance to send message');
|
|
376
|
-
}
|
|
377
|
-
if (errorMessage.includes('user rejected')) {
|
|
378
|
-
throw new Error('Transaction rejected by user');
|
|
379
|
-
}
|
|
380
|
-
throw new Error(`Transaction failed: ${errorMessage}`);
|
|
381
|
-
}
|
|
382
|
-
// Wait for confirmation with timeout
|
|
383
|
-
const receipt = await Promise.race([
|
|
384
|
-
publicClient.waitForTransactionReceipt({ hash: txHash }),
|
|
385
|
-
new Promise((_, reject) => setTimeout(() => reject(new Error('Transaction confirmation timeout')), 60000))
|
|
386
|
-
]);
|
|
250
|
+
async delegateTo(connectedWallet, chainInfo, delegate, options) {
|
|
251
|
+
if (chainInfo.chainType === types_1.ChainType.EVM) {
|
|
252
|
+
const evmClient = await this.getEVMClient();
|
|
253
|
+
const result = await evmClient.delegateTo(delegate, connectedWallet, chainInfo, options?.gasOptions);
|
|
387
254
|
return {
|
|
388
|
-
transactionHash:
|
|
255
|
+
transactionHash: result.hash,
|
|
389
256
|
chainType: types_1.ChainType.EVM,
|
|
390
|
-
|
|
391
|
-
fee: BigInt(priority ? '100000' : '10000'), // 0.1 or 0.01 USDC in micro-USDC
|
|
392
|
-
gasUsed: receipt.gasUsed,
|
|
393
|
-
isPriority: priority,
|
|
257
|
+
delegate,
|
|
394
258
|
success: true
|
|
395
259
|
};
|
|
396
260
|
}
|
|
397
|
-
|
|
398
|
-
|
|
399
|
-
|
|
400
|
-
}
|
|
401
|
-
async registerEVMDomain(_domain, _isExtension) {
|
|
402
|
-
// Domain registration not implemented in current EVM version (delegation-only)
|
|
403
|
-
throw new Error('Domain registration not yet implemented in EVM version - use delegation instead');
|
|
404
|
-
}
|
|
405
|
-
async delegateEVM(delegate) {
|
|
406
|
-
const { viem } = await this.getEVMModules();
|
|
407
|
-
if (!this.config.evm) {
|
|
408
|
-
throw new Error('EVM configuration not provided');
|
|
409
|
-
}
|
|
410
|
-
// Validate EVM address format
|
|
411
|
-
if (!viem.isAddress(delegate)) {
|
|
412
|
-
throw new Error('Invalid EVM address format for delegate');
|
|
413
|
-
}
|
|
414
|
-
// Note: Domain functionality is now integrated into the Mailer contract
|
|
415
|
-
throw new Error('Domain delegation is now handled through the Mailer contract - use MailerClient instead');
|
|
416
|
-
}
|
|
417
|
-
async claimEVMRevenue() {
|
|
418
|
-
const { viem, MailerClient } = await this.getEVMModules();
|
|
419
|
-
if (!this.config.evm) {
|
|
420
|
-
throw new Error('EVM configuration not provided');
|
|
421
|
-
}
|
|
422
|
-
const publicClient = viem.createPublicClient({
|
|
423
|
-
transport: viem.http(this.config.evm.rpc),
|
|
424
|
-
chain: {
|
|
425
|
-
id: this.config.evm.chainId,
|
|
426
|
-
name: 'Custom Chain',
|
|
427
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
428
|
-
rpcUrls: {
|
|
429
|
-
default: { http: [this.config.evm.rpc] }
|
|
430
|
-
}
|
|
431
|
-
}
|
|
432
|
-
});
|
|
433
|
-
const walletClient = viem.createWalletClient({
|
|
434
|
-
transport: viem.http(this.config.evm.rpc),
|
|
435
|
-
chain: {
|
|
436
|
-
id: this.config.evm.chainId,
|
|
437
|
-
name: 'Custom Chain',
|
|
438
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
439
|
-
rpcUrls: {
|
|
440
|
-
default: { http: [this.config.evm.rpc] }
|
|
441
|
-
}
|
|
442
|
-
}
|
|
443
|
-
});
|
|
444
|
-
const client = new MailerClient(this.config.evm.contracts.mailer, publicClient);
|
|
445
|
-
const txHash = await client.claimRecipientShare(walletClient, this.wallet.address);
|
|
446
|
-
const receipt = await publicClient.waitForTransactionReceipt({ hash: txHash });
|
|
447
|
-
const block = await publicClient.getBlock({ blockNumber: receipt.blockNumber });
|
|
448
|
-
return {
|
|
449
|
-
hash: txHash,
|
|
450
|
-
chainType: types_1.ChainType.EVM,
|
|
451
|
-
blockNumber: receipt.blockNumber,
|
|
452
|
-
timestamp: Number(block.timestamp) * 1000
|
|
453
|
-
};
|
|
454
|
-
}
|
|
455
|
-
// Private methods for Solana implementation
|
|
456
|
-
async sendSolanaMessage(subject, body, priority, resolveSenderToName = false) {
|
|
457
|
-
try {
|
|
458
|
-
const { MailerClient, PublicKey, Connection } = await this.getSolanaModules();
|
|
459
|
-
if (!this.config.solana) {
|
|
460
|
-
throw new Error('Solana configuration not provided');
|
|
461
|
-
}
|
|
462
|
-
if (!this.config.solana.programs.mailer) {
|
|
463
|
-
throw new Error('Solana Mailer program address not configured');
|
|
464
|
-
}
|
|
465
|
-
const connection = new Connection(this.config.solana.rpc, 'confirmed');
|
|
466
|
-
// Test connection
|
|
467
|
-
try {
|
|
468
|
-
await Promise.race([
|
|
469
|
-
connection.getSlot(),
|
|
470
|
-
new Promise((_, reject) => setTimeout(() => reject(new Error('Connection timeout')), 10000))
|
|
471
|
-
]);
|
|
472
|
-
}
|
|
473
|
-
catch (error) {
|
|
474
|
-
throw new Error(`Failed to connect to Solana RPC: ${error instanceof Error ? error.message : String(error)}`);
|
|
475
|
-
}
|
|
476
|
-
// Create wallet adapter for native client
|
|
477
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
478
|
-
const wallet = MailerClient.createWallet(this.wallet);
|
|
479
|
-
const programId = new PublicKey(this.config.solana.programs.mailer);
|
|
480
|
-
const usdcMint = new PublicKey(this.config.solana.usdcMint);
|
|
481
|
-
// For now, send to the wallet itself (self-messaging)
|
|
482
|
-
const recipientKey = new PublicKey(this.wallet.address);
|
|
483
|
-
const client = new MailerClient(connection, wallet, programId, usdcMint);
|
|
484
|
-
// Get current fees
|
|
485
|
-
const fees = await client.getFees();
|
|
486
|
-
let txHash;
|
|
487
|
-
txHash = await client.send(recipientKey.toBase58(), subject, body, priority, resolveSenderToName);
|
|
488
|
-
// Get transaction details
|
|
489
|
-
const tx = await connection.getTransaction(txHash, { commitment: 'confirmed', maxSupportedTransactionVersion: 0 });
|
|
490
|
-
// Get current slot for transaction info
|
|
491
|
-
const slot = await connection.getSlot();
|
|
261
|
+
else if (chainInfo.chainType === types_1.ChainType.SOLANA) {
|
|
262
|
+
const solanaClient = await this.getSolanaClient();
|
|
263
|
+
const result = await solanaClient.delegateTo(delegate, connectedWallet, chainInfo, options?.computeOptions);
|
|
492
264
|
return {
|
|
493
|
-
transactionHash:
|
|
265
|
+
transactionHash: result.transactionHash,
|
|
494
266
|
chainType: types_1.ChainType.SOLANA,
|
|
495
|
-
|
|
496
|
-
recipient: recipientKey.toBase58(),
|
|
497
|
-
subject,
|
|
498
|
-
body,
|
|
499
|
-
slot,
|
|
500
|
-
timestamp: tx?.blockTime ? tx.blockTime * 1000 : Date.now(),
|
|
501
|
-
isPriority: priority,
|
|
267
|
+
delegate,
|
|
502
268
|
success: true
|
|
503
269
|
};
|
|
504
270
|
}
|
|
505
|
-
|
|
506
|
-
throw new Error(`
|
|
507
|
-
}
|
|
508
|
-
}
|
|
509
|
-
async registerSolanaDomain(_domain, _isExtension) {
|
|
510
|
-
// Domain registration not implemented in current Solana version
|
|
511
|
-
throw new Error('Domain registration not yet implemented in Solana version - use delegation instead');
|
|
512
|
-
}
|
|
513
|
-
async delegateSolana(_delegate) {
|
|
514
|
-
if (!this.config.solana) {
|
|
515
|
-
throw new Error('Solana configuration not provided');
|
|
271
|
+
else {
|
|
272
|
+
throw new Error(`Unsupported chain type: ${chainInfo.chainType}`);
|
|
516
273
|
}
|
|
517
|
-
// Note: Domain functionality is now integrated into the Mailer contract
|
|
518
|
-
throw new Error('Domain delegation is now handled through the Mailer contract - use MailerClient instead');
|
|
519
|
-
}
|
|
520
|
-
async claimSolanaRevenue() {
|
|
521
|
-
const { MailerClient, PublicKey, Connection } = await this.getSolanaModules();
|
|
522
|
-
if (!this.config.solana) {
|
|
523
|
-
throw new Error('Solana configuration not provided');
|
|
524
|
-
}
|
|
525
|
-
const connection = new Connection(this.config.solana.rpc, 'confirmed');
|
|
526
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
527
|
-
const wallet = MailerClient.createWallet(this.wallet);
|
|
528
|
-
const programId = new PublicKey(this.config.solana.programs.mailer);
|
|
529
|
-
const usdcMint = new PublicKey(this.config.solana.usdcMint);
|
|
530
|
-
const client = new MailerClient(connection, wallet, programId, usdcMint);
|
|
531
|
-
const txHash = await client.claimRecipientShare();
|
|
532
|
-
const slot = await connection.getSlot();
|
|
533
|
-
return {
|
|
534
|
-
hash: txHash,
|
|
535
|
-
chainType: types_1.ChainType.SOLANA,
|
|
536
|
-
slot,
|
|
537
|
-
timestamp: Date.now()
|
|
538
|
-
};
|
|
539
274
|
}
|
|
540
275
|
/**
|
|
541
|
-
*
|
|
542
|
-
* @returns Send fee in USDC micro-units (6 decimals)
|
|
276
|
+
* Reject delegation
|
|
543
277
|
*/
|
|
544
|
-
async
|
|
545
|
-
if (
|
|
546
|
-
|
|
278
|
+
async rejectDelegation(connectedWallet, chainInfo, delegatingAddress, options) {
|
|
279
|
+
if (chainInfo.chainType === types_1.ChainType.EVM) {
|
|
280
|
+
const evmClient = await this.getEVMClient();
|
|
281
|
+
const result = await evmClient.rejectDelegation(connectedWallet, chainInfo, delegatingAddress, options?.gasOptions);
|
|
282
|
+
return {
|
|
283
|
+
hash: result.hash,
|
|
284
|
+
chainType: types_1.ChainType.EVM
|
|
285
|
+
};
|
|
286
|
+
}
|
|
287
|
+
else if (chainInfo.chainType === types_1.ChainType.SOLANA) {
|
|
288
|
+
const solanaClient = await this.getSolanaClient();
|
|
289
|
+
const result = await solanaClient.rejectDelegation(connectedWallet, chainInfo, delegatingAddress, options?.computeOptions);
|
|
290
|
+
return {
|
|
291
|
+
hash: result.transactionHash,
|
|
292
|
+
chainType: types_1.ChainType.SOLANA
|
|
293
|
+
};
|
|
547
294
|
}
|
|
548
295
|
else {
|
|
549
|
-
|
|
296
|
+
throw new Error(`Unsupported chain type: ${chainInfo.chainType}`);
|
|
550
297
|
}
|
|
551
298
|
}
|
|
552
299
|
/**
|
|
553
|
-
*
|
|
554
|
-
* @param
|
|
555
|
-
* @
|
|
300
|
+
* Claim revenue share
|
|
301
|
+
* @param wallet - Wallet connection
|
|
302
|
+
* @param chainInfo - Chain information
|
|
303
|
+
* @returns Transaction result
|
|
556
304
|
*/
|
|
557
|
-
async
|
|
558
|
-
|
|
559
|
-
|
|
560
|
-
|
|
305
|
+
async claimRevenue(connectedWallet, chainInfo, options) {
|
|
306
|
+
if (chainInfo.chainType === types_1.ChainType.EVM) {
|
|
307
|
+
const evmClient = await this.getEVMClient();
|
|
308
|
+
const result = await evmClient.claimRecipientShare(connectedWallet, chainInfo, options?.gasOptions);
|
|
309
|
+
return {
|
|
310
|
+
hash: result.hash,
|
|
311
|
+
chainType: types_1.ChainType.EVM
|
|
312
|
+
};
|
|
313
|
+
}
|
|
314
|
+
else if (chainInfo.chainType === types_1.ChainType.SOLANA) {
|
|
315
|
+
const solanaClient = await this.getSolanaClient();
|
|
316
|
+
const result = await solanaClient.claimRecipientShare(connectedWallet, chainInfo, options?.computeOptions);
|
|
317
|
+
return {
|
|
318
|
+
hash: result.transactionHash,
|
|
319
|
+
chainType: types_1.ChainType.SOLANA
|
|
320
|
+
};
|
|
561
321
|
}
|
|
562
322
|
else {
|
|
563
|
-
|
|
323
|
+
throw new Error(`Unsupported chain type: ${chainInfo.chainType}`);
|
|
564
324
|
}
|
|
565
325
|
}
|
|
566
326
|
/**
|
|
567
|
-
*
|
|
568
|
-
* @returns Owner claimable amount in USDC micro-units
|
|
327
|
+
* Claim owner share (owner only)
|
|
569
328
|
*/
|
|
570
|
-
async
|
|
571
|
-
if (
|
|
572
|
-
|
|
329
|
+
async claimOwnerShare(connectedWallet, chainInfo, options) {
|
|
330
|
+
if (chainInfo.chainType === types_1.ChainType.EVM) {
|
|
331
|
+
const evmClient = await this.getEVMClient();
|
|
332
|
+
const result = await evmClient.claimOwnerShare(connectedWallet, chainInfo, options?.gasOptions);
|
|
333
|
+
return {
|
|
334
|
+
hash: result.hash,
|
|
335
|
+
chainType: types_1.ChainType.EVM
|
|
336
|
+
};
|
|
337
|
+
}
|
|
338
|
+
else if (chainInfo.chainType === types_1.ChainType.SOLANA) {
|
|
339
|
+
const solanaClient = await this.getSolanaClient();
|
|
340
|
+
const result = await solanaClient.claimOwnerShare(connectedWallet, chainInfo, options?.computeOptions);
|
|
341
|
+
return {
|
|
342
|
+
hash: result.transactionHash,
|
|
343
|
+
chainType: types_1.ChainType.SOLANA
|
|
344
|
+
};
|
|
573
345
|
}
|
|
574
346
|
else {
|
|
575
|
-
|
|
347
|
+
throw new Error(`Unsupported chain type: ${chainInfo.chainType}`);
|
|
576
348
|
}
|
|
577
349
|
}
|
|
578
350
|
/**
|
|
579
|
-
*
|
|
580
|
-
* @param address - Address to check delegation for (defaults to connected wallet)
|
|
581
|
-
* @returns Delegation address or null if no delegation
|
|
351
|
+
* Claim expired shares (owner only)
|
|
582
352
|
*/
|
|
583
|
-
async
|
|
584
|
-
|
|
585
|
-
|
|
586
|
-
|
|
353
|
+
async claimExpiredShares(connectedWallet, chainInfo, recipient, options) {
|
|
354
|
+
if (chainInfo.chainType === types_1.ChainType.EVM) {
|
|
355
|
+
const evmClient = await this.getEVMClient();
|
|
356
|
+
const result = await evmClient.claimExpiredShares(recipient, connectedWallet, chainInfo, options?.gasOptions);
|
|
357
|
+
return {
|
|
358
|
+
hash: result.hash,
|
|
359
|
+
chainType: types_1.ChainType.EVM
|
|
360
|
+
};
|
|
361
|
+
}
|
|
362
|
+
else if (chainInfo.chainType === types_1.ChainType.SOLANA) {
|
|
363
|
+
const solanaClient = await this.getSolanaClient();
|
|
364
|
+
const result = await solanaClient.claimExpiredShares(recipient, connectedWallet, chainInfo, options?.computeOptions);
|
|
365
|
+
return {
|
|
366
|
+
hash: result.transactionHash,
|
|
367
|
+
chainType: types_1.ChainType.SOLANA
|
|
368
|
+
};
|
|
587
369
|
}
|
|
588
370
|
else {
|
|
589
|
-
|
|
371
|
+
throw new Error(`Unsupported chain type: ${chainInfo.chainType}`);
|
|
590
372
|
}
|
|
591
373
|
}
|
|
592
|
-
// EVM read methods
|
|
593
|
-
async getEVMSendFee() {
|
|
594
|
-
const { viem, MailerClient } = await this.getEVMModules();
|
|
595
|
-
if (!this.config.evm?.contracts.mailer) {
|
|
596
|
-
throw new Error('EVM Mailer contract address not configured');
|
|
597
|
-
}
|
|
598
|
-
const publicClient = viem.createPublicClient({
|
|
599
|
-
transport: viem.http(this.config.evm.rpc),
|
|
600
|
-
chain: {
|
|
601
|
-
id: this.config.evm.chainId,
|
|
602
|
-
name: 'Custom Chain',
|
|
603
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
604
|
-
rpcUrls: {
|
|
605
|
-
default: { http: [this.config.evm.rpc] }
|
|
606
|
-
}
|
|
607
|
-
}
|
|
608
|
-
});
|
|
609
|
-
const client = new MailerClient(this.config.evm.contracts.mailer, publicClient);
|
|
610
|
-
return client.getSendFee();
|
|
611
|
-
}
|
|
612
|
-
async getEVMClaimableAmount(address) {
|
|
613
|
-
const { viem, MailerClient } = await this.getEVMModules();
|
|
614
|
-
if (!this.config.evm?.contracts.mailer) {
|
|
615
|
-
throw new Error('EVM Mailer contract address not configured');
|
|
616
|
-
}
|
|
617
|
-
const publicClient = viem.createPublicClient({
|
|
618
|
-
transport: viem.http(this.config.evm.rpc),
|
|
619
|
-
chain: {
|
|
620
|
-
id: this.config.evm.chainId,
|
|
621
|
-
name: 'Custom Chain',
|
|
622
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
623
|
-
rpcUrls: {
|
|
624
|
-
default: { http: [this.config.evm.rpc] }
|
|
625
|
-
}
|
|
626
|
-
}
|
|
627
|
-
});
|
|
628
|
-
const client = new MailerClient(this.config.evm.contracts.mailer, publicClient);
|
|
629
|
-
const result = await client.getRecipientClaimable(address);
|
|
630
|
-
return result.amount;
|
|
631
|
-
}
|
|
632
|
-
async getEVMOwnerClaimable() {
|
|
633
|
-
const { viem, MailerClient } = await this.getEVMModules();
|
|
634
|
-
if (!this.config.evm?.contracts.mailer) {
|
|
635
|
-
throw new Error('EVM Mailer contract address not configured');
|
|
636
|
-
}
|
|
637
|
-
const publicClient = viem.createPublicClient({
|
|
638
|
-
transport: viem.http(this.config.evm.rpc),
|
|
639
|
-
chain: {
|
|
640
|
-
id: this.config.evm.chainId,
|
|
641
|
-
name: 'Custom Chain',
|
|
642
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
643
|
-
rpcUrls: {
|
|
644
|
-
default: { http: [this.config.evm.rpc] }
|
|
645
|
-
}
|
|
646
|
-
}
|
|
647
|
-
});
|
|
648
|
-
const client = new MailerClient(this.config.evm.contracts.mailer, publicClient);
|
|
649
|
-
return client.getOwnerClaimable();
|
|
650
|
-
}
|
|
651
|
-
async getEVMDelegation(_address) {
|
|
652
|
-
// Delegation read not implemented in EVM client yet
|
|
653
|
-
// Would need to add getDelegation method to EVM MailerClient
|
|
654
|
-
throw new Error('getDelegation not yet implemented for EVM');
|
|
655
|
-
}
|
|
656
|
-
// Solana read methods
|
|
657
|
-
async getSolanaSendFee() {
|
|
658
|
-
const { MailerClient, PublicKey, Connection } = await this.getSolanaModules();
|
|
659
|
-
if (!this.config.solana?.programs.mailer) {
|
|
660
|
-
throw new Error('Solana Mailer program address not configured');
|
|
661
|
-
}
|
|
662
|
-
const connection = new Connection(this.config.solana.rpc, 'confirmed');
|
|
663
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
664
|
-
const wallet = MailerClient.createWallet(this.wallet);
|
|
665
|
-
const programId = new PublicKey(this.config.solana.programs.mailer);
|
|
666
|
-
const usdcMint = new PublicKey(this.config.solana.usdcMint);
|
|
667
|
-
const client = new MailerClient(connection, wallet, programId, usdcMint);
|
|
668
|
-
const fees = await client.getFees();
|
|
669
|
-
return BigInt(fees.sendFee);
|
|
670
|
-
}
|
|
671
|
-
async getSolanaClaimableAmount(address) {
|
|
672
|
-
const { MailerClient, PublicKey, Connection } = await this.getSolanaModules();
|
|
673
|
-
if (!this.config.solana?.programs.mailer) {
|
|
674
|
-
throw new Error('Solana Mailer program address not configured');
|
|
675
|
-
}
|
|
676
|
-
const connection = new Connection(this.config.solana.rpc, 'confirmed');
|
|
677
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
678
|
-
const wallet = MailerClient.createWallet(this.wallet);
|
|
679
|
-
const programId = new PublicKey(this.config.solana.programs.mailer);
|
|
680
|
-
const usdcMint = new PublicKey(this.config.solana.usdcMint);
|
|
681
|
-
const client = new MailerClient(connection, wallet, programId, usdcMint);
|
|
682
|
-
const recipientKey = new PublicKey(address);
|
|
683
|
-
const claimInfo = await client.getRecipientClaimable(recipientKey);
|
|
684
|
-
return claimInfo ? BigInt(claimInfo.amount) : 0n;
|
|
685
|
-
}
|
|
686
|
-
async getSolanaOwnerClaimable() {
|
|
687
|
-
const { MailerClient, PublicKey, Connection } = await this.getSolanaModules();
|
|
688
|
-
if (!this.config.solana?.programs.mailer) {
|
|
689
|
-
throw new Error('Solana Mailer program address not configured');
|
|
690
|
-
}
|
|
691
|
-
const connection = new Connection(this.config.solana.rpc, 'confirmed');
|
|
692
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
693
|
-
const wallet = MailerClient.createWallet(this.wallet);
|
|
694
|
-
const programId = new PublicKey(this.config.solana.programs.mailer);
|
|
695
|
-
const usdcMint = new PublicKey(this.config.solana.usdcMint);
|
|
696
|
-
const client = new MailerClient(connection, wallet, programId, usdcMint);
|
|
697
|
-
const amount = await client.getOwnerClaimable();
|
|
698
|
-
return BigInt(amount);
|
|
699
|
-
}
|
|
700
|
-
async getSolanaDelegation(address) {
|
|
701
|
-
const { MailerClient, PublicKey, Connection } = await this.getSolanaModules();
|
|
702
|
-
if (!this.config.solana?.programs.mailer) {
|
|
703
|
-
throw new Error('Solana Mailer program address not configured');
|
|
704
|
-
}
|
|
705
|
-
const connection = new Connection(this.config.solana.rpc, 'confirmed');
|
|
706
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
707
|
-
const wallet = MailerClient.createWallet(this.wallet);
|
|
708
|
-
const programId = new PublicKey(this.config.solana.programs.mailer);
|
|
709
|
-
const usdcMint = new PublicKey(this.config.solana.usdcMint);
|
|
710
|
-
const client = new MailerClient(connection, wallet, programId, usdcMint);
|
|
711
|
-
const delegatorKey = new PublicKey(address);
|
|
712
|
-
const delegationInfo = await client.getDelegation(delegatorKey);
|
|
713
|
-
return delegationInfo?.delegate || null;
|
|
714
|
-
}
|
|
715
374
|
/**
|
|
716
|
-
*
|
|
717
|
-
* @param to - Recipient address
|
|
718
|
-
* @param mailId - Pre-prepared message identifier
|
|
719
|
-
* @param priority - Whether to use priority sending with revenue share
|
|
720
|
-
* @param resolveSenderToName - If true, resolve sender address to name
|
|
721
|
-
* @returns Promise resolving to MessageResult
|
|
375
|
+
* Set fees (owner only)
|
|
722
376
|
*/
|
|
723
|
-
async
|
|
724
|
-
if (
|
|
725
|
-
|
|
377
|
+
async setFees(connectedWallet, chainInfo, sendFee, delegationFee, options) {
|
|
378
|
+
if (chainInfo.chainType === types_1.ChainType.EVM) {
|
|
379
|
+
const evmClient = await this.getEVMClient();
|
|
380
|
+
// EVM client uses separate methods
|
|
381
|
+
await evmClient.setFee(connectedWallet, chainInfo, sendFee, options?.gasOptions);
|
|
382
|
+
const result2 = await evmClient.setDelegationFee(connectedWallet, chainInfo, delegationFee, options?.gasOptions);
|
|
383
|
+
return {
|
|
384
|
+
hash: result2.hash, // Return last transaction
|
|
385
|
+
chainType: types_1.ChainType.EVM
|
|
386
|
+
};
|
|
387
|
+
}
|
|
388
|
+
else if (chainInfo.chainType === types_1.ChainType.SOLANA) {
|
|
389
|
+
const solanaClient = await this.getSolanaClient();
|
|
390
|
+
const result = await solanaClient.setFees(connectedWallet, chainInfo, sendFee, delegationFee, options?.computeOptions);
|
|
391
|
+
return {
|
|
392
|
+
hash: result.transactionHash,
|
|
393
|
+
chainType: types_1.ChainType.SOLANA
|
|
394
|
+
};
|
|
726
395
|
}
|
|
727
396
|
else {
|
|
728
|
-
|
|
397
|
+
throw new Error(`Unsupported chain type: ${chainInfo.chainType}`);
|
|
729
398
|
}
|
|
730
399
|
}
|
|
731
400
|
/**
|
|
732
|
-
*
|
|
733
|
-
* @param toEmail - Email address of the recipient
|
|
734
|
-
* @param subject - Message subject
|
|
735
|
-
* @param body - Message body
|
|
736
|
-
* @returns Promise resolving to MessageResult
|
|
401
|
+
* Set custom fee percentage
|
|
737
402
|
*/
|
|
738
|
-
async
|
|
739
|
-
if (
|
|
740
|
-
|
|
403
|
+
async setCustomFeePercentage(connectedWallet, chainInfo, target, percentage, options) {
|
|
404
|
+
if (chainInfo.chainType === types_1.ChainType.EVM) {
|
|
405
|
+
const evmClient = await this.getEVMClient();
|
|
406
|
+
const result = await evmClient.setCustomFeePercentage(connectedWallet, chainInfo, target, percentage, options?.gasOptions);
|
|
407
|
+
return {
|
|
408
|
+
hash: result.hash,
|
|
409
|
+
chainType: types_1.ChainType.EVM
|
|
410
|
+
};
|
|
411
|
+
}
|
|
412
|
+
else if (chainInfo.chainType === types_1.ChainType.SOLANA) {
|
|
413
|
+
const solanaClient = await this.getSolanaClient();
|
|
414
|
+
const result = await solanaClient.setCustomFeePercentage(connectedWallet, chainInfo, target, percentage, options?.computeOptions);
|
|
415
|
+
return {
|
|
416
|
+
hash: result.transactionHash,
|
|
417
|
+
chainType: types_1.ChainType.SOLANA
|
|
418
|
+
};
|
|
741
419
|
}
|
|
742
420
|
else {
|
|
743
|
-
|
|
421
|
+
throw new Error(`Unsupported chain type: ${chainInfo.chainType}`);
|
|
744
422
|
}
|
|
745
423
|
}
|
|
746
424
|
/**
|
|
747
|
-
*
|
|
748
|
-
* @param toEmail - Email address of the recipient
|
|
749
|
-
* @param mailId - Pre-prepared message identifier
|
|
750
|
-
* @returns Promise resolving to MessageResult
|
|
425
|
+
* Clear custom fee percentage
|
|
751
426
|
*/
|
|
752
|
-
async
|
|
753
|
-
if (
|
|
754
|
-
|
|
427
|
+
async clearCustomFeePercentage(connectedWallet, chainInfo, target, options) {
|
|
428
|
+
if (chainInfo.chainType === types_1.ChainType.EVM) {
|
|
429
|
+
const evmClient = await this.getEVMClient();
|
|
430
|
+
const result = await evmClient.clearCustomFeePercentage(connectedWallet, chainInfo, target, options?.gasOptions);
|
|
431
|
+
return {
|
|
432
|
+
hash: result.hash,
|
|
433
|
+
chainType: types_1.ChainType.EVM
|
|
434
|
+
};
|
|
435
|
+
}
|
|
436
|
+
else if (chainInfo.chainType === types_1.ChainType.SOLANA) {
|
|
437
|
+
const solanaClient = await this.getSolanaClient();
|
|
438
|
+
const result = await solanaClient.clearCustomFeePercentage(connectedWallet, chainInfo, target, options?.computeOptions);
|
|
439
|
+
return {
|
|
440
|
+
hash: result.transactionHash,
|
|
441
|
+
chainType: types_1.ChainType.SOLANA
|
|
442
|
+
};
|
|
755
443
|
}
|
|
756
444
|
else {
|
|
757
|
-
|
|
445
|
+
throw new Error(`Unsupported chain type: ${chainInfo.chainType}`);
|
|
758
446
|
}
|
|
759
447
|
}
|
|
760
448
|
/**
|
|
761
|
-
*
|
|
762
|
-
* @param newFee - New fee amount in USDC micro-units (6 decimals)
|
|
763
|
-
* @returns Promise resolving to transaction details
|
|
449
|
+
* Pause the contract/program (owner only)
|
|
764
450
|
*/
|
|
765
|
-
async
|
|
766
|
-
if (
|
|
767
|
-
|
|
451
|
+
async pause(connectedWallet, chainInfo, options) {
|
|
452
|
+
if (chainInfo.chainType === types_1.ChainType.EVM) {
|
|
453
|
+
const evmClient = await this.getEVMClient();
|
|
454
|
+
const result = await evmClient.pause(connectedWallet, chainInfo, options?.gasOptions);
|
|
455
|
+
return {
|
|
456
|
+
hash: result.hash,
|
|
457
|
+
chainType: types_1.ChainType.EVM
|
|
458
|
+
};
|
|
459
|
+
}
|
|
460
|
+
else if (chainInfo.chainType === types_1.ChainType.SOLANA) {
|
|
461
|
+
const solanaClient = await this.getSolanaClient();
|
|
462
|
+
const result = await solanaClient.pause(connectedWallet, chainInfo, options?.computeOptions);
|
|
463
|
+
return {
|
|
464
|
+
hash: result.transactionHash,
|
|
465
|
+
chainType: types_1.ChainType.SOLANA
|
|
466
|
+
};
|
|
768
467
|
}
|
|
769
468
|
else {
|
|
770
|
-
|
|
469
|
+
throw new Error(`Unsupported chain type: ${chainInfo.chainType}`);
|
|
771
470
|
}
|
|
772
471
|
}
|
|
773
472
|
/**
|
|
774
|
-
*
|
|
775
|
-
* @returns Current send fee in USDC micro-units (6 decimals)
|
|
473
|
+
* Unpause the contract/program (owner only)
|
|
776
474
|
*/
|
|
777
|
-
async
|
|
778
|
-
|
|
475
|
+
async unpause(connectedWallet, chainInfo, options) {
|
|
476
|
+
if (chainInfo.chainType === types_1.ChainType.EVM) {
|
|
477
|
+
const evmClient = await this.getEVMClient();
|
|
478
|
+
const result = await evmClient.unpause(connectedWallet, chainInfo, options?.gasOptions);
|
|
479
|
+
return {
|
|
480
|
+
hash: result.hash,
|
|
481
|
+
chainType: types_1.ChainType.EVM
|
|
482
|
+
};
|
|
483
|
+
}
|
|
484
|
+
else if (chainInfo.chainType === types_1.ChainType.SOLANA) {
|
|
485
|
+
const solanaClient = await this.getSolanaClient();
|
|
486
|
+
const result = await solanaClient.unpause(connectedWallet, chainInfo, options?.computeOptions);
|
|
487
|
+
return {
|
|
488
|
+
hash: result.transactionHash,
|
|
489
|
+
chainType: types_1.ChainType.SOLANA
|
|
490
|
+
};
|
|
491
|
+
}
|
|
492
|
+
else {
|
|
493
|
+
throw new Error(`Unsupported chain type: ${chainInfo.chainType}`);
|
|
494
|
+
}
|
|
779
495
|
}
|
|
780
496
|
/**
|
|
781
|
-
*
|
|
782
|
-
* @param newFee - New delegation fee in USDC micro-units
|
|
783
|
-
* @returns Promise resolving to transaction details
|
|
497
|
+
* Emergency unpause (owner only)
|
|
784
498
|
*/
|
|
785
|
-
async
|
|
786
|
-
if (
|
|
787
|
-
|
|
499
|
+
async emergencyUnpause(connectedWallet, chainInfo, options) {
|
|
500
|
+
if (chainInfo.chainType === types_1.ChainType.EVM) {
|
|
501
|
+
const evmClient = await this.getEVMClient();
|
|
502
|
+
const result = await evmClient.emergencyUnpause(connectedWallet, chainInfo, options?.gasOptions);
|
|
503
|
+
return {
|
|
504
|
+
hash: result.hash,
|
|
505
|
+
chainType: types_1.ChainType.EVM
|
|
506
|
+
};
|
|
507
|
+
}
|
|
508
|
+
else if (chainInfo.chainType === types_1.ChainType.SOLANA) {
|
|
509
|
+
const solanaClient = await this.getSolanaClient();
|
|
510
|
+
const result = await solanaClient.emergencyUnpause(connectedWallet, chainInfo, options?.computeOptions);
|
|
511
|
+
return {
|
|
512
|
+
hash: result.transactionHash,
|
|
513
|
+
chainType: types_1.ChainType.SOLANA
|
|
514
|
+
};
|
|
788
515
|
}
|
|
789
516
|
else {
|
|
790
|
-
|
|
517
|
+
throw new Error(`Unsupported chain type: ${chainInfo.chainType}`);
|
|
791
518
|
}
|
|
792
519
|
}
|
|
793
520
|
/**
|
|
794
|
-
*
|
|
795
|
-
*
|
|
521
|
+
* Distribute claimable funds when paused
|
|
522
|
+
* Note: EVM supports single recipient, Solana supports multiple
|
|
796
523
|
*/
|
|
797
|
-
async
|
|
798
|
-
if (
|
|
799
|
-
|
|
524
|
+
async distributeClaimableFunds(connectedWallet, chainInfo, recipient, options) {
|
|
525
|
+
if (chainInfo.chainType === types_1.ChainType.EVM) {
|
|
526
|
+
const evmClient = await this.getEVMClient();
|
|
527
|
+
// EVM only supports single recipient
|
|
528
|
+
const singleRecipient = Array.isArray(recipient) ? recipient[0] : recipient;
|
|
529
|
+
const result = await evmClient.distributeClaimableFunds(connectedWallet, chainInfo, singleRecipient, options?.gasOptions);
|
|
530
|
+
return {
|
|
531
|
+
hash: result.hash,
|
|
532
|
+
chainType: types_1.ChainType.EVM
|
|
533
|
+
};
|
|
534
|
+
}
|
|
535
|
+
else if (chainInfo.chainType === types_1.ChainType.SOLANA) {
|
|
536
|
+
const solanaClient = await this.getSolanaClient();
|
|
537
|
+
// Solana supports multiple recipients
|
|
538
|
+
const recipients = Array.isArray(recipient) ? recipient : [recipient];
|
|
539
|
+
const result = await solanaClient.distributeClaimableFunds(connectedWallet, chainInfo, recipients, options?.computeOptions);
|
|
540
|
+
return {
|
|
541
|
+
hash: result.transactionHash,
|
|
542
|
+
chainType: types_1.ChainType.SOLANA
|
|
543
|
+
};
|
|
800
544
|
}
|
|
801
545
|
else {
|
|
802
|
-
|
|
546
|
+
throw new Error(`Unsupported chain type: ${chainInfo.chainType}`);
|
|
803
547
|
}
|
|
804
548
|
}
|
|
805
549
|
/**
|
|
806
|
-
*
|
|
807
|
-
*
|
|
808
|
-
* @returns Promise resolving to transaction details
|
|
550
|
+
* Set permission for a contract to use caller's USDC for sending messages
|
|
551
|
+
* Note: Only supported on EVM chains
|
|
809
552
|
*/
|
|
810
|
-
async
|
|
811
|
-
if (
|
|
812
|
-
|
|
553
|
+
async setPermission(connectedWallet, chainInfo, contractAddress, options) {
|
|
554
|
+
if (chainInfo.chainType === types_1.ChainType.EVM) {
|
|
555
|
+
const evmClient = await this.getEVMClient();
|
|
556
|
+
const result = await evmClient.setPermission(connectedWallet, chainInfo, contractAddress, options?.gasOptions);
|
|
557
|
+
return {
|
|
558
|
+
hash: result.hash,
|
|
559
|
+
chainType: types_1.ChainType.EVM
|
|
560
|
+
};
|
|
561
|
+
}
|
|
562
|
+
else if (chainInfo.chainType === types_1.ChainType.SOLANA) {
|
|
563
|
+
throw new Error('Permission system is not supported on Solana');
|
|
813
564
|
}
|
|
814
565
|
else {
|
|
815
|
-
|
|
566
|
+
throw new Error(`Unsupported chain type: ${chainInfo.chainType}`);
|
|
816
567
|
}
|
|
817
568
|
}
|
|
818
569
|
/**
|
|
819
|
-
*
|
|
820
|
-
*
|
|
570
|
+
* Remove permission from a contract
|
|
571
|
+
* Note: Only supported on EVM chains
|
|
821
572
|
*/
|
|
822
|
-
async
|
|
823
|
-
if (
|
|
824
|
-
|
|
573
|
+
async removePermission(connectedWallet, chainInfo, contractAddress, options) {
|
|
574
|
+
if (chainInfo.chainType === types_1.ChainType.EVM) {
|
|
575
|
+
const evmClient = await this.getEVMClient();
|
|
576
|
+
const result = await evmClient.removePermission(connectedWallet, chainInfo, contractAddress, options?.gasOptions);
|
|
577
|
+
return {
|
|
578
|
+
hash: result.hash,
|
|
579
|
+
chainType: types_1.ChainType.EVM
|
|
580
|
+
};
|
|
581
|
+
}
|
|
582
|
+
else if (chainInfo.chainType === types_1.ChainType.SOLANA) {
|
|
583
|
+
throw new Error('Permission system is not supported on Solana');
|
|
825
584
|
}
|
|
826
585
|
else {
|
|
827
|
-
|
|
586
|
+
throw new Error(`Unsupported chain type: ${chainInfo.chainType}`);
|
|
828
587
|
}
|
|
829
588
|
}
|
|
830
589
|
/**
|
|
831
|
-
*
|
|
832
|
-
*
|
|
833
|
-
* @returns Promise resolving to transaction details
|
|
590
|
+
* Check if permission exists for a contract/wallet pair
|
|
591
|
+
* Note: Only supported on EVM chains
|
|
834
592
|
*/
|
|
835
|
-
async
|
|
836
|
-
if (
|
|
837
|
-
|
|
593
|
+
async hasPermission(chainInfo, contractAddress, walletAddress, publicClient) {
|
|
594
|
+
if (chainInfo.chainType === types_1.ChainType.EVM) {
|
|
595
|
+
const evmClient = await this.getEVMClient();
|
|
596
|
+
return await evmClient.hasPermission(chainInfo, contractAddress, walletAddress, publicClient);
|
|
597
|
+
}
|
|
598
|
+
else if (chainInfo.chainType === types_1.ChainType.SOLANA) {
|
|
599
|
+
// Solana doesn't have permission system, always return false
|
|
600
|
+
return false;
|
|
838
601
|
}
|
|
839
602
|
else {
|
|
840
|
-
|
|
603
|
+
throw new Error(`Unsupported chain type: ${chainInfo.chainType}`);
|
|
841
604
|
}
|
|
842
605
|
}
|
|
606
|
+
// ============= Read Methods =============
|
|
843
607
|
/**
|
|
844
|
-
*
|
|
845
|
-
* @
|
|
608
|
+
* Get the send fee for messages
|
|
609
|
+
* @param chainInfo - Chain information with RPC endpoint
|
|
610
|
+
* @param publicClient - Optional public client for EVM (will create if not provided)
|
|
611
|
+
* @param connection - Optional connection for Solana (will create if not provided)
|
|
612
|
+
* @returns Fee amount in USDC micro-units
|
|
846
613
|
*/
|
|
847
|
-
async
|
|
848
|
-
if (
|
|
849
|
-
|
|
614
|
+
async getSendFee(chainInfo, publicClient, connection) {
|
|
615
|
+
if (chainInfo.chainType === types_1.ChainType.EVM) {
|
|
616
|
+
const evmClient = await this.getEVMClient();
|
|
617
|
+
return await evmClient.getSendFee(chainInfo, publicClient);
|
|
618
|
+
}
|
|
619
|
+
else if (chainInfo.chainType === types_1.ChainType.SOLANA) {
|
|
620
|
+
const solanaClient = await this.getSolanaClient();
|
|
621
|
+
return await solanaClient.getSendFee(chainInfo, connection);
|
|
850
622
|
}
|
|
851
623
|
else {
|
|
852
|
-
|
|
624
|
+
throw new Error(`Unsupported chain type: ${chainInfo.chainType}`);
|
|
853
625
|
}
|
|
854
626
|
}
|
|
855
627
|
/**
|
|
856
|
-
*
|
|
857
|
-
* @returns Promise resolving to transaction details
|
|
628
|
+
* Get delegation fee
|
|
858
629
|
*/
|
|
859
|
-
async
|
|
860
|
-
if (
|
|
861
|
-
|
|
630
|
+
async getDelegationFee(chainInfo, publicClient, connection) {
|
|
631
|
+
if (chainInfo.chainType === types_1.ChainType.EVM) {
|
|
632
|
+
const evmClient = await this.getEVMClient();
|
|
633
|
+
return await evmClient.getDelegationFee(chainInfo, publicClient);
|
|
634
|
+
}
|
|
635
|
+
else if (chainInfo.chainType === types_1.ChainType.SOLANA) {
|
|
636
|
+
const solanaClient = await this.getSolanaClient();
|
|
637
|
+
return await solanaClient.getDelegationFee(chainInfo, connection);
|
|
862
638
|
}
|
|
863
639
|
else {
|
|
864
|
-
|
|
640
|
+
throw new Error(`Unsupported chain type: ${chainInfo.chainType}`);
|
|
865
641
|
}
|
|
866
642
|
}
|
|
867
643
|
/**
|
|
868
|
-
*
|
|
869
|
-
* @
|
|
644
|
+
* Get delegation for an address
|
|
645
|
+
* @param address - Address to check
|
|
646
|
+
* @param chainInfo - Chain information with RPC endpoint
|
|
647
|
+
* @param publicClient - Optional public client for EVM
|
|
648
|
+
* @param connection - Optional connection for Solana
|
|
649
|
+
* @returns Delegated address or null
|
|
870
650
|
*/
|
|
871
|
-
async
|
|
872
|
-
if (
|
|
873
|
-
|
|
651
|
+
async getDelegation(address, chainInfo, publicClient, connection) {
|
|
652
|
+
if (chainInfo.chainType === types_1.ChainType.EVM) {
|
|
653
|
+
const evmClient = await this.getEVMClient();
|
|
654
|
+
const delegation = await evmClient.getDelegation(address, chainInfo, publicClient);
|
|
655
|
+
return delegation === '0x0000000000000000000000000000000000000000' ? null : delegation;
|
|
656
|
+
}
|
|
657
|
+
else if (chainInfo.chainType === types_1.ChainType.SOLANA) {
|
|
658
|
+
const solanaClient = await this.getSolanaClient();
|
|
659
|
+
const delegation = await solanaClient.getDelegation(address, chainInfo, connection);
|
|
660
|
+
return delegation ? delegation.toBase58() : null;
|
|
874
661
|
}
|
|
875
662
|
else {
|
|
876
|
-
|
|
663
|
+
throw new Error(`Unsupported chain type: ${chainInfo.chainType}`);
|
|
877
664
|
}
|
|
878
665
|
}
|
|
879
666
|
/**
|
|
880
|
-
*
|
|
881
|
-
* @returns True if contract is paused, false otherwise
|
|
667
|
+
* Get recipient claimable info
|
|
882
668
|
*/
|
|
883
|
-
async
|
|
884
|
-
if (
|
|
885
|
-
|
|
669
|
+
async getRecipientClaimable(recipient, chainInfo, publicClient, connection) {
|
|
670
|
+
if (chainInfo.chainType === types_1.ChainType.EVM) {
|
|
671
|
+
const evmClient = await this.getEVMClient();
|
|
672
|
+
return await evmClient.getRecipientClaimable(recipient, chainInfo, publicClient);
|
|
673
|
+
}
|
|
674
|
+
else if (chainInfo.chainType === types_1.ChainType.SOLANA) {
|
|
675
|
+
const solanaClient = await this.getSolanaClient();
|
|
676
|
+
const info = await solanaClient.getRecipientClaimable(recipient, chainInfo, connection);
|
|
677
|
+
if (!info)
|
|
678
|
+
return null;
|
|
679
|
+
return {
|
|
680
|
+
amount: BigInt(info.amount),
|
|
681
|
+
expiresAt: BigInt(info.expiresAt),
|
|
682
|
+
isExpired: info.isExpired
|
|
683
|
+
};
|
|
886
684
|
}
|
|
887
685
|
else {
|
|
888
|
-
|
|
686
|
+
throw new Error(`Unsupported chain type: ${chainInfo.chainType}`);
|
|
889
687
|
}
|
|
890
688
|
}
|
|
891
689
|
/**
|
|
892
|
-
*
|
|
893
|
-
* @param recipient - Address to distribute funds for
|
|
894
|
-
* @returns Promise resolving to transaction details
|
|
690
|
+
* Get owner claimable amount
|
|
895
691
|
*/
|
|
896
|
-
async
|
|
897
|
-
if (
|
|
898
|
-
|
|
692
|
+
async getOwnerClaimable(chainInfo, publicClient, connection) {
|
|
693
|
+
if (chainInfo.chainType === types_1.ChainType.EVM) {
|
|
694
|
+
const evmClient = await this.getEVMClient();
|
|
695
|
+
return await evmClient.getOwnerClaimable(chainInfo, publicClient);
|
|
696
|
+
}
|
|
697
|
+
else if (chainInfo.chainType === types_1.ChainType.SOLANA) {
|
|
698
|
+
const solanaClient = await this.getSolanaClient();
|
|
699
|
+
const amount = await solanaClient.getOwnerClaimable(chainInfo, connection);
|
|
700
|
+
return BigInt(amount);
|
|
899
701
|
}
|
|
900
702
|
else {
|
|
901
|
-
|
|
703
|
+
throw new Error(`Unsupported chain type: ${chainInfo.chainType}`);
|
|
902
704
|
}
|
|
903
705
|
}
|
|
904
|
-
// EVM Implementation Methods
|
|
905
|
-
async sendPreparedEVM(to, mailId, priority, resolveSenderToName) {
|
|
906
|
-
const { viem, MailerClient } = await this.getEVMModules();
|
|
907
|
-
if (!this.config.evm?.contracts.mailer) {
|
|
908
|
-
throw new Error('EVM Mailer contract address not configured');
|
|
909
|
-
}
|
|
910
|
-
const publicClient = viem.createPublicClient({
|
|
911
|
-
transport: viem.http(this.config.evm.rpc),
|
|
912
|
-
chain: {
|
|
913
|
-
id: this.config.evm.chainId,
|
|
914
|
-
name: 'Custom Chain',
|
|
915
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
916
|
-
rpcUrls: {
|
|
917
|
-
default: { http: [this.config.evm.rpc] }
|
|
918
|
-
}
|
|
919
|
-
}
|
|
920
|
-
});
|
|
921
|
-
const walletClient = viem.createWalletClient({
|
|
922
|
-
transport: viem.http(this.config.evm.rpc),
|
|
923
|
-
chain: {
|
|
924
|
-
id: this.config.evm.chainId,
|
|
925
|
-
name: 'Custom Chain',
|
|
926
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
927
|
-
rpcUrls: {
|
|
928
|
-
default: { http: [this.config.evm.rpc] }
|
|
929
|
-
}
|
|
930
|
-
}
|
|
931
|
-
});
|
|
932
|
-
const client = new MailerClient(this.config.evm.contracts.mailer, publicClient);
|
|
933
|
-
const payer = this.wallet.address;
|
|
934
|
-
const txHash = await client.sendPrepared(to, mailId, payer, priority, resolveSenderToName, walletClient, this.wallet.address);
|
|
935
|
-
const receipt = await publicClient.waitForTransactionReceipt({ hash: txHash });
|
|
936
|
-
return {
|
|
937
|
-
transactionHash: txHash,
|
|
938
|
-
chainType: types_1.ChainType.EVM,
|
|
939
|
-
fee: BigInt(priority ? '100000' : '10000'),
|
|
940
|
-
gasUsed: receipt.gasUsed,
|
|
941
|
-
isPriority: priority,
|
|
942
|
-
success: true
|
|
943
|
-
};
|
|
944
|
-
}
|
|
945
|
-
async sendToEmailEVM(toEmail, subject, body) {
|
|
946
|
-
const { viem, MailerClient } = await this.getEVMModules();
|
|
947
|
-
if (!this.config.evm?.contracts.mailer) {
|
|
948
|
-
throw new Error('EVM Mailer contract address not configured');
|
|
949
|
-
}
|
|
950
|
-
const publicClient = viem.createPublicClient({
|
|
951
|
-
transport: viem.http(this.config.evm.rpc),
|
|
952
|
-
chain: {
|
|
953
|
-
id: this.config.evm.chainId,
|
|
954
|
-
name: 'Custom Chain',
|
|
955
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
956
|
-
rpcUrls: {
|
|
957
|
-
default: { http: [this.config.evm.rpc] }
|
|
958
|
-
}
|
|
959
|
-
}
|
|
960
|
-
});
|
|
961
|
-
const walletClient = viem.createWalletClient({
|
|
962
|
-
transport: viem.http(this.config.evm.rpc),
|
|
963
|
-
chain: {
|
|
964
|
-
id: this.config.evm.chainId,
|
|
965
|
-
name: 'Custom Chain',
|
|
966
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
967
|
-
rpcUrls: {
|
|
968
|
-
default: { http: [this.config.evm.rpc] }
|
|
969
|
-
}
|
|
970
|
-
}
|
|
971
|
-
});
|
|
972
|
-
const client = new MailerClient(this.config.evm.contracts.mailer, publicClient);
|
|
973
|
-
const payer = this.wallet.address;
|
|
974
|
-
const txHash = await client.sendToEmailAddress(toEmail, subject, body, payer, walletClient, this.wallet.address);
|
|
975
|
-
const receipt = await publicClient.waitForTransactionReceipt({ hash: txHash });
|
|
976
|
-
return {
|
|
977
|
-
transactionHash: txHash,
|
|
978
|
-
chainType: types_1.ChainType.EVM,
|
|
979
|
-
fee: BigInt('10000'), // 10% fee only
|
|
980
|
-
gasUsed: receipt.gasUsed,
|
|
981
|
-
isPriority: false,
|
|
982
|
-
success: true
|
|
983
|
-
};
|
|
984
|
-
}
|
|
985
|
-
async sendPreparedToEmailEVM(toEmail, mailId) {
|
|
986
|
-
const { viem, MailerClient } = await this.getEVMModules();
|
|
987
|
-
if (!this.config.evm?.contracts.mailer) {
|
|
988
|
-
throw new Error('EVM Mailer contract address not configured');
|
|
989
|
-
}
|
|
990
|
-
const publicClient = viem.createPublicClient({
|
|
991
|
-
transport: viem.http(this.config.evm.rpc),
|
|
992
|
-
chain: {
|
|
993
|
-
id: this.config.evm.chainId,
|
|
994
|
-
name: 'Custom Chain',
|
|
995
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
996
|
-
rpcUrls: {
|
|
997
|
-
default: { http: [this.config.evm.rpc] }
|
|
998
|
-
}
|
|
999
|
-
}
|
|
1000
|
-
});
|
|
1001
|
-
const walletClient = viem.createWalletClient({
|
|
1002
|
-
transport: viem.http(this.config.evm.rpc),
|
|
1003
|
-
chain: {
|
|
1004
|
-
id: this.config.evm.chainId,
|
|
1005
|
-
name: 'Custom Chain',
|
|
1006
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
1007
|
-
rpcUrls: {
|
|
1008
|
-
default: { http: [this.config.evm.rpc] }
|
|
1009
|
-
}
|
|
1010
|
-
}
|
|
1011
|
-
});
|
|
1012
|
-
const client = new MailerClient(this.config.evm.contracts.mailer, publicClient);
|
|
1013
|
-
const payer = this.wallet.address;
|
|
1014
|
-
const txHash = await client.sendPreparedToEmailAddress(toEmail, mailId, payer, walletClient, this.wallet.address);
|
|
1015
|
-
const receipt = await publicClient.waitForTransactionReceipt({ hash: txHash });
|
|
1016
|
-
return {
|
|
1017
|
-
transactionHash: txHash,
|
|
1018
|
-
chainType: types_1.ChainType.EVM,
|
|
1019
|
-
fee: BigInt('10000'), // 10% fee only
|
|
1020
|
-
gasUsed: receipt.gasUsed,
|
|
1021
|
-
isPriority: false,
|
|
1022
|
-
success: true
|
|
1023
|
-
};
|
|
1024
|
-
}
|
|
1025
|
-
async setFeeEVM(newFee) {
|
|
1026
|
-
const { viem, MailerClient } = await this.getEVMModules();
|
|
1027
|
-
if (!this.config.evm?.contracts.mailer) {
|
|
1028
|
-
throw new Error('EVM Mailer contract address not configured');
|
|
1029
|
-
}
|
|
1030
|
-
const publicClient = viem.createPublicClient({
|
|
1031
|
-
transport: viem.http(this.config.evm.rpc),
|
|
1032
|
-
chain: {
|
|
1033
|
-
id: this.config.evm.chainId,
|
|
1034
|
-
name: 'Custom Chain',
|
|
1035
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
1036
|
-
rpcUrls: {
|
|
1037
|
-
default: { http: [this.config.evm.rpc] }
|
|
1038
|
-
}
|
|
1039
|
-
}
|
|
1040
|
-
});
|
|
1041
|
-
const walletClient = viem.createWalletClient({
|
|
1042
|
-
transport: viem.http(this.config.evm.rpc),
|
|
1043
|
-
chain: {
|
|
1044
|
-
id: this.config.evm.chainId,
|
|
1045
|
-
name: 'Custom Chain',
|
|
1046
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
1047
|
-
rpcUrls: {
|
|
1048
|
-
default: { http: [this.config.evm.rpc] }
|
|
1049
|
-
}
|
|
1050
|
-
}
|
|
1051
|
-
});
|
|
1052
|
-
const client = new MailerClient(this.config.evm.contracts.mailer, publicClient);
|
|
1053
|
-
const txHash = await client.setFee(newFee, walletClient, this.wallet.address);
|
|
1054
|
-
const receipt = await publicClient.waitForTransactionReceipt({ hash: txHash });
|
|
1055
|
-
const block = await publicClient.getBlock({ blockNumber: receipt.blockNumber });
|
|
1056
|
-
return {
|
|
1057
|
-
hash: txHash,
|
|
1058
|
-
chainType: types_1.ChainType.EVM,
|
|
1059
|
-
blockNumber: receipt.blockNumber,
|
|
1060
|
-
timestamp: Number(block.timestamp) * 1000
|
|
1061
|
-
};
|
|
1062
|
-
}
|
|
1063
|
-
async setDelegationFeeEVM(newFee) {
|
|
1064
|
-
const { viem, MailerClient } = await this.getEVMModules();
|
|
1065
|
-
if (!this.config.evm?.contracts.mailer) {
|
|
1066
|
-
throw new Error('EVM Mailer contract address not configured');
|
|
1067
|
-
}
|
|
1068
|
-
const publicClient = viem.createPublicClient({
|
|
1069
|
-
transport: viem.http(this.config.evm.rpc),
|
|
1070
|
-
chain: {
|
|
1071
|
-
id: this.config.evm.chainId,
|
|
1072
|
-
name: 'Custom Chain',
|
|
1073
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
1074
|
-
rpcUrls: {
|
|
1075
|
-
default: { http: [this.config.evm.rpc] }
|
|
1076
|
-
}
|
|
1077
|
-
}
|
|
1078
|
-
});
|
|
1079
|
-
const walletClient = viem.createWalletClient({
|
|
1080
|
-
transport: viem.http(this.config.evm.rpc),
|
|
1081
|
-
chain: {
|
|
1082
|
-
id: this.config.evm.chainId,
|
|
1083
|
-
name: 'Custom Chain',
|
|
1084
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
1085
|
-
rpcUrls: {
|
|
1086
|
-
default: { http: [this.config.evm.rpc] }
|
|
1087
|
-
}
|
|
1088
|
-
}
|
|
1089
|
-
});
|
|
1090
|
-
const client = new MailerClient(this.config.evm.contracts.mailer, publicClient);
|
|
1091
|
-
const txHash = await client.setDelegationFee(newFee, walletClient, this.wallet.address);
|
|
1092
|
-
const receipt = await publicClient.waitForTransactionReceipt({ hash: txHash });
|
|
1093
|
-
const block = await publicClient.getBlock({ blockNumber: receipt.blockNumber });
|
|
1094
|
-
return {
|
|
1095
|
-
hash: txHash,
|
|
1096
|
-
chainType: types_1.ChainType.EVM,
|
|
1097
|
-
blockNumber: receipt.blockNumber,
|
|
1098
|
-
timestamp: Number(block.timestamp) * 1000
|
|
1099
|
-
};
|
|
1100
|
-
}
|
|
1101
|
-
async getDelegationFeeEVM() {
|
|
1102
|
-
const { viem, MailerClient } = await this.getEVMModules();
|
|
1103
|
-
if (!this.config.evm?.contracts.mailer) {
|
|
1104
|
-
throw new Error('EVM Mailer contract address not configured');
|
|
1105
|
-
}
|
|
1106
|
-
const publicClient = viem.createPublicClient({
|
|
1107
|
-
transport: viem.http(this.config.evm.rpc),
|
|
1108
|
-
chain: {
|
|
1109
|
-
id: this.config.evm.chainId,
|
|
1110
|
-
name: 'Custom Chain',
|
|
1111
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
1112
|
-
rpcUrls: {
|
|
1113
|
-
default: { http: [this.config.evm.rpc] }
|
|
1114
|
-
}
|
|
1115
|
-
}
|
|
1116
|
-
});
|
|
1117
|
-
const client = new MailerClient(this.config.evm.contracts.mailer, publicClient);
|
|
1118
|
-
return client.getDelegationFee();
|
|
1119
|
-
}
|
|
1120
|
-
async rejectDelegationEVM(delegatorAddress) {
|
|
1121
|
-
const { viem, MailerClient } = await this.getEVMModules();
|
|
1122
|
-
if (!this.config.evm?.contracts.mailer) {
|
|
1123
|
-
throw new Error('EVM Mailer contract address not configured');
|
|
1124
|
-
}
|
|
1125
|
-
const publicClient = viem.createPublicClient({
|
|
1126
|
-
transport: viem.http(this.config.evm.rpc),
|
|
1127
|
-
chain: {
|
|
1128
|
-
id: this.config.evm.chainId,
|
|
1129
|
-
name: 'Custom Chain',
|
|
1130
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
1131
|
-
rpcUrls: {
|
|
1132
|
-
default: { http: [this.config.evm.rpc] }
|
|
1133
|
-
}
|
|
1134
|
-
}
|
|
1135
|
-
});
|
|
1136
|
-
const walletClient = viem.createWalletClient({
|
|
1137
|
-
transport: viem.http(this.config.evm.rpc),
|
|
1138
|
-
chain: {
|
|
1139
|
-
id: this.config.evm.chainId,
|
|
1140
|
-
name: 'Custom Chain',
|
|
1141
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
1142
|
-
rpcUrls: {
|
|
1143
|
-
default: { http: [this.config.evm.rpc] }
|
|
1144
|
-
}
|
|
1145
|
-
}
|
|
1146
|
-
});
|
|
1147
|
-
const client = new MailerClient(this.config.evm.contracts.mailer, publicClient);
|
|
1148
|
-
const txHash = await client.rejectDelegation(delegatorAddress, walletClient, this.wallet.address);
|
|
1149
|
-
const receipt = await publicClient.waitForTransactionReceipt({ hash: txHash });
|
|
1150
|
-
const block = await publicClient.getBlock({ blockNumber: receipt.blockNumber });
|
|
1151
|
-
return {
|
|
1152
|
-
hash: txHash,
|
|
1153
|
-
chainType: types_1.ChainType.EVM,
|
|
1154
|
-
blockNumber: receipt.blockNumber,
|
|
1155
|
-
timestamp: Number(block.timestamp) * 1000
|
|
1156
|
-
};
|
|
1157
|
-
}
|
|
1158
|
-
async claimOwnerShareEVM() {
|
|
1159
|
-
const { viem, MailerClient } = await this.getEVMModules();
|
|
1160
|
-
if (!this.config.evm?.contracts.mailer) {
|
|
1161
|
-
throw new Error('EVM Mailer contract address not configured');
|
|
1162
|
-
}
|
|
1163
|
-
const publicClient = viem.createPublicClient({
|
|
1164
|
-
transport: viem.http(this.config.evm.rpc),
|
|
1165
|
-
chain: {
|
|
1166
|
-
id: this.config.evm.chainId,
|
|
1167
|
-
name: 'Custom Chain',
|
|
1168
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
1169
|
-
rpcUrls: {
|
|
1170
|
-
default: { http: [this.config.evm.rpc] }
|
|
1171
|
-
}
|
|
1172
|
-
}
|
|
1173
|
-
});
|
|
1174
|
-
const walletClient = viem.createWalletClient({
|
|
1175
|
-
transport: viem.http(this.config.evm.rpc),
|
|
1176
|
-
chain: {
|
|
1177
|
-
id: this.config.evm.chainId,
|
|
1178
|
-
name: 'Custom Chain',
|
|
1179
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
1180
|
-
rpcUrls: {
|
|
1181
|
-
default: { http: [this.config.evm.rpc] }
|
|
1182
|
-
}
|
|
1183
|
-
}
|
|
1184
|
-
});
|
|
1185
|
-
const client = new MailerClient(this.config.evm.contracts.mailer, publicClient);
|
|
1186
|
-
const txHash = await client.claimOwnerShare(walletClient, this.wallet.address);
|
|
1187
|
-
const receipt = await publicClient.waitForTransactionReceipt({ hash: txHash });
|
|
1188
|
-
const block = await publicClient.getBlock({ blockNumber: receipt.blockNumber });
|
|
1189
|
-
return {
|
|
1190
|
-
hash: txHash,
|
|
1191
|
-
chainType: types_1.ChainType.EVM,
|
|
1192
|
-
blockNumber: receipt.blockNumber,
|
|
1193
|
-
timestamp: Number(block.timestamp) * 1000
|
|
1194
|
-
};
|
|
1195
|
-
}
|
|
1196
|
-
async claimExpiredSharesEVM(recipient) {
|
|
1197
|
-
const { viem, MailerClient } = await this.getEVMModules();
|
|
1198
|
-
if (!this.config.evm?.contracts.mailer) {
|
|
1199
|
-
throw new Error('EVM Mailer contract address not configured');
|
|
1200
|
-
}
|
|
1201
|
-
const publicClient = viem.createPublicClient({
|
|
1202
|
-
transport: viem.http(this.config.evm.rpc),
|
|
1203
|
-
chain: {
|
|
1204
|
-
id: this.config.evm.chainId,
|
|
1205
|
-
name: 'Custom Chain',
|
|
1206
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
1207
|
-
rpcUrls: {
|
|
1208
|
-
default: { http: [this.config.evm.rpc] }
|
|
1209
|
-
}
|
|
1210
|
-
}
|
|
1211
|
-
});
|
|
1212
|
-
const walletClient = viem.createWalletClient({
|
|
1213
|
-
transport: viem.http(this.config.evm.rpc),
|
|
1214
|
-
chain: {
|
|
1215
|
-
id: this.config.evm.chainId,
|
|
1216
|
-
name: 'Custom Chain',
|
|
1217
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
1218
|
-
rpcUrls: {
|
|
1219
|
-
default: { http: [this.config.evm.rpc] }
|
|
1220
|
-
}
|
|
1221
|
-
}
|
|
1222
|
-
});
|
|
1223
|
-
const client = new MailerClient(this.config.evm.contracts.mailer, publicClient);
|
|
1224
|
-
const txHash = await client.claimExpiredShares(recipient, walletClient, this.wallet.address);
|
|
1225
|
-
const receipt = await publicClient.waitForTransactionReceipt({ hash: txHash });
|
|
1226
|
-
const block = await publicClient.getBlock({ blockNumber: receipt.blockNumber });
|
|
1227
|
-
return {
|
|
1228
|
-
hash: txHash,
|
|
1229
|
-
chainType: types_1.ChainType.EVM,
|
|
1230
|
-
blockNumber: receipt.blockNumber,
|
|
1231
|
-
timestamp: Number(block.timestamp) * 1000
|
|
1232
|
-
};
|
|
1233
|
-
}
|
|
1234
|
-
async pauseEVM() {
|
|
1235
|
-
const { viem, MailerClient } = await this.getEVMModules();
|
|
1236
|
-
if (!this.config.evm?.contracts.mailer) {
|
|
1237
|
-
throw new Error('EVM Mailer contract address not configured');
|
|
1238
|
-
}
|
|
1239
|
-
const publicClient = viem.createPublicClient({
|
|
1240
|
-
transport: viem.http(this.config.evm.rpc),
|
|
1241
|
-
chain: {
|
|
1242
|
-
id: this.config.evm.chainId,
|
|
1243
|
-
name: 'Custom Chain',
|
|
1244
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
1245
|
-
rpcUrls: {
|
|
1246
|
-
default: { http: [this.config.evm.rpc] }
|
|
1247
|
-
}
|
|
1248
|
-
}
|
|
1249
|
-
});
|
|
1250
|
-
const walletClient = viem.createWalletClient({
|
|
1251
|
-
transport: viem.http(this.config.evm.rpc),
|
|
1252
|
-
chain: {
|
|
1253
|
-
id: this.config.evm.chainId,
|
|
1254
|
-
name: 'Custom Chain',
|
|
1255
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
1256
|
-
rpcUrls: {
|
|
1257
|
-
default: { http: [this.config.evm.rpc] }
|
|
1258
|
-
}
|
|
1259
|
-
}
|
|
1260
|
-
});
|
|
1261
|
-
const client = new MailerClient(this.config.evm.contracts.mailer, publicClient);
|
|
1262
|
-
const txHash = await client.pause(walletClient, this.wallet.address);
|
|
1263
|
-
const receipt = await publicClient.waitForTransactionReceipt({ hash: txHash });
|
|
1264
|
-
const block = await publicClient.getBlock({ blockNumber: receipt.blockNumber });
|
|
1265
|
-
return {
|
|
1266
|
-
hash: txHash,
|
|
1267
|
-
chainType: types_1.ChainType.EVM,
|
|
1268
|
-
blockNumber: receipt.blockNumber,
|
|
1269
|
-
timestamp: Number(block.timestamp) * 1000
|
|
1270
|
-
};
|
|
1271
|
-
}
|
|
1272
|
-
async unpauseEVM() {
|
|
1273
|
-
const { viem, MailerClient } = await this.getEVMModules();
|
|
1274
|
-
if (!this.config.evm?.contracts.mailer) {
|
|
1275
|
-
throw new Error('EVM Mailer contract address not configured');
|
|
1276
|
-
}
|
|
1277
|
-
const publicClient = viem.createPublicClient({
|
|
1278
|
-
transport: viem.http(this.config.evm.rpc),
|
|
1279
|
-
chain: {
|
|
1280
|
-
id: this.config.evm.chainId,
|
|
1281
|
-
name: 'Custom Chain',
|
|
1282
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
1283
|
-
rpcUrls: {
|
|
1284
|
-
default: { http: [this.config.evm.rpc] }
|
|
1285
|
-
}
|
|
1286
|
-
}
|
|
1287
|
-
});
|
|
1288
|
-
const walletClient = viem.createWalletClient({
|
|
1289
|
-
transport: viem.http(this.config.evm.rpc),
|
|
1290
|
-
chain: {
|
|
1291
|
-
id: this.config.evm.chainId,
|
|
1292
|
-
name: 'Custom Chain',
|
|
1293
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
1294
|
-
rpcUrls: {
|
|
1295
|
-
default: { http: [this.config.evm.rpc] }
|
|
1296
|
-
}
|
|
1297
|
-
}
|
|
1298
|
-
});
|
|
1299
|
-
const client = new MailerClient(this.config.evm.contracts.mailer, publicClient);
|
|
1300
|
-
const txHash = await client.unpause(walletClient, this.wallet.address);
|
|
1301
|
-
const receipt = await publicClient.waitForTransactionReceipt({ hash: txHash });
|
|
1302
|
-
const block = await publicClient.getBlock({ blockNumber: receipt.blockNumber });
|
|
1303
|
-
return {
|
|
1304
|
-
hash: txHash,
|
|
1305
|
-
chainType: types_1.ChainType.EVM,
|
|
1306
|
-
blockNumber: receipt.blockNumber,
|
|
1307
|
-
timestamp: Number(block.timestamp) * 1000
|
|
1308
|
-
};
|
|
1309
|
-
}
|
|
1310
|
-
async emergencyUnpauseEVM() {
|
|
1311
|
-
const { viem, MailerClient } = await this.getEVMModules();
|
|
1312
|
-
if (!this.config.evm?.contracts.mailer) {
|
|
1313
|
-
throw new Error('EVM Mailer contract address not configured');
|
|
1314
|
-
}
|
|
1315
|
-
const publicClient = viem.createPublicClient({
|
|
1316
|
-
transport: viem.http(this.config.evm.rpc),
|
|
1317
|
-
chain: {
|
|
1318
|
-
id: this.config.evm.chainId,
|
|
1319
|
-
name: 'Custom Chain',
|
|
1320
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
1321
|
-
rpcUrls: {
|
|
1322
|
-
default: { http: [this.config.evm.rpc] }
|
|
1323
|
-
}
|
|
1324
|
-
}
|
|
1325
|
-
});
|
|
1326
|
-
const walletClient = viem.createWalletClient({
|
|
1327
|
-
transport: viem.http(this.config.evm.rpc),
|
|
1328
|
-
chain: {
|
|
1329
|
-
id: this.config.evm.chainId,
|
|
1330
|
-
name: 'Custom Chain',
|
|
1331
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
1332
|
-
rpcUrls: {
|
|
1333
|
-
default: { http: [this.config.evm.rpc] }
|
|
1334
|
-
}
|
|
1335
|
-
}
|
|
1336
|
-
});
|
|
1337
|
-
const client = new MailerClient(this.config.evm.contracts.mailer, publicClient);
|
|
1338
|
-
const txHash = await client.emergencyUnpause(walletClient, this.wallet.address);
|
|
1339
|
-
const receipt = await publicClient.waitForTransactionReceipt({ hash: txHash });
|
|
1340
|
-
const block = await publicClient.getBlock({ blockNumber: receipt.blockNumber });
|
|
1341
|
-
return {
|
|
1342
|
-
hash: txHash,
|
|
1343
|
-
chainType: types_1.ChainType.EVM,
|
|
1344
|
-
blockNumber: receipt.blockNumber,
|
|
1345
|
-
timestamp: Number(block.timestamp) * 1000
|
|
1346
|
-
};
|
|
1347
|
-
}
|
|
1348
|
-
async isPausedEVM() {
|
|
1349
|
-
const { viem, MailerClient } = await this.getEVMModules();
|
|
1350
|
-
if (!this.config.evm?.contracts.mailer) {
|
|
1351
|
-
throw new Error('EVM Mailer contract address not configured');
|
|
1352
|
-
}
|
|
1353
|
-
const publicClient = viem.createPublicClient({
|
|
1354
|
-
transport: viem.http(this.config.evm.rpc),
|
|
1355
|
-
chain: {
|
|
1356
|
-
id: this.config.evm.chainId,
|
|
1357
|
-
name: 'Custom Chain',
|
|
1358
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
1359
|
-
rpcUrls: {
|
|
1360
|
-
default: { http: [this.config.evm.rpc] }
|
|
1361
|
-
}
|
|
1362
|
-
}
|
|
1363
|
-
});
|
|
1364
|
-
const client = new MailerClient(this.config.evm.contracts.mailer, publicClient);
|
|
1365
|
-
return client.isPaused();
|
|
1366
|
-
}
|
|
1367
|
-
async distributeClaimableFundsEVM(recipient) {
|
|
1368
|
-
const { viem, MailerClient } = await this.getEVMModules();
|
|
1369
|
-
if (!this.config.evm?.contracts.mailer) {
|
|
1370
|
-
throw new Error('EVM Mailer contract address not configured');
|
|
1371
|
-
}
|
|
1372
|
-
const publicClient = viem.createPublicClient({
|
|
1373
|
-
transport: viem.http(this.config.evm.rpc),
|
|
1374
|
-
chain: {
|
|
1375
|
-
id: this.config.evm.chainId,
|
|
1376
|
-
name: 'Custom Chain',
|
|
1377
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
1378
|
-
rpcUrls: {
|
|
1379
|
-
default: { http: [this.config.evm.rpc] }
|
|
1380
|
-
}
|
|
1381
|
-
}
|
|
1382
|
-
});
|
|
1383
|
-
const walletClient = viem.createWalletClient({
|
|
1384
|
-
transport: viem.http(this.config.evm.rpc),
|
|
1385
|
-
chain: {
|
|
1386
|
-
id: this.config.evm.chainId,
|
|
1387
|
-
name: 'Custom Chain',
|
|
1388
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
1389
|
-
rpcUrls: {
|
|
1390
|
-
default: { http: [this.config.evm.rpc] }
|
|
1391
|
-
}
|
|
1392
|
-
}
|
|
1393
|
-
});
|
|
1394
|
-
const client = new MailerClient(this.config.evm.contracts.mailer, publicClient);
|
|
1395
|
-
const txHash = await client.distributeClaimableFunds(recipient, walletClient, this.wallet.address);
|
|
1396
|
-
const receipt = await publicClient.waitForTransactionReceipt({ hash: txHash });
|
|
1397
|
-
const block = await publicClient.getBlock({ blockNumber: receipt.blockNumber });
|
|
1398
|
-
return {
|
|
1399
|
-
hash: txHash,
|
|
1400
|
-
chainType: types_1.ChainType.EVM,
|
|
1401
|
-
blockNumber: receipt.blockNumber,
|
|
1402
|
-
timestamp: Number(block.timestamp) * 1000
|
|
1403
|
-
};
|
|
1404
|
-
}
|
|
1405
|
-
// Solana Implementation Methods
|
|
1406
|
-
async sendPreparedSolana(to, mailId, priority, resolveSenderToName) {
|
|
1407
|
-
const { MailerClient, PublicKey, Connection } = await this.getSolanaModules();
|
|
1408
|
-
if (!this.config.solana?.programs.mailer) {
|
|
1409
|
-
throw new Error('Solana Mailer program address not configured');
|
|
1410
|
-
}
|
|
1411
|
-
const connection = new Connection(this.config.solana.rpc, 'confirmed');
|
|
1412
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
1413
|
-
const wallet = MailerClient.createWallet(this.wallet);
|
|
1414
|
-
const programId = new PublicKey(this.config.solana.programs.mailer);
|
|
1415
|
-
const usdcMint = new PublicKey(this.config.solana.usdcMint);
|
|
1416
|
-
const recipientKey = new PublicKey(to);
|
|
1417
|
-
const client = new MailerClient(connection, wallet, programId, usdcMint);
|
|
1418
|
-
const txHash = await client.sendPrepared(recipientKey, mailId, priority, resolveSenderToName);
|
|
1419
|
-
const fees = await client.getFees();
|
|
1420
|
-
const slot = await connection.getSlot();
|
|
1421
|
-
const tx = await connection.getTransaction(txHash, { commitment: 'confirmed', maxSupportedTransactionVersion: 0 });
|
|
1422
|
-
return {
|
|
1423
|
-
transactionHash: txHash,
|
|
1424
|
-
chainType: types_1.ChainType.SOLANA,
|
|
1425
|
-
fee: priority ? fees.sendFee : fees.sendFee / 10,
|
|
1426
|
-
slot,
|
|
1427
|
-
timestamp: tx?.blockTime ? tx.blockTime * 1000 : Date.now(),
|
|
1428
|
-
isPriority: priority,
|
|
1429
|
-
success: true
|
|
1430
|
-
};
|
|
1431
|
-
}
|
|
1432
|
-
async sendToEmailSolana(toEmail, subject, body) {
|
|
1433
|
-
const { MailerClient, PublicKey, Connection } = await this.getSolanaModules();
|
|
1434
|
-
if (!this.config.solana?.programs.mailer) {
|
|
1435
|
-
throw new Error('Solana Mailer program address not configured');
|
|
1436
|
-
}
|
|
1437
|
-
const connection = new Connection(this.config.solana.rpc, 'confirmed');
|
|
1438
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
1439
|
-
const wallet = MailerClient.createWallet(this.wallet);
|
|
1440
|
-
const programId = new PublicKey(this.config.solana.programs.mailer);
|
|
1441
|
-
const usdcMint = new PublicKey(this.config.solana.usdcMint);
|
|
1442
|
-
const client = new MailerClient(connection, wallet, programId, usdcMint);
|
|
1443
|
-
const txHash = await client.sendToEmail(toEmail, subject, body);
|
|
1444
|
-
const fees = await client.getFees();
|
|
1445
|
-
const slot = await connection.getSlot();
|
|
1446
|
-
const tx = await connection.getTransaction(txHash, { commitment: 'confirmed', maxSupportedTransactionVersion: 0 });
|
|
1447
|
-
return {
|
|
1448
|
-
transactionHash: txHash,
|
|
1449
|
-
chainType: types_1.ChainType.SOLANA,
|
|
1450
|
-
fee: fees.sendFee / 10, // 10% fee only
|
|
1451
|
-
slot,
|
|
1452
|
-
timestamp: tx?.blockTime ? tx.blockTime * 1000 : Date.now(),
|
|
1453
|
-
isPriority: false,
|
|
1454
|
-
success: true
|
|
1455
|
-
};
|
|
1456
|
-
}
|
|
1457
|
-
async sendPreparedToEmailSolana(toEmail, mailId) {
|
|
1458
|
-
const { MailerClient, PublicKey, Connection } = await this.getSolanaModules();
|
|
1459
|
-
if (!this.config.solana?.programs.mailer) {
|
|
1460
|
-
throw new Error('Solana Mailer program address not configured');
|
|
1461
|
-
}
|
|
1462
|
-
const connection = new Connection(this.config.solana.rpc, 'confirmed');
|
|
1463
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
1464
|
-
const wallet = MailerClient.createWallet(this.wallet);
|
|
1465
|
-
const programId = new PublicKey(this.config.solana.programs.mailer);
|
|
1466
|
-
const usdcMint = new PublicKey(this.config.solana.usdcMint);
|
|
1467
|
-
const client = new MailerClient(connection, wallet, programId, usdcMint);
|
|
1468
|
-
const txHash = await client.sendPreparedToEmail(toEmail, mailId);
|
|
1469
|
-
const fees = await client.getFees();
|
|
1470
|
-
const slot = await connection.getSlot();
|
|
1471
|
-
const tx = await connection.getTransaction(txHash, { commitment: 'confirmed', maxSupportedTransactionVersion: 0 });
|
|
1472
|
-
return {
|
|
1473
|
-
transactionHash: txHash,
|
|
1474
|
-
chainType: types_1.ChainType.SOLANA,
|
|
1475
|
-
fee: fees.sendFee / 10, // 10% fee only
|
|
1476
|
-
slot,
|
|
1477
|
-
timestamp: tx?.blockTime ? tx.blockTime * 1000 : Date.now(),
|
|
1478
|
-
isPriority: false,
|
|
1479
|
-
success: true
|
|
1480
|
-
};
|
|
1481
|
-
}
|
|
1482
|
-
async setFeeSolana(newFee) {
|
|
1483
|
-
const { MailerClient, PublicKey, Connection } = await this.getSolanaModules();
|
|
1484
|
-
if (!this.config.solana?.programs.mailer) {
|
|
1485
|
-
throw new Error('Solana Mailer program address not configured');
|
|
1486
|
-
}
|
|
1487
|
-
const connection = new Connection(this.config.solana.rpc, 'confirmed');
|
|
1488
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
1489
|
-
const wallet = MailerClient.createWallet(this.wallet);
|
|
1490
|
-
const programId = new PublicKey(this.config.solana.programs.mailer);
|
|
1491
|
-
const usdcMint = new PublicKey(this.config.solana.usdcMint);
|
|
1492
|
-
const client = new MailerClient(connection, wallet, programId, usdcMint);
|
|
1493
|
-
const txHash = await client.setFee(newFee);
|
|
1494
|
-
const slot = await connection.getSlot();
|
|
1495
|
-
return {
|
|
1496
|
-
hash: txHash,
|
|
1497
|
-
chainType: types_1.ChainType.SOLANA,
|
|
1498
|
-
slot,
|
|
1499
|
-
timestamp: Date.now()
|
|
1500
|
-
};
|
|
1501
|
-
}
|
|
1502
|
-
async setDelegationFeeSolana(newFee) {
|
|
1503
|
-
const { MailerClient, PublicKey, Connection } = await this.getSolanaModules();
|
|
1504
|
-
if (!this.config.solana?.programs.mailer) {
|
|
1505
|
-
throw new Error('Solana Mailer program address not configured');
|
|
1506
|
-
}
|
|
1507
|
-
const connection = new Connection(this.config.solana.rpc, 'confirmed');
|
|
1508
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
1509
|
-
const wallet = MailerClient.createWallet(this.wallet);
|
|
1510
|
-
const programId = new PublicKey(this.config.solana.programs.mailer);
|
|
1511
|
-
const usdcMint = new PublicKey(this.config.solana.usdcMint);
|
|
1512
|
-
const client = new MailerClient(connection, wallet, programId, usdcMint);
|
|
1513
|
-
const txHash = await client.setDelegationFee(newFee);
|
|
1514
|
-
const slot = await connection.getSlot();
|
|
1515
|
-
return {
|
|
1516
|
-
hash: txHash,
|
|
1517
|
-
chainType: types_1.ChainType.SOLANA,
|
|
1518
|
-
slot,
|
|
1519
|
-
timestamp: Date.now()
|
|
1520
|
-
};
|
|
1521
|
-
}
|
|
1522
|
-
async getDelegationFeeSolana() {
|
|
1523
|
-
const { MailerClient, PublicKey, Connection } = await this.getSolanaModules();
|
|
1524
|
-
if (!this.config.solana?.programs.mailer) {
|
|
1525
|
-
throw new Error('Solana Mailer program address not configured');
|
|
1526
|
-
}
|
|
1527
|
-
const connection = new Connection(this.config.solana.rpc, 'confirmed');
|
|
1528
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
1529
|
-
const wallet = MailerClient.createWallet(this.wallet);
|
|
1530
|
-
const programId = new PublicKey(this.config.solana.programs.mailer);
|
|
1531
|
-
const usdcMint = new PublicKey(this.config.solana.usdcMint);
|
|
1532
|
-
const client = new MailerClient(connection, wallet, programId, usdcMint);
|
|
1533
|
-
const fees = await client.getFees();
|
|
1534
|
-
return BigInt(fees.delegationFee);
|
|
1535
|
-
}
|
|
1536
|
-
async rejectDelegationSolana(delegatorAddress) {
|
|
1537
|
-
const { MailerClient, PublicKey, Connection } = await this.getSolanaModules();
|
|
1538
|
-
if (!this.config.solana?.programs.mailer) {
|
|
1539
|
-
throw new Error('Solana Mailer program address not configured');
|
|
1540
|
-
}
|
|
1541
|
-
const connection = new Connection(this.config.solana.rpc, 'confirmed');
|
|
1542
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
1543
|
-
const wallet = MailerClient.createWallet(this.wallet);
|
|
1544
|
-
const programId = new PublicKey(this.config.solana.programs.mailer);
|
|
1545
|
-
const usdcMint = new PublicKey(this.config.solana.usdcMint);
|
|
1546
|
-
const client = new MailerClient(connection, wallet, programId, usdcMint);
|
|
1547
|
-
const txHash = await client.rejectDelegation(delegatorAddress);
|
|
1548
|
-
const slot = await connection.getSlot();
|
|
1549
|
-
return {
|
|
1550
|
-
hash: txHash,
|
|
1551
|
-
chainType: types_1.ChainType.SOLANA,
|
|
1552
|
-
slot,
|
|
1553
|
-
timestamp: Date.now()
|
|
1554
|
-
};
|
|
1555
|
-
}
|
|
1556
|
-
async claimOwnerShareSolana() {
|
|
1557
|
-
const { MailerClient, PublicKey, Connection } = await this.getSolanaModules();
|
|
1558
|
-
if (!this.config.solana?.programs.mailer) {
|
|
1559
|
-
throw new Error('Solana Mailer program address not configured');
|
|
1560
|
-
}
|
|
1561
|
-
const connection = new Connection(this.config.solana.rpc, 'confirmed');
|
|
1562
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
1563
|
-
const wallet = MailerClient.createWallet(this.wallet);
|
|
1564
|
-
const programId = new PublicKey(this.config.solana.programs.mailer);
|
|
1565
|
-
const usdcMint = new PublicKey(this.config.solana.usdcMint);
|
|
1566
|
-
const client = new MailerClient(connection, wallet, programId, usdcMint);
|
|
1567
|
-
const txHash = await client.claimOwnerShare();
|
|
1568
|
-
const slot = await connection.getSlot();
|
|
1569
|
-
return {
|
|
1570
|
-
hash: txHash,
|
|
1571
|
-
chainType: types_1.ChainType.SOLANA,
|
|
1572
|
-
slot,
|
|
1573
|
-
timestamp: Date.now()
|
|
1574
|
-
};
|
|
1575
|
-
}
|
|
1576
|
-
async claimExpiredSharesSolana(recipient) {
|
|
1577
|
-
const { MailerClient, PublicKey, Connection } = await this.getSolanaModules();
|
|
1578
|
-
if (!this.config.solana?.programs.mailer) {
|
|
1579
|
-
throw new Error('Solana Mailer program address not configured');
|
|
1580
|
-
}
|
|
1581
|
-
const connection = new Connection(this.config.solana.rpc, 'confirmed');
|
|
1582
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
1583
|
-
const wallet = MailerClient.createWallet(this.wallet);
|
|
1584
|
-
const programId = new PublicKey(this.config.solana.programs.mailer);
|
|
1585
|
-
const usdcMint = new PublicKey(this.config.solana.usdcMint);
|
|
1586
|
-
const recipientKey = new PublicKey(recipient);
|
|
1587
|
-
const client = new MailerClient(connection, wallet, programId, usdcMint);
|
|
1588
|
-
const txHash = await client.claimExpiredShares(recipientKey);
|
|
1589
|
-
const slot = await connection.getSlot();
|
|
1590
|
-
return {
|
|
1591
|
-
hash: txHash,
|
|
1592
|
-
chainType: types_1.ChainType.SOLANA,
|
|
1593
|
-
slot,
|
|
1594
|
-
timestamp: Date.now()
|
|
1595
|
-
};
|
|
1596
|
-
}
|
|
1597
|
-
async pauseSolana() {
|
|
1598
|
-
const { MailerClient, PublicKey, Connection } = await this.getSolanaModules();
|
|
1599
|
-
if (!this.config.solana?.programs.mailer) {
|
|
1600
|
-
throw new Error('Solana Mailer program address not configured');
|
|
1601
|
-
}
|
|
1602
|
-
const connection = new Connection(this.config.solana.rpc, 'confirmed');
|
|
1603
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
1604
|
-
const wallet = MailerClient.createWallet(this.wallet);
|
|
1605
|
-
const programId = new PublicKey(this.config.solana.programs.mailer);
|
|
1606
|
-
const usdcMint = new PublicKey(this.config.solana.usdcMint);
|
|
1607
|
-
const client = new MailerClient(connection, wallet, programId, usdcMint);
|
|
1608
|
-
const txHash = await client.pause();
|
|
1609
|
-
const slot = await connection.getSlot();
|
|
1610
|
-
return {
|
|
1611
|
-
hash: txHash,
|
|
1612
|
-
chainType: types_1.ChainType.SOLANA,
|
|
1613
|
-
slot,
|
|
1614
|
-
timestamp: Date.now()
|
|
1615
|
-
};
|
|
1616
|
-
}
|
|
1617
|
-
async unpauseSolana() {
|
|
1618
|
-
const { MailerClient, PublicKey, Connection } = await this.getSolanaModules();
|
|
1619
|
-
if (!this.config.solana?.programs.mailer) {
|
|
1620
|
-
throw new Error('Solana Mailer program address not configured');
|
|
1621
|
-
}
|
|
1622
|
-
const connection = new Connection(this.config.solana.rpc, 'confirmed');
|
|
1623
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
1624
|
-
const wallet = MailerClient.createWallet(this.wallet);
|
|
1625
|
-
const programId = new PublicKey(this.config.solana.programs.mailer);
|
|
1626
|
-
const usdcMint = new PublicKey(this.config.solana.usdcMint);
|
|
1627
|
-
const client = new MailerClient(connection, wallet, programId, usdcMint);
|
|
1628
|
-
const txHash = await client.unpause();
|
|
1629
|
-
const slot = await connection.getSlot();
|
|
1630
|
-
return {
|
|
1631
|
-
hash: txHash,
|
|
1632
|
-
chainType: types_1.ChainType.SOLANA,
|
|
1633
|
-
slot,
|
|
1634
|
-
timestamp: Date.now()
|
|
1635
|
-
};
|
|
1636
|
-
}
|
|
1637
|
-
async emergencyUnpauseSolana() {
|
|
1638
|
-
const { MailerClient, PublicKey, Connection } = await this.getSolanaModules();
|
|
1639
|
-
if (!this.config.solana?.programs.mailer) {
|
|
1640
|
-
throw new Error('Solana Mailer program address not configured');
|
|
1641
|
-
}
|
|
1642
|
-
const connection = new Connection(this.config.solana.rpc, 'confirmed');
|
|
1643
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
1644
|
-
const wallet = MailerClient.createWallet(this.wallet);
|
|
1645
|
-
const programId = new PublicKey(this.config.solana.programs.mailer);
|
|
1646
|
-
const usdcMint = new PublicKey(this.config.solana.usdcMint);
|
|
1647
|
-
const client = new MailerClient(connection, wallet, programId, usdcMint);
|
|
1648
|
-
const txHash = await client.emergencyUnpause();
|
|
1649
|
-
const slot = await connection.getSlot();
|
|
1650
|
-
return {
|
|
1651
|
-
hash: txHash,
|
|
1652
|
-
chainType: types_1.ChainType.SOLANA,
|
|
1653
|
-
slot,
|
|
1654
|
-
timestamp: Date.now()
|
|
1655
|
-
};
|
|
1656
|
-
}
|
|
1657
|
-
async isPausedSolana() {
|
|
1658
|
-
const { MailerClient, PublicKey, Connection } = await this.getSolanaModules();
|
|
1659
|
-
if (!this.config.solana?.programs.mailer) {
|
|
1660
|
-
throw new Error('Solana Mailer program address not configured');
|
|
1661
|
-
}
|
|
1662
|
-
const connection = new Connection(this.config.solana.rpc, 'confirmed');
|
|
1663
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
1664
|
-
const wallet = MailerClient.createWallet(this.wallet);
|
|
1665
|
-
const programId = new PublicKey(this.config.solana.programs.mailer);
|
|
1666
|
-
const usdcMint = new PublicKey(this.config.solana.usdcMint);
|
|
1667
|
-
const client = new MailerClient(connection, wallet, programId, usdcMint);
|
|
1668
|
-
return client.isPaused();
|
|
1669
|
-
}
|
|
1670
|
-
async distributeClaimableFundsSolana(recipient) {
|
|
1671
|
-
const { MailerClient, PublicKey, Connection } = await this.getSolanaModules();
|
|
1672
|
-
if (!this.config.solana?.programs.mailer) {
|
|
1673
|
-
throw new Error('Solana Mailer program address not configured');
|
|
1674
|
-
}
|
|
1675
|
-
const connection = new Connection(this.config.solana.rpc, 'confirmed');
|
|
1676
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
1677
|
-
const wallet = MailerClient.createWallet(this.wallet);
|
|
1678
|
-
const programId = new PublicKey(this.config.solana.programs.mailer);
|
|
1679
|
-
const usdcMint = new PublicKey(this.config.solana.usdcMint);
|
|
1680
|
-
const client = new MailerClient(connection, wallet, programId, usdcMint);
|
|
1681
|
-
const txHash = await client.distributeClaimableFunds(recipient);
|
|
1682
|
-
const slot = await connection.getSlot();
|
|
1683
|
-
return {
|
|
1684
|
-
hash: txHash,
|
|
1685
|
-
chainType: types_1.ChainType.SOLANA,
|
|
1686
|
-
slot,
|
|
1687
|
-
timestamp: Date.now()
|
|
1688
|
-
};
|
|
1689
|
-
}
|
|
1690
706
|
/**
|
|
1691
|
-
*
|
|
1692
|
-
* @param contractAddress - Contract address to grant permission to
|
|
1693
|
-
* @returns Promise resolving to transaction details
|
|
1694
|
-
* @throws {Error} When called on Solana (not supported)
|
|
707
|
+
* Get custom fee percentage
|
|
1695
708
|
*/
|
|
1696
|
-
async
|
|
1697
|
-
if (
|
|
1698
|
-
|
|
709
|
+
async getCustomFeePercentage(target, chainInfo, publicClient, connection) {
|
|
710
|
+
if (chainInfo.chainType === types_1.ChainType.EVM) {
|
|
711
|
+
const evmClient = await this.getEVMClient();
|
|
712
|
+
return await evmClient.getCustomFeePercentage(target, chainInfo, publicClient);
|
|
713
|
+
}
|
|
714
|
+
else if (chainInfo.chainType === types_1.ChainType.SOLANA) {
|
|
715
|
+
const solanaClient = await this.getSolanaClient();
|
|
716
|
+
return await solanaClient.getCustomFeePercentage(target, chainInfo, connection);
|
|
1699
717
|
}
|
|
1700
718
|
else {
|
|
1701
|
-
throw new Error(
|
|
719
|
+
throw new Error(`Unsupported chain type: ${chainInfo.chainType}`);
|
|
1702
720
|
}
|
|
1703
721
|
}
|
|
1704
722
|
/**
|
|
1705
|
-
*
|
|
1706
|
-
* @param contractAddress - Contract address to revoke permission from
|
|
1707
|
-
* @returns Promise resolving to transaction details
|
|
1708
|
-
* @throws {Error} When called on Solana (not supported)
|
|
723
|
+
* Check if contract/program is paused
|
|
1709
724
|
*/
|
|
1710
|
-
async
|
|
1711
|
-
if (
|
|
1712
|
-
|
|
725
|
+
async isPaused(chainInfo, publicClient, connection) {
|
|
726
|
+
if (chainInfo.chainType === types_1.ChainType.EVM) {
|
|
727
|
+
const evmClient = await this.getEVMClient();
|
|
728
|
+
return await evmClient.isPaused(chainInfo, publicClient);
|
|
729
|
+
}
|
|
730
|
+
else if (chainInfo.chainType === types_1.ChainType.SOLANA) {
|
|
731
|
+
const solanaClient = await this.getSolanaClient();
|
|
732
|
+
return await solanaClient.isPaused(chainInfo, connection);
|
|
1713
733
|
}
|
|
1714
734
|
else {
|
|
1715
|
-
throw new Error(
|
|
735
|
+
throw new Error(`Unsupported chain type: ${chainInfo.chainType}`);
|
|
1716
736
|
}
|
|
1717
737
|
}
|
|
1718
738
|
/**
|
|
1719
|
-
*
|
|
1720
|
-
* @param contractAddress - Contract address to check
|
|
1721
|
-
* @param wallet - Wallet address to check permission for (defaults to connected wallet)
|
|
1722
|
-
* @returns Promise resolving to true if permission exists, false otherwise
|
|
1723
|
-
* @throws {Error} When called on Solana (not supported)
|
|
739
|
+
* Get contract/program owner
|
|
1724
740
|
*/
|
|
1725
|
-
async
|
|
1726
|
-
if (
|
|
1727
|
-
|
|
741
|
+
async getOwner(chainInfo, publicClient, connection) {
|
|
742
|
+
if (chainInfo.chainType === types_1.ChainType.EVM) {
|
|
743
|
+
const evmClient = await this.getEVMClient();
|
|
744
|
+
return await evmClient.getOwner(chainInfo, publicClient);
|
|
745
|
+
}
|
|
746
|
+
else if (chainInfo.chainType === types_1.ChainType.SOLANA) {
|
|
747
|
+
const solanaClient = await this.getSolanaClient();
|
|
748
|
+
const owner = await solanaClient.getOwner(chainInfo, connection);
|
|
749
|
+
return owner.toBase58();
|
|
1728
750
|
}
|
|
1729
751
|
else {
|
|
1730
|
-
throw new Error(
|
|
752
|
+
throw new Error(`Unsupported chain type: ${chainInfo.chainType}`);
|
|
1731
753
|
}
|
|
1732
754
|
}
|
|
1733
|
-
|
|
1734
|
-
|
|
1735
|
-
|
|
1736
|
-
|
|
1737
|
-
|
|
1738
|
-
}
|
|
1739
|
-
const publicClient = viem.createPublicClient({
|
|
1740
|
-
transport: viem.http(this.config.evm.rpc),
|
|
1741
|
-
chain: {
|
|
1742
|
-
id: this.config.evm.chainId,
|
|
1743
|
-
name: 'Custom Chain',
|
|
1744
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
1745
|
-
rpcUrls: {
|
|
1746
|
-
default: { http: [this.config.evm.rpc] }
|
|
1747
|
-
}
|
|
1748
|
-
}
|
|
1749
|
-
});
|
|
1750
|
-
const walletClient = viem.createWalletClient({
|
|
1751
|
-
transport: viem.http(this.config.evm.rpc),
|
|
1752
|
-
chain: {
|
|
1753
|
-
id: this.config.evm.chainId,
|
|
1754
|
-
name: 'Custom Chain',
|
|
1755
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
1756
|
-
rpcUrls: {
|
|
1757
|
-
default: { http: [this.config.evm.rpc] }
|
|
1758
|
-
}
|
|
1759
|
-
}
|
|
1760
|
-
});
|
|
1761
|
-
const client = new MailerClient(this.config.evm.contracts.mailer, publicClient);
|
|
1762
|
-
const txHash = await client.setPermission(contractAddress, walletClient, this.wallet.address);
|
|
1763
|
-
const receipt = await publicClient.waitForTransactionReceipt({ hash: txHash });
|
|
1764
|
-
const block = await publicClient.getBlock({ blockNumber: receipt.blockNumber });
|
|
1765
|
-
return {
|
|
1766
|
-
hash: txHash,
|
|
1767
|
-
chainType: types_1.ChainType.EVM,
|
|
1768
|
-
blockNumber: receipt.blockNumber,
|
|
1769
|
-
timestamp: Number(block.timestamp) * 1000
|
|
1770
|
-
};
|
|
1771
|
-
}
|
|
1772
|
-
async removePermissionEVM(contractAddress) {
|
|
1773
|
-
const { viem, MailerClient } = await this.getEVMModules();
|
|
1774
|
-
if (!this.config.evm?.contracts.mailer) {
|
|
1775
|
-
throw new Error('EVM Mailer contract address not configured');
|
|
1776
|
-
}
|
|
1777
|
-
const publicClient = viem.createPublicClient({
|
|
1778
|
-
transport: viem.http(this.config.evm.rpc),
|
|
1779
|
-
chain: {
|
|
1780
|
-
id: this.config.evm.chainId,
|
|
1781
|
-
name: 'Custom Chain',
|
|
1782
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
1783
|
-
rpcUrls: {
|
|
1784
|
-
default: { http: [this.config.evm.rpc] }
|
|
1785
|
-
}
|
|
1786
|
-
}
|
|
1787
|
-
});
|
|
1788
|
-
const walletClient = viem.createWalletClient({
|
|
1789
|
-
transport: viem.http(this.config.evm.rpc),
|
|
1790
|
-
chain: {
|
|
1791
|
-
id: this.config.evm.chainId,
|
|
1792
|
-
name: 'Custom Chain',
|
|
1793
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
1794
|
-
rpcUrls: {
|
|
1795
|
-
default: { http: [this.config.evm.rpc] }
|
|
1796
|
-
}
|
|
1797
|
-
}
|
|
1798
|
-
});
|
|
1799
|
-
const client = new MailerClient(this.config.evm.contracts.mailer, publicClient);
|
|
1800
|
-
const txHash = await client.removePermission(contractAddress, walletClient, this.wallet.address);
|
|
1801
|
-
const receipt = await publicClient.waitForTransactionReceipt({ hash: txHash });
|
|
1802
|
-
const block = await publicClient.getBlock({ blockNumber: receipt.blockNumber });
|
|
1803
|
-
return {
|
|
1804
|
-
hash: txHash,
|
|
1805
|
-
chainType: types_1.ChainType.EVM,
|
|
1806
|
-
blockNumber: receipt.blockNumber,
|
|
1807
|
-
timestamp: Number(block.timestamp) * 1000
|
|
1808
|
-
};
|
|
1809
|
-
}
|
|
1810
|
-
async hasPermissionEVM(contractAddress, wallet) {
|
|
1811
|
-
const { viem, MailerClient } = await this.getEVMModules();
|
|
1812
|
-
if (!this.config.evm?.contracts.mailer) {
|
|
1813
|
-
throw new Error('EVM Mailer contract address not configured');
|
|
1814
|
-
}
|
|
1815
|
-
const publicClient = viem.createPublicClient({
|
|
1816
|
-
transport: viem.http(this.config.evm.rpc),
|
|
1817
|
-
chain: {
|
|
1818
|
-
id: this.config.evm.chainId,
|
|
1819
|
-
name: 'Custom Chain',
|
|
1820
|
-
nativeCurrency: { name: 'ETH', symbol: 'ETH', decimals: 18 },
|
|
1821
|
-
rpcUrls: {
|
|
1822
|
-
default: { http: [this.config.evm.rpc] }
|
|
1823
|
-
}
|
|
1824
|
-
}
|
|
1825
|
-
});
|
|
1826
|
-
const client = new MailerClient(this.config.evm.contracts.mailer, publicClient);
|
|
1827
|
-
return client.hasPermission(contractAddress, wallet);
|
|
1828
|
-
}
|
|
1829
|
-
// Utility methods
|
|
1830
|
-
getChainType() {
|
|
1831
|
-
return this.chainType;
|
|
1832
|
-
}
|
|
1833
|
-
getWalletAddress() {
|
|
1834
|
-
return this.wallet.address;
|
|
755
|
+
/**
|
|
756
|
+
* Register a domain (not implemented - for backward compatibility)
|
|
757
|
+
*/
|
|
758
|
+
async registerDomain(_domain) {
|
|
759
|
+
throw new Error('Domain registration not yet implemented');
|
|
1835
760
|
}
|
|
1836
761
|
}
|
|
1837
762
|
exports.OnchainMailerClient = OnchainMailerClient;
|
|
1838
|
-
//
|
|
763
|
+
// Cache for dynamic imports
|
|
1839
764
|
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
1840
|
-
OnchainMailerClient.
|
|
765
|
+
OnchainMailerClient.evmClient = null;
|
|
1841
766
|
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
1842
|
-
OnchainMailerClient.
|
|
767
|
+
OnchainMailerClient.solanaClient = null;
|
|
1843
768
|
//# sourceMappingURL=onchain-mailer-client.js.map
|