A secure, gas-optimized airdrop smart contract built with Solidity that uses EIP-712 for off-chain signature verification and Merkle Trees for scalable whitelisting.
- ✅ EIP-712 typed structured signatures for off-chain whitelisting
- 🌲 Merkle Tree proof verification for scalable claims (
O(log N)) - 🔒 Signature replay protection
- 🔄 One-time claim enforcement
- ⛽ Gas-optimized design
-
Solidity for smart contracts
-
Foundry for testing and deployment
-
Merkle Tree JS utilities for generating proofs
-
EIP-712 Typed Data Signatures
├── contracts
│ └── Airdrop.sol
├── scripts
│ └── DeployMerkleAirDrop.s.sol / Interact.s.sol
├── test
│ └── MerkleAirDrop.t.sol
├── assets
│ └── airdrop.png
└── README.md
- Off-chain, a list of eligible addresses and airdrop amounts is created.
- A Merkle Tree is generated using this list.
- Each user signs a claim message using EIP-712.
- The user sends a transaction with:
- Their address and claim amount
- EIP-712 signature
- Merkle proof
- The smart contract verifies:
- The Merkle proof is valid
- The signature matches the typed data
- The user hasn’t claimed before
- Tokens are transferred securely 🎉
-
Clone the repo:
git clone https://github.com/DakshMane/AirDropContract cd merkle-airdrop -
Install dependencies:
npm install
-
Compile contracts:
forge build
-
Run tests:
forge test
function claim(address account, uint256 amount, bytes calldata sig, bytes32[] calldata merkleProof) external {
require(!claimed[account], "Already claimed");
// Verify Merkle proof
bytes32 node = keccak256(abi.encodePacked(account, amount));
require(MerkleProof.verify(merkleProof, merkleRoot, node), "Invalid proof");
// Verify EIP-712 signature
require(verifySignature(account, amount, sig), "Invalid signature");
claimed[account] = true;
token.transfer(account, amount);
}PRs and feedback welcome! If you found this useful or learned something, feel free to give it a ⭐
Made with ❤️ by Daksh Mane
Open to feedback, collaborations, and Web3 conversations!
