Skip to content

Commit

Permalink
Test and fix claim function + merkle proof dummy data
Browse files Browse the repository at this point in the history
  • Loading branch information
geovgy committed Aug 19, 2024
1 parent 38fcacf commit 22c1566
Show file tree
Hide file tree
Showing 8 changed files with 111 additions and 1 deletion.
3 changes: 3 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -12,3 +12,6 @@ docs/

# Dotenv file
.env

# node nodules
node_modules/
Binary file added bun.lockb
Binary file not shown.
29 changes: 29 additions & 0 deletions merkle.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
import { StandardMerkleTree } from "@openzeppelin/merkle-tree";
import fs from "fs";

// Creating a Merkle Tree
// (1)
const values = [
["randomClaimCode1"],
["randomClaimCode2"]
];

// (2)
const tree = StandardMerkleTree.of(values, ["string"]);

// (3)
console.log('Merkle Root:', tree.root);

// (4)
fs.writeFileSync("tree.json", JSON.stringify(tree.dump()));

// Generating a proof
// (1)
for (const [i, v] of tree.entries()) {
if (v[0] === 'randomClaimCode1') {
// (2)
const proof = tree.getProof(i);
console.log('Value:', v);
console.log('Proof:', proof);
}
}
14 changes: 14 additions & 0 deletions package.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
{
"name": "pod-v2",
"module": "index.ts",
"type": "module",
"devDependencies": {
"@types/bun": "latest"
},
"peerDependencies": {
"typescript": "^5.0.0"
},
"dependencies": {
"@openzeppelin/merkle-tree": "^1.0.7"
}
}
6 changes: 5 additions & 1 deletion src/PODv2.sol
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ contract PODv2 is ERC1155, Ownable {
require(_merkleRoots[id] != 0, "ProofOfDrink: Merkle root not set");
require(!_claimed[id][claimCode], "ProofOfDrink: Claim code already used");
require(
MerkleProof.verify(proof, _merkleRoots[id], keccak256(abi.encodePacked(claimCode))),
MerkleProof.verify(proof, _merkleRoots[id], _toLeaf(claimCode)),
"ProofOfDrink: Invalid proof"
);
_claimed[id][claimCode] = true;
Expand Down Expand Up @@ -75,4 +75,8 @@ contract PODv2 is ERC1155, Ownable {
function _setTokenURI(uint256 id, string calldata uri_) internal {
_tokenURIs[id] = uri_;
}

function _toLeaf(string calldata claimCode) internal pure returns (bytes32) {
return keccak256(bytes.concat(keccak256(abi.encode(claimCode))));
}
}
32 changes: 32 additions & 0 deletions test/PODv2.t.sol
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,11 @@ contract PODv2Test is Test {
PODv2 internal pod;
address internal owner = address(0x1);

// Mock claim data
string[] internal claimCodes = ["randomClaimCode1", "randomClaimCode2"];
bytes32 internal merkleRoot = 0xf655031d86398a1795d61dbfde8dc580055d425e1189ad27f91122ab76b3ea8a;
bytes32[] internal merkleProof = [bytes32(0x16194519b413b5592f3cc85d14c03c252445f323ccf53e24380ef4cfdcb0b4ea)];

function setUp() public {
pod = new PODv2(owner);
}
Expand Down Expand Up @@ -86,4 +91,31 @@ contract PODv2Test is Test {

vm.assertEq(pod.uri(1), newUri);
}

function test_claim() public {
vm.prank(owner);
pod.create(merkleRoot, "ipfs://testtesttest");

address recipient = address(0x420);

// Should execute and emit event
vm.expectEmit();
emit PODv2.Claimed(recipient, 1, claimCodes[0]);

pod.claim(recipient, 1, claimCodes[0], merkleProof);

vm.assertEq(pod.balanceOf(recipient, 1), 1);

// Revert if claim code already used
vm.expectRevert();
pod.claim(recipient, 1, claimCodes[0], merkleProof);

// Revert if invalid proof
vm.expectRevert();
pod.claim(recipient, 1, claimCodes[1], merkleProof); // merkle proof is for claimCodes[0]

// Revert if merkle root not set
vm.expectRevert();
pod.claim(recipient, 2, claimCodes[0], merkleProof); // id 2 not created yet
}
}
1 change: 1 addition & 0 deletions tree.json
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
{"format":"standard-v1","leafEncoding":["string"],"tree":["0xf655031d86398a1795d61dbfde8dc580055d425e1189ad27f91122ab76b3ea8a","0xd4d75523d33f48daba71ecbfd46679f6968e274d31705b04355c4a1570ed303c","0x16194519b413b5592f3cc85d14c03c252445f323ccf53e24380ef4cfdcb0b4ea"],"values":[{"value":["randomClaimCode1"],"treeIndex":1},{"value":["randomClaimCode2"],"treeIndex":2}]}
27 changes: 27 additions & 0 deletions tsconfig.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
{
"compilerOptions": {
// Enable latest features
"lib": ["ESNext"],
"target": "ESNext",
"module": "ESNext",
"moduleDetection": "force",
"jsx": "react-jsx",
"allowJs": true,

// Bundler mode
"moduleResolution": "bundler",
"allowImportingTsExtensions": true,
"verbatimModuleSyntax": true,
"noEmit": true,

// Best practices
"strict": true,
"skipLibCheck": true,
"noFallthroughCasesInSwitch": true,

// Some stricter flags (disabled by default)
"noUnusedLocals": false,
"noUnusedParameters": false,
"noPropertyAccessFromIndexSignature": false
}
}

0 comments on commit 22c1566

Please sign in to comment.