diff --git a/src/agent/index.ts b/src/agent/index.ts index 58e5188..b8aa154 100644 --- a/src/agent/index.ts +++ b/src/agent/index.ts @@ -144,6 +144,7 @@ export class SolanaAgentKit { async sendCompressedAirdrop( mintAddress: string, amount: number, + decimals: number, recipients: string[], priorityFeeInLamports: number, shouldLog: boolean @@ -152,6 +153,7 @@ export class SolanaAgentKit { this, new PublicKey(mintAddress), amount, + decimals, recipients.map((recipient) => new PublicKey(recipient)), priorityFeeInLamports, shouldLog diff --git a/src/langchain/index.ts b/src/langchain/index.ts index 72a699d..1f5f717 100644 --- a/src/langchain/index.ts +++ b/src/langchain/index.ts @@ -704,14 +704,15 @@ export class SolanaTokenDataByTickerTool extends Tool { export class SolanaCompressedAirdropTool extends Tool { name = "solana_compressed_airdrop"; - description = `Airdrop SPL tokens with ZK Compression + description = `Airdrop SPL tokens with ZK Compression (also called as airdropping tokens) - Inputs: - - mintAddress: string, the mint address of the token, e.g., "JUPyiwrYJFskUPiHa7hkeR8VUtAeFoSYbKedZNsDvCN" - - amount: number, the amount of tokens to airdrop per recipient, e.g., 42 - - recipients: string[], the recipient addresses, e.g., ["1nc1nerator11111111111111111111111111111111", "1nc1nerator11111111111111111111111111111111"] - - priorityFeeInLamports: number, the priority fee in lamports. Default is 30_000. - `; + Inputs (input is a JSON string): + mintAddress: string, the mint address of the token, e.g., "JUPyiwrYJFskUPiHa7hkeR8VUtAeFoSYbKedZNsDvCN" (required) + amount: number, the amount of tokens to airdrop per recipient, e.g., 42 (required) + decimals: number, the decimals of the token, e.g., 6 (required) + recipients: string[], the recipient addresses, e.g., ["1nc1nerator11111111111111111111111111111111"] (required) + priorityFeeInLamports: number, the priority fee in lamports. Default is 30_000. (optional) + shouldLog: boolean, whether to log progress to stdout. Default is false. (optional)`; constructor(private solanaKit: SolanaAgentKit) { super(); @@ -724,9 +725,10 @@ export class SolanaCompressedAirdropTool extends Tool { const txs = await this.solanaKit.sendCompressedAirdrop( parsedInput.mintAddress, parsedInput.amount, + parsedInput.decimals, parsedInput.recipients, parsedInput.priorityFeeInLamports || 30_000, - false // no logging + parsedInput.shouldLog || false ); return JSON.stringify({ diff --git a/src/tools/send_compressed_airdrop.ts b/src/tools/send_compressed_airdrop.ts index 720dc31..313bbdb 100644 --- a/src/tools/send_compressed_airdrop.ts +++ b/src/tools/send_compressed_airdrop.ts @@ -51,15 +51,18 @@ export const getAirdropCostEstimate = ( * @param agent Agent * @param mintAddress SPL Mint address * @param amount Amount to send per recipient + * @param decimals Decimals of the token * @param recipients Recipient wallet addresses (no ATAs) + * @param priorityFeeInLamports Priority fee in lamports * @param shouldLog Whether to log progress to stdout. Defaults to false. */ export async function sendCompressedAirdrop( agent: SolanaAgentKit, mintAddress: PublicKey, amount: number, + decimals: number, recipients: PublicKey[], - prioFeeInLamports: number, + priorityFeeInLamports: number, shouldLog: boolean = false ): Promise { if (recipients.length > MAX_AIRDROP_RECIPIENTS) { @@ -67,6 +70,18 @@ export async function sendCompressedAirdrop( `Max airdrop can be ${MAX_AIRDROP_RECIPIENTS} recipients at a time. For more scale, use open source ZK Compression airdrop tools such as https://github.com/helius-labs/airship.` ); } + + + const url = agent.connection.rpcEndpoint; + if (url.includes("devnet")) { + throw new Error("Devnet is not supported for airdrop. Please use mainnet."); + } + if (!url.includes("helius")) { + console.warn( + "Warning: Must use RPC with ZK Compression support. Double check with your RPC provider if in doubt." + ); + } + let sourceTokenAccount: Account; try { sourceTokenAccount = await getOrCreateAssociatedTokenAccount( @@ -97,10 +112,10 @@ export async function sendCompressedAirdrop( return await processAll( agent, - amount, + amount * 10 ** decimals, mintAddress, recipients, - prioFeeInLamports, + priorityFeeInLamports, shouldLog ); } @@ -110,7 +125,7 @@ async function processAll( amount: number, mint: PublicKey, recipients: PublicKey[], - prioFeeInLamports: number, + priorityFeeInLamports: number, shouldLog: boolean ): Promise { const mintAddress = mint; @@ -147,7 +162,10 @@ async function processAll( const instructions: TransactionInstruction[] = [ ComputeBudgetProgram.setComputeUnitLimit({ units: 500_000 }), ComputeBudgetProgram.setComputeUnitPrice({ - microLamports: calculateComputeUnitPrice(prioFeeInLamports, 500_000), + microLamports: calculateComputeUnitPrice( + priorityFeeInLamports, + 500_000 + ), }), ]; @@ -176,14 +194,6 @@ async function processAll( ); const url = agent.connection.rpcEndpoint; - if (url.includes("devnet")) { - throw new Error("Devnet is not supported for airdrop. Please use mainnet."); - } - if (!url.includes("helius")) { - console.warn( - "Warning: Must use RPC with ZK Compression support. Double check with your RPC provider if in doubt." - ); - } const rpc = createRpc(url, url, url); const results = [];