# snarkjs: JavaScript implementation of zkSNARKs. This is a JavaScript and Pure Web Assembly implementation of zkSNARK schemes. It uses the Groth16 Protocol (3 point only and 3 pairings) This library includes all the tools required to perform trusted setup multi-party ceremonies: including the universal "powers of tau" ceremony, and the second phase circuit specific ceremonies. The formats used in this library for the multi-party computation are compatible with the ones used in [Semaphore's Perpetual Powers of Tau](https://github.com/weijiekoh/perpetualpowersoftau) and [other implementations](https://github.com/kobigurk/phase2-bn254). This library uses the compiled circuits generated by the [circom](https://github.com/iden3/circom) compiler. The library works in `node.js` as well as directly in the browser. It's an [ES module](https://hacks.mozilla.org/2018/03/es-modules-a-cartoon-deep-dive/), so it can be directly imported into bigger projects using [Rollup](https://rollupjs.org/guide/en/) or [Webpack](https://webpack.js.org/). The low-level cryptography is performed directly in wasm, and uses worker threads to parallelize the computations. The result is a high performance library with benchmarks comparable to host implementations. ## Preliminaries ### Install node v14 First off, make sure you have a recent version of `Node.js` installed. While any version after `v12` should work fine, we recommend you install `v14` or later. If you’re not sure which version of Node you have installed, you can run: ```sh node -v ``` To download the latest version of Node, see [here](https://nodejs.org/en/download/). ### Install snarkjs and circom To install `circom` and `snarkjs`, run: ```sh npm install -g circom@latest npm install -g snarkjs@latest ``` If you're seeing an error, try prefixing both commands with `sudo`. ### Understand the Help command To see a list of all `snarkjs` commands, as well as descriptions about their inputs and outputs, run: ```sh snarkjs --help ``` The help for specific command: Example ```sh snarkjs groth16 prove --help ``` Most of the commands have a short alias. For example, the previous command can also be invoked as: ```sh snarkjs g16p --help ``` ### Debugging tip If you a feel a command is taking longer than it should, re-run it with a `-v` or `--verbose` option to see more details about how it's progressing and where it's getting blocked. For example: ```sh snarkjs g16p -v ``` ## Tutorial ### 0. Create a new directory ```sh mkdir snarkjs_example cd snarkjs_example ``` ### 1. Start a new ceremony. ```sh snarkjs powersoftau new bn128 12 pot12_0000.ptau ``` The first parameter after `new` refers to the type of curve you wish to use. At the moment, we support both `bn128` and `bls12-381`. The second parameter, in this case `12`, is the power of two of the maximum number of contraints that the ceremony can accept. In this case, the maximum number of constraints is `2^12 = 4096`. ### 2. Contribute to the ceremony ```sh snarkjs powersoftau contribute pot12_0000.ptau pot12_0001.ptau --name="Example Name" -v ``` The name is a random name and it's include for reference. It's printed in the verification. ### 3. Provide a second contribution ```sh snarkjs powersoftau contribute pot12_0001.ptau pot12_0002.ptau --name="Second contribution Name" -v -e="some random text" ``` the -e parameter allows the comman to be non interactive and use this text as an extra source of entropy for the random generation. ### 4. Verify the file ```sh snarkjs powersoftau verify pot12_0002.ptau ``` This command checks all the contributions of the Multiparty Computation (MPC) and list the hashes of the intermediary results. ### Contribute using third party software ```sh snarkjs powersoftau export challange pot12_0002.ptau challange_0003 snarkjs powersoftau challange contribute bn128 challange_0003 response_0003 snarkjs powersoftau import response pot12_0002.ptau response_0003 pot12_0003.ptau -n="Third contribution name" ``` ### Add a beacon ```sh snarkjs powersoftau beacon pot12_0003.ptau pot12_beacon.ptau 0102030405060708090a0b0c0d0e0f101112131415161718191a1b1c1d1e1f 10 -n="Final Beacon" ``` ### Prepare phase2 ```sh snarkjs powersoftau prepare phase2 pot12_beacon.ptau pot12_final.ptau -v ``` ### Verify the last file ```sh snarkjs powersoftau verify pot12_final.ptau ``` ### Create a circuit ```sh cat < circuit.circom template Multiplier(n) { signal private input a; signal private input b; signal output c; signal int[n]; int[0] <== a*a + b; for (var i=1; i input.json {"a": 3, "b": 11} EOT snarkjs wtns calculate circuit.wasm input.json witness.wtns ``` ### Debug witness calculation In general, when you are developing a new circuit you will want to check for some errors in the witness calculation process. You can do it by doing ```sh snarkjs wtns debug circuit.wasm input.json witness.wtns circuit.sym --trigger --get --set ``` This will log every time a new component is started/ended ( --trigger ) when a signal is set (--set) and when it's get (--get) ### Proof calculation ```sh snarkjs groth16 prove circuit_final.zkey witness.wtns proof.json public.json ``` It is possible also to do the calculate witness and the prove calculation in the same command: ```sh snarkjs groth16 fullprove input.json circuit.wasm circuit_final.zkey proof.json public.json ``` ### Verify ```sh snarkjs groth16 verify verification_key.json public.json proof.json ``` ### Export Solidity Verifier ```sh snarkjs zkey export solidityverifier circuit_final.zkey verifier.sol ``` You can deploy th "Verifier" smartcontract using remix for example. In order to simulate a verification call, you can do: ```sh snarkjs zkey export soliditycalldata public.json proof.json ``` And cut and paste the resolt directlly in the "verifyProof" field in the deployed smart contract. This call will return true if the proof and the public data is valid. ## Use in node ```sh npm init npm install snarkjs ``` ```js const snarkjs = require("snarkjs"); const fs = require("fs"); async function run() { const { proof, publicSignals } = await snarkjs.groth16.fullProve({a: 10, b: 21}, "circuit.wasm", "circuit_final.zkey"); console.log("Proof: "); console.log(JSON.stringify(proof, null, 1)); const vKey = JSON.parse(fs.readFileSync("verification_key.json")); const res = await snarkjs.groth16.verify(vKey, publicSignals, proof); if (res === true) { console.log("Verification OK"); } else { console.log("Invalid proof"); } } run().then(() => { process.exit(0); }); ``` ## Use in the web load snarkjs.min.js and start using it normally. ``` cp node_modules/snarkjs/build/snarkjs.min.js . ``` ```html Snarkjs client example

Snarkjs client example

 Proof: 
 Result: 
``` ## License snarkjs is part of the iden3 project copyright 2018 0KIMS association and published with GPL-3 license. Please check the COPYING file for more details.