Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

使用 Merkle 树做白名单验证 #3

Open
tangminjie opened this issue Jun 15, 2022 · 0 comments
Open

使用 Merkle 树做白名单验证 #3

tangminjie opened this issue Jun 15, 2022 · 0 comments

Comments

@tangminjie
Copy link
Member

使用 Merkle 树做白名单验证,简单来说就是将所有的白名单钱包地址做为 Merkle 树的叶节点生成一棵 Merkle 树,在部署的NFT 合约中只存储 Merkle 树的 root hash,这样避免了在合约中存储所有白名单地址带来的高额 gas 费用。在 mint 时,链下生成钱包地址的 Merkle proof,调用合约进行验证。

合约实现

whitelist.sol中实现了传统mapping储存白名单的方式和Merkle树储存白名单的方式,因为使用mapping需要占用大量的存储空间,所以我们选择使用Merkle的方式来验证。

openzepplin MerkleProof

openzeppelin 提供了Merkle实现库,我们仅需要import '@openzeppelin/contracts/utils/cryptography/MerkleProof.sol';
并且实现:
1.设置Merkle root hash
2. 提供external接口对 proof进行验证,MerkleProof.verify(proof, _merkleTreeRoot, keccak256(abi.encodePacked(leaf) 其中leaf传入调用者的地址,也就是白名单中的地址才能校验成功。

Merkle proof 证明生成

调用合约验证的 Merkle proof 需要在前端生成。生成过程需要用到 merkletreejs和 keccak256 两个库,前者用于创建 Merkle 树,后者用于生成哈希。
链下实现代码在Utils/helpers.js文件中:

  1. 获取 hardhat-deploy生成的地址,当作白名单测试地址。
  2. 生成白名单地址的Merkle树:
    const leafNodes = whitelistAddresses.map((adr) => keccak256(adr));
    const merkleTree = new MerkleTree(leafNodes, keccak256, {
      sortPairs: true,
    });
  1. 对地址列表生成Merkle证明: proofs: whitelistAddresses.map((addr) => merkleTree.getHexProof(keccak256(addr))),
    生成证明格式:
Proof of 0xc12ae5Ba30Da6eB11978939379D383beb5Df9b33:  [
  '0x1575cc1dded49f942913392f94716824d29b8fa45876b2db6295d16a606533a4',
  '0x6c42c6099e51e28eef8f19f71765bb42c571d5c7177996f177606138f65c0c2b',
  '0xb0d6f760008340e3f60414d84b305702faa6418f44f31de07b10e05bf369eb3b',
  '0x4c880bf401add28c4e51270dfe16b28c3ca1b3d263ff7c5863fc8214b4046364'
]

验证过程

调用checkMerkleTreeRootForWhitelist 传入验证者address 和对应的 proof。

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant