Created
September 22, 2023 18:23
-
-
Save whatl3y/38f2a3470f6736744cfc8b0b5a8d015e to your computer and use it in GitHub Desktop.
Arbitrum Airdrop Wallet Check - checks and displays eligibility and claimable amount for 300 wallets in a seed phrase
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import assert from 'assert' | |
import BigNumber from 'bignumber.js' | |
import dotenv from 'dotenv' | |
import Web3 from 'web3' | |
import { Wallet } from 'ethers' | |
import { | |
Multicall, | |
ContractCallResults, | |
ContractCallContext, | |
} from 'ethereum-multicall' | |
import { AbiItem } from 'web3-utils' | |
dotenv.config() | |
;(async function run() { | |
try { | |
await main() | |
process.exit(0) | |
} catch (err) { | |
console.error(err) | |
process.exit(1) | |
} | |
})() | |
async function main() { | |
assert(process.env.SEED_PHRASE, 'seed') | |
const web3 = new Web3(new Web3.providers.HttpProvider(`https://1rpc.io/arb`)) | |
const multicall = new Multicall({ | |
web3Instance: web3, | |
tryAggregate: true, | |
}) | |
const airdropAbi = tokenDistAbi() | |
const addresses = new Array(300) | |
.fill(0) | |
.map((_, idx) => | |
getWalletFromSeedAndIdx(process.env.SEED_PHRASE as string, idx) | |
) | |
const callContext: ContractCallContext[] = [ | |
{ | |
reference: `available`, | |
contractAddress: '0x67a24ce4321ab3af51c2d0a4801c3e111d88c9d9', | |
abi: airdropAbi, | |
calls: addresses.map(({ address }) => ({ | |
reference: 'TokenDistributor', | |
methodName: 'claimableTokens', | |
methodParameters: [address], | |
})), | |
}, | |
] | |
const { results }: ContractCallResults = await multicall.call(callContext) | |
const claimResults = | |
results && results.available && results.available.callsReturnContext | |
const unclaimed = claimResults | |
.map((res, i) => ({ | |
address: addresses[i].address, | |
// pk: addresses[i].privateKey, | |
amountClaimable: new BigNumber( | |
res.returnValues[0].hex.toLowerCase() | |
).toFixed(), | |
})) | |
.filter((res) => new BigNumber(res.amountClaimable).gt(0)) | |
console.log(unclaimed) | |
console.log( | |
'TOTAL', | |
unclaimed | |
.reduce((tot, info) => tot.plus(info.amountClaimable), new BigNumber(0)) | |
.div(new BigNumber(10).pow(18)) | |
.toFormat() | |
) | |
} | |
function getWalletFromSeedAndIdx(seed: string, idx: number | string): Wallet { | |
return Wallet.fromMnemonic(seed, `m/44'/60'/0'/0/${idx}`) | |
} | |
function tokenDistAbi() { | |
const airdropAbi: AbiItem[] = [ | |
{ | |
inputs: [{ internalType: 'address', name: '', type: 'address' }], | |
name: 'claimableTokens', | |
outputs: [{ internalType: 'uint256', name: '', type: 'uint256' }], | |
stateMutability: 'view', | |
type: 'function', | |
}, | |
] | |
return airdropAbi | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment