On-chain NFT holder snapshot using ownerOf() for Ethereum and Monad.
Set values in snap.js under DEFAULTS:
chaincontractAddress- optional manual range
Fixed RPCs:
- Ethereum:
https://eth.llamarpc.com - Monad:
https://rpc.monad.xyz
Output format:
snapshot.txtwith one line per holder:address,count
Then run:
npm install
node snap.jsRun the web app:
cd frontend
npm install
npm run devThen open the local URL shown by Vite and run snapshots from UI. UI behavior:
- user enters only contract + chain
- app auto-uses fixed RPC and fixed concurrency
- app auto-downloads
snapshot-<chain>.txt(address,count)
Contract source: contracts/NFTLens.sol
- Use it for small batched validation checks (
ownersOf) after snapshot - Full snapshot still uses transfer-log indexing
Frontend:
- paste deployed lens address in
Lens Contract Address - click
Validate Sample (30)to compare indexed owners vs on-chain
CLI demo call:
node scripts/lens-demo.js --rpc https://eth.llamarpc.com --nft 0xYourNFT --lens 0xYourLens --ids 1,2,3,4,5Deploy lens contracts:
- Add to
.env:
DEPLOYER_PRIVATE_KEY=0xYOUR_PRIVATE_KEY
ETH_RPC_URL=https://eth.llamarpc.com
MONAD_RPC_URL=https://rpc.monad.xyz- Install deps and deploy:
npm install
npm run deploy:lens -- --chain monad
# or
npm run deploy:lens -- --chain eth
# deploy ERC20 lens
npm run deploy:lens -- --chain monad --contract erc20
npm run deploy:lens -- --chain eth --contract erc20