From 593ab72ecfbd3fb1b60aa605633dc115d89440de Mon Sep 17 00:00:00 2001 From: yssf-io Date: Tue, 2 Jan 2024 10:25:10 +0100 Subject: [PATCH] adding ethers and call to aws endpoint in app --- app/App.tsx | 93 ++++++++++---- app/babel.config.js | 3 + app/package.json | 4 + app/utils/snarkjs.ts | 45 +++++++ app/yarn.lock | 206 +++++++++++++++++++++++++++++- common/src/constants/constants.ts | 2 + 6 files changed, 324 insertions(+), 29 deletions(-) create mode 100644 app/utils/snarkjs.ts diff --git a/app/App.tsx b/app/App.tsx index ee5a48b60..933100121 100644 --- a/app/App.tsx +++ b/app/App.tsx @@ -45,9 +45,9 @@ import { DEFAULT_DOB, DEFAULT_DOE, DEFAULT_ADDRESS, - LOCAL_IP, } from '@env'; import {DataHash, PassportData} from '../common/src/utils/types'; +import {AWS_ENDPOINT} from '../common/src/constants/constants'; import { hash, toUnsignedByte, @@ -59,8 +59,14 @@ import { } from '../common/src/utils/utils'; import { samplePassportData } from '../common/src/utils/passportDataStatic'; +import "@ethersproject/shims" +import { ethers } from "ethers"; +import axios from 'axios'; +import groth16ExportSolidityCallData from './utils/snarkjs'; +import contractAddresses from "./deployments/addresses.json" +import proofOfPassportArtefact from "./deployments/ProofOfPassport.json"; + console.log('DEFAULT_PNUMBER', DEFAULT_PNUMBER); -console.log('LOCAL_IP', LOCAL_IP); const SKIP_SCAN = false; @@ -89,8 +95,7 @@ function App(): JSX.Element { const [proofTime, setProofTime] = useState(0); const [totalTime, setTotalTime] = useState(0); - const [proofResult, setProofResult] = useState(''); - + const [proof, setProof] = useState<{proof: string, inputs: string} | null>(null); const [minting, setMinting] = useState(false); const [disclosure, setDisclosure] = useState({ @@ -258,8 +263,6 @@ function App(): JSX.Element { const start = Date.now(); NativeModules.RNPassportReader.provePassport(inputs, (err: any, res: any) => { const end = Date.now(); - setGeneratingProof(false) - setStep('proofGenerated'); if (err) { console.error(err); @@ -275,21 +278,67 @@ function App(): JSX.Element { const deserializedProof = JSON.parse(parsedResponse.serialized_proof); console.log('deserializedProof', deserializedProof); + + const deserializedInputs = JSON.parse(parsedResponse.serialized_inputs); + console.log('deserializedInputs', deserializedInputs); setProofTime(parsedResponse.duration); setTotalTime(end - start); - setProofResult(JSON.stringify(deserializedProof)); + setProof({ + proof: JSON.stringify(deserializedProof), + inputs: JSON.stringify(deserializedInputs), + }); + setGeneratingProof(false) + setStep('proofGenerated'); }); }; - const handleMint = () => { + const handleMint = async () => { setMinting(true) + if (!proof?.proof || !proof?.inputs) { + console.log('proof or inputs is null'); + return; + } + if (!contractAddresses.ProofOfPassport || !proofOfPassportArtefact.abi) { + console.log('contracts addresses or abi not found'); + return; + } - // 5. Format the proof and publicInputs as calldata for the verifier contract - // 6. Call the verifier contract with the calldata + // Format the proof and publicInputs as calldata for the verifier contract + const p = JSON.parse(proof.proof); + const i = JSON.parse(proof.inputs); + // const p = {"a": ["16502577771187684977980616374304236605057905196561863637384296592370445017998", "3901861368174142739149849352179287633574688417834634300291202761562972709023"], "b": [["14543689684654938043989715590415160645004827219804187355799512446208262437248", "2758656853017552407340621959452084149765188239766723663849017782705599048610"], ["11277365272183899064677884160333958573750879878546952615484891009952508146334", "6233152645613613236466445508816847016425532566954931368157994995587995754446"]], "c": ["6117026818273543012196632774531089444191538074414171872462281003025766583671", "10261526153619394223629018490329697233150978685332753612996629076672112420472"]} + // const i = ["0", "0", "0", "146183216590389235917737925524385821154", "43653084046336027166990", "21085389953176386480267", "56519161086598100699293", "15779090386165698845937", "23690430366843652392111", "22932463418406768540896", "51019038683800409078189", "50360649287615093470666", "47789371969706091489401", "15311247864741754764238", "20579290199534174842880", "1318168358802144844680228651107716082931624381008"] + console.log('p', p); + console.log('i', i); + const cd = groth16ExportSolidityCallData(p, i); + const callData = JSON.parse(`[${cd}]`); + console.log('callData', callData); + // format transaction + // for now, we do it all on mumbai + try { + const provider = new ethers.JsonRpcProvider('https://polygon-mumbai-bor.publicnode.com'); + const proofOfPassportOnMumbai = new ethers.Contract(contractAddresses.ProofOfPassport, proofOfPassportArtefact.abi, provider); + + const transactionRequest = await proofOfPassportOnMumbai + .mint.populateTransaction(...callData); + console.log('transactionRequest', transactionRequest); + + const response = await axios.post(AWS_ENDPOINT, { + chain: "mumbai", + tx_data: transactionRequest + }); + console.log('response status', response.status) + console.log('response data', response.data) + const receipt = await provider.waitForTransaction(response.data.hash); + console.log('receipt', receipt) + } catch (err) { + console.log('err', err); + } }; + return ( @@ -456,7 +505,7 @@ function App(): JSX.Element { Proof: - {proofResult} + {JSON.stringify(proof)} @@ -466,22 +515,12 @@ function App(): JSX.Element { Total Duration: {formatDuration(totalTime)} - - {generatingProof ? - - : - } + ) : null} diff --git a/app/babel.config.js b/app/babel.config.js index f842b77fc..6d2f1f342 100644 --- a/app/babel.config.js +++ b/app/babel.config.js @@ -1,3 +1,6 @@ module.exports = { presets: ['module:metro-react-native-babel-preset'], + plugins: [ + ["@babel/plugin-transform-private-methods", { "loose": true }], + ], }; diff --git a/app/package.json b/app/package.json index c535003f4..8429accca 100644 --- a/app/package.json +++ b/app/package.json @@ -10,12 +10,16 @@ "test": "jest" }, "dependencies": { + "@babel/plugin-transform-private-methods": "^7.23.3", + "@ethersproject/shims": "^5.7.0", "@gluestack-style/react": "^1.0.12", "@gluestack-ui/config": "^1.0.3", "@gluestack-ui/themed": "^1.0.11", + "axios": "^1.6.3", "body-parser": "^1.20.2", "buffer": "^6.0.3", "crypto-js": "^4.1.1", + "ethers": "^6.9.1", "express": "^4.18.2", "js-sha256": "^0.9.0", "node-forge": "^1.3.1", diff --git a/app/utils/snarkjs.ts b/app/utils/snarkjs.ts new file mode 100644 index 000000000..2005645bd --- /dev/null +++ b/app/utils/snarkjs.ts @@ -0,0 +1,45 @@ +// utils from snarkjs. If snarkjs is updated and this breaks, might move this to lambda function +function unstringifyBigInts(o: any): any { + if (typeof o == "string" && /^[0-9]+$/.test(o)) { + return BigInt(o); + } else if (typeof o == "string" && /^0x[0-9a-fA-F]+$/.test(o)) { + return BigInt(o); + } else if (Array.isArray(o)) { + return o.map(unstringifyBigInts); + } else if (typeof o == "object") { + if (o === null) return null; + const res: any = {}; + const keys = Object.keys(o); + keys.forEach((k) => { + res[k] = unstringifyBigInts(o[k]); + }); + return res; + } else { + return o; + } +} + +function p256(n: any) { + let nstr = n.toString(16); + while (nstr.length < 64) nstr = "0"+nstr; + nstr = `"0x${nstr}"`; + return nstr; +} + +export default function groth16ExportSolidityCallData(_proof: any, _pub: any) { + const proof = unstringifyBigInts(_proof); + const pub = unstringifyBigInts(_pub); + + let inputs = ""; + for (let i=0; i= 1.43.0 < 2": resolved "https://registry.yarnpkg.com/mime-db/-/mime-db-1.52.0.tgz#bbabcdc02859f4987301c856e3387ce5ec43bf70" integrity sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg== -mime-types@^2.1.27, mime-types@~2.1.24, mime-types@~2.1.34: +mime-types@^2.1.12, mime-types@^2.1.27, mime-types@~2.1.24, mime-types@~2.1.34: version "2.1.35" resolved "https://registry.yarnpkg.com/mime-types/-/mime-types-2.1.35.tgz#381a871b62a734450660ae3deee44813f70d959a" integrity sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw== @@ -7125,6 +7312,11 @@ proxy-addr@~2.0.7: forwarded "0.2.0" ipaddr.js "1.9.1" +proxy-from-env@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/proxy-from-env/-/proxy-from-env-1.1.0.tgz#e102f16ca355424865755d2c9e8ea4f24d58c3e2" + integrity sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg== + punycode@^2.1.0: version "2.3.0" resolved "https://registry.yarnpkg.com/punycode/-/punycode-2.3.0.tgz#f67fa67c94da8f4d0cfff981aee4118064199b8f" @@ -7992,6 +8184,11 @@ tsconfig@7: strip-bom "^3.0.0" strip-json-comments "^2.0.0" +tslib@2.4.0: + version "2.4.0" + resolved "https://registry.yarnpkg.com/tslib/-/tslib-2.4.0.tgz#7cecaa7f073ce680a05847aa77be941098f36dc3" + integrity sha512-d6xOpEDfsi2CZVlPQzGeux8XMwLT9hssAsaPYExaQMuYskwb+x1x7J371tWlbBdWHroy99KnVB6qIkUbs5X3UQ== + tslib@^1.8.1: version "1.14.1" resolved "https://registry.yarnpkg.com/tslib/-/tslib-1.14.1.tgz#cf2d38bdc34a134bcaf1091c41f6619e2f672d00" @@ -8304,6 +8501,11 @@ write-file-atomic@^4.0.2: imurmurhash "^0.1.4" signal-exit "^3.0.7" +ws@8.5.0: + version "8.5.0" + resolved "https://registry.yarnpkg.com/ws/-/ws-8.5.0.tgz#bfb4be96600757fe5382de12c670dab984a1ed4f" + integrity sha512-BWX0SWVgLPzYwF8lTzEy1egjhS4S4OEAHfsO8o65WOVsrnSRGaSiUaa9e0ggGlkMTtBlmOpEXiie9RUcBO86qg== + ws@^6.2.2: version "6.2.2" resolved "https://registry.yarnpkg.com/ws/-/ws-6.2.2.tgz#dd5cdbd57a9979916097652d78f1cc5faea0c32e" diff --git a/common/src/constants/constants.ts b/common/src/constants/constants.ts index 9b198657c..0bec20f4a 100644 --- a/common/src/constants/constants.ts +++ b/common/src/constants/constants.ts @@ -1,3 +1,5 @@ +export const AWS_ENDPOINT = "https://0pw5u65m3a.execute-api.eu-north-1.amazonaws.com/api-stage/mint" + export const attributeToPosition = { issuing_state: [2, 4], name: [5, 43],