Skip to content

Commit

Permalink
Merge pull request #12 from majin-land/add-redeem-resolver
Browse files Browse the repository at this point in the history
add redeem resolver
  • Loading branch information
imajindev authored Aug 10, 2024
2 parents 9dd61b1 + 9ae752f commit ed42e82
Show file tree
Hide file tree
Showing 9 changed files with 2,975 additions and 13 deletions.
11 changes: 10 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -129,4 +129,13 @@ dist
.yarn/install-state.gz
.pnp.*

.nx
.nx

#Hardhat files
coverage
coverage.json
typechain
cache
artifacts
.openzeppelin
build
1 change: 1 addition & 0 deletions apps/contract/.env.sample
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
TESTNET_PRIVATE_KEY=
7 changes: 7 additions & 0 deletions apps/contract/.solhint.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
{
"extends": "solhint:recommended",
"rules": {
"compiler-version": ["error", "^0.8.0"],
"func-visibility": ["warn", { "ignoreConstructors": true }]
}
}
1 change: 1 addition & 0 deletions apps/contract/.solhintignore
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
node_modules
105 changes: 105 additions & 0 deletions apps/contract/hardhat.config.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,105 @@
const fs = require('fs')
const fsExtra = require('fs-extra')
const { subtask, task } = require('hardhat/config')
const { TASK_CLEAN, TASK_COMPILE } = require('hardhat/builtin-tasks/task-names')
// require('@nomiclabs/hardhat-waffle')
// require('@nomiclabs/hardhat-ethers')
require('hardhat-deploy')
require('hardhat-contract-sizer')
require('@openzeppelin/hardhat-upgrades')

require('dotenv').config({ path: './.env' })

let mnemonic = process.env.MNEMONIC
if (!mnemonic) {
mnemonic = 'test test test test test test test test test test test junk'
}
const mnemonicAccounts = {
mnemonic,
}

const account = {
Testnet: process.env.TESTNET_PRIVATE_KEY,
Mainnet: process.env.MAINNET_PRIVATE_KEY,
}

// Default output dir to abi contracts in frontend
const contractsFrontDir = './compiled'

// You need to export an object to set up your config
// Go to https://hardhat.org/config/ to learn more

/**
* @type import('hardhat/config').HardhatUserConfig
*/
const config = {
solidity: {
version: '0.8.20',
settings: {
evmVersion: "paris",
optimizer: {
enabled: true,
runs: 200,
},
},
},
paths: {
sources: './src',
tests: './test',
cache: './cache',
artifacts: './artifacts',
},
defaultNetwork: 'optimismSepolia',
networks: {
hardhat: {
accounts: mnemonicAccounts,
},
optimismSepolia: {
url: 'https://sepolia.optimism.io',
chainId: 11155420,
accounts: account.Testnet ? [account.Testnet] : mnemonicAccounts,
},
},
namedAccounts: {
deployer: {
default: 0, // here this will by default take the first account as deployer
},
},
mocha: {
timeout: 50000, // 50 seconds timeout
},
}

// // This is a sample Hardhat task. To learn how to create your own go to
// // https://hardhat.org/guides/create-task.html
// task('accounts', 'Prints the list of accounts', async (taskArgs, hre) => {
// const accounts = await hre.ethers.getSigners()
// accounts.forEach((acc) => {
// console.log(acc.address)
// })
// })

task(TASK_CLEAN, 'Clean all artifacts & folder contracts in frontend').setAction(async (taskArgs, hre, runSuper) => {
await runSuper()
if (fs.existsSync('./deployments')) {
fs.rmdirSync('./deployments', { recursive: true })
}
await hre.run('clean-front-contracts')
})

subtask('clean-front-contracts', 'Clear frontend contracts folder').setAction(async () => {
// Clear if exist
if (fs.existsSync(contractsFrontDir)) {
fsExtra.emptyDirSync(contractsFrontDir)
}
})

task(TASK_COMPILE, 'Deploy contracts').setAction(async (taskArgs, hre, runSuper) => {
console.log('TASK_COMPILE', taskArgs)
if (!fs.existsSync(contractsFrontDir)) {
fs.mkdirSync(contractsFrontDir, { recursive: true })
}
await runSuper(taskArgs)
})

module.exports = config
33 changes: 33 additions & 0 deletions apps/contract/scripts/deploy-ticket-redeem.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
// We require the Hardhat Runtime Environment explicitly here. This is optional
// but useful for running the script in a standalone fashion through `node <script>`.
//
// When running the script with `npx hardhat run <script>` you'll find the Hardhat
// Runtime Environment's members available in the global scope.
require('dotenv').config({ path: '../.env' })
const { ethers } = require('hardhat')

async function main() {
const [deployer] = await ethers.getSigners()
console.log('Deploying contracts with the account:', deployer.address)

console.log('deployer', deployer)

// const deployerBalance = (await deployer.getBalance()).toString()
// console.log('Account balance:', deployerBalance)

// if (deployerBalance === '0') return // deployment will fail

const RedeemResolver = await ethers.getContractFactory('RedeemResolver')
const redeemResolver = await RedeemResolver.deploy('0x4200000000000000000000000000000000000021')
await redeemResolver.deployed()

console.log('RedeemResolver deployed to:', redeemResolver.address)
console.log('RedeemResolver details:', redeemResolver)
}

// We recommend this pattern to be able to use async/await everywhere
// and properly handle errors.
main().catch((error) => {
console.error(error)
process.exitCode = 1
})
53 changes: 53 additions & 0 deletions apps/contract/src/RedeemResolver.sol
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@

// redeem ticket attestation resolver
// SPDX-License-Identifier: MIT
pragma solidity 0.8.20;

import { SchemaResolver } from "@ethereum-attestation-service/eas-contracts/contracts/resolver/SchemaResolver.sol";
import { IEAS, Attestation } from "@ethereum-attestation-service/eas-contracts/contracts/IEAS.sol";

contract RedeemResolver is SchemaResolver {
error OutOfBounds();

mapping(bytes32 => bool) private redeemedMap;

constructor(IEAS eas) SchemaResolver(eas) {
}

function onAttest(Attestation calldata attestation, uint256 /*value*/) internal override returns (bool) {
bytes32 uid = _toBytes32(attestation.data, 0);

bool redeemed = redeemedMap[uid];
if (redeemed == true) {
return false;
}
redeemedMap[uid] = true;

return true;
}

function onRevoke(Attestation calldata /*attestation*/, uint256 /*value*/) internal pure override returns (bool) {
return true;
}

function toBytes32(bytes memory data, uint256 start) external pure returns (bytes32) {
return _toBytes32(data, start);
}

function _toBytes32(bytes memory data, uint256 start) private pure returns (bytes32) {
unchecked {
if (data.length < start + 32) {
revert OutOfBounds();
}
}

bytes32 tempBytes32;

// solhint-disable-next-line no-inline-assembly
assembly {
tempBytes32 := mload(add(add(data, 0x20), start))
}

return tempBytes32;
}
}
Loading

0 comments on commit ed42e82

Please sign in to comment.