# Manage through ABI

Bolarity enables you to interact with any smart contract. This section demonstrates how to construct your interaction data using Aave USDT vault as an example.

**Step 1: Generate the payload for your requirement**

```typescript
// Call Aave contract methods

// Encode the user's Solana address as a bytes32 format for compatibility with Ethereum.
const userAddress = coder.encode(
  ["bytes32"],
  [Buffer.from(new PublicKey("6v9YRMJbiXSjwco3evS2XdNuqPbwzKf3ykmn5iQJ4UyF").toBytes())]
); // Your Solana address

// Define the user's Ethereum proxy address.
const proxyAddress = '0xD00c212f8Cc24CdB897D5CE4eD1962Ca0A52f709'; // Your generated Ethereum address

// *** Approve USDT ***
const usdtContractAddress = coder.encode(
  ["bytes32"],
  [ethers.utils.zeroPad(Buffer.from(hexStringToUint8Array('0xaA8E23Fb1079EA71e0a56F48a2aA51851D8433D0')), 32)]
); // USDT contract address

let ABI = ["function approve(address to, uint256 tokenId)"];
let iface = new ethers.utils.Interface(ABI);

// Encode the approval function call to allow infinite USDT approval to a specific address.
let paras = iface.encodeFunctionData("approve", [
  '0x6ae43d3271ff6888e7fc43fd7321a503ff738951', // Address to approve
  BigInt("0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff") // Maximum token approval
]);

// Assemble the payload for the approval transaction.
let payloadPart = coder.encode(
  ["bytes32", "uint256", "bytes"],
  [usdtContractAddress, 0, paras]
);
let payload = coder.encode(
  ["bytes32", "bytes"],
  [userAddress, payloadPart]
);

console.log("Approve USDT Payload:", payload);

// *** Deposit USDT ***
// Ensure USDT is approved before proceeding with the deposit.

const depositContractAddress = coder.encode(
  ["bytes32"],
  [ethers.utils.zeroPad(Buffer.from(hexStringToUint8Array('0x6Ae43d3271ff6888e7Fc43Fd7321a503ff738951')), 32)]
); // Aave lending pool contract address

ABI = ["function supply(address asset,uint256 amount,address onBehalfOf,uint16 referralCode)"];
iface = new ethers.utils.Interface(ABI);

// Encode the supply function call to deposit USDT into Aave.
paras = iface.encodeFunctionData("supply", [
  '0xaa8e23fb1079ea71e0a56f48a2aa51851d8433d0', // USDT contract address
  100000000, // Amount to deposit (100 USDT, 6 decimal precision)
  proxyAddress, // Deposit on behalf of the proxy address
  0 // Referral code
]);

// Assemble the payload for the deposit transaction.
payloadPart = coder.encode(
  ["bytes32", "uint256", "bytes"],
  [depositContractAddress, 0, paras]
);
payload = coder.encode(
  ["bytes32", "bytes"],
  [userAddress, payloadPart]
);

console.log("Deposit USDT Payload:", payload);

// *** Withdraw USDT ***
const withdrawContractAddress = coder.encode(
  ["bytes32"],
  [ethers.utils.zeroPad(Buffer.from(hexStringToUint8Array('0x6Ae43d3271ff6888e7Fc43Fd7321a503ff738951')), 32)]
); // Aave lending pool contract address

ABI = ["function withdraw(address asset,uint256 amount,address to)"];
iface = new ethers.utils.Interface(ABI);

// Encode the withdraw function call to remove USDT from Aave.
paras = iface.encodeFunctionData("withdraw", [
  '0xaa8e23fb1079ea71e0a56f48a2aa51851d8433d0', // USDT contract address
  BigInt("0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff"), // Withdraw maximum amount
  proxyAddress // Withdraw to the proxy address
]);

// Assemble the payload for the withdrawal transaction.
payloadPart = coder.encode(
  ["bytes32", "uint256", "bytes"],
  [withdrawContractAddress, 0, paras]
);
payload = coder.encode(
  ["bytes32", "bytes"],
  [userAddress, payloadPart]
);

console.log("Withdraw USDT Payload:", payload);

```

**Step 2: Call Ethereum smart contract using this payload**

```typescript
// Encode the Solana address as a bytes32 format, compatible with Ethereum.
const solanaAddress = coder.encode(
  ["bytes32"],
  [Buffer.from(new PublicKey("your-solana-account").toBytes())]
);

// Encode the target Ethereum contract address, padded to 32 bytes for consistency.
const contractAddress = coder.encode(
  ["bytes32"],
  [ethers.utils.zeroPad(Buffer.from([contractAddressYouWantToCall]), 32)]
);

// Define the ABI for the Ethereum contract's "store" function, which accepts a uint256 parameter.
let ABI = ["function store(uint256 num)"];

// Create an ethers Interface instance to encode the function call data.
let iface = new ethers.utils.Interface(ABI);

// Encode the function call for the "store" function with a parameter value of 2.
let params = iface.encodeFunctionData("store", [2]);

// Assemble the payload part by encoding the contract address, a placeholder value (0), and the encoded function data.
let payloadPart = coder.encode(
  ["bytes32", "uint256", "bytes"],
  [contractAddress, 0, params]
);

// Final payload: combine the Solana address and the payload part into a single message.
const payload = coder.encode(
  ["bytes32", "bytes"],
  [solanaAddress, payloadPart]
);

// Send the message using the Solana program (via the Anchor framework).
const programID = new PublicKey("solana-program-address"); // The Solana program ID.
const program = new anchor.Program(idl, programID); // Anchor program instance.
const message = hexStringToUint8Array(payload); // Convert payload to a byte array.

// Create the instruction to send the message to the Solana program.
const ix3 = program.methods
  .sendMessage(Buffer.from(message)) // Pass the message as a buffer.
  .accounts({
    config: realConfig, // Real configuration for the program.
    wormholeProgram: CORE_BRIDGE_PID, // Wormhole program ID for cross-chain communication.
    ...wormholeAccounts2, // Additional necessary accounts for the transaction.
  })
  .instruction();

// Create a new transaction and add the instruction.
const tx3 = new Transaction().add(await ix3);

try {
  const commitment: Commitment = 'confirmed'; // Set the commitment level for transaction confirmation.
  
  // Send the transaction and await confirmation.
  await sendAndConfirmTransaction(provider.connection, tx3, [yourSolanaAccount], { commitment });
} catch (error) {
  // Catch and log any errors during the transaction submission process.
  console.error("Error submitting transaction:", error);
}
```


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://docs.bolarity.xyz/quick-start/cross-chain-yield-management/manage-through-abi.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
