groth16-circuit

star 1

Create Circom circuits for zkVerify Groth16 proofs with snarkjs. Use when the user wants to create a ZK circuit, write circom code, or start a new zero-knowledge proof project.

HorizenLabs By HorizenLabs schedule Updated 2/3/2026

name: groth16-circuit description: Create Circom circuits for zkVerify Groth16 proofs with snarkjs. Use when the user wants to create a ZK circuit, write circom code, or start a new zero-knowledge proof project. argument-hint: [circuit-type]

Create Circom Circuit for zkVerify

Help the user create a Circom circuit that will be used with zkVerify for proof verification.

Arguments

If invoked with an argument (e.g., /groth16-circuit hash-preimage), use it as the circuit type and skip asking what to prove.

Argument Circuit Type
hash-preimage Prove knowledge of hash preimage
range-proof Prove value is within range
merkle-proof Prove membership in Merkle tree
age-check Prove age meets minimum
(custom) Use as circuit description

If no argument provided, ask the user what they want to prove.

Pre-flight Check

Before creating the circuit, verify Node.js is available:

node --version
Check If Missing
node Direct user to install Node.js

If Node.js is missing, stop and help user install it first.

Note: Circom is NOT required for this skill. You can create .circom files without having circom installed. Circom will be automatically installed when the user runs /groth16-compile.

Scope

This skill is specifically for:

  • Language: Circom
  • Prover: snarkjs
  • Proof System: Groth16
  • Verifier: zkVerify

This skill is NOT for:

  • Groth16 proofs from other libraries (arkworks/Rust, gnark/Go)
  • Other proof systems (Ultraplonk, RISC0, SP1, Plonky2, etc.)
  • Other circuit languages (Noir, Rust zkVM code, etc.)

If the user asks for a different proof system or language, inform them this skill only covers Circom/Groth16 and suggest they check zkVerify documentation for other proof systems.

Instructions

  1. Ask about the circuit purpose if not specified:

    • What computation should be proven?
    • What are the private inputs (hidden)?
    • What are the public inputs (revealed)?
  2. Create the circuit file in circuits/ directory

  3. Analyze input dependencies to determine if a helper script is needed

  4. Create valid inputs - either directly or via helper script

Critical: Analyzing Input Dependencies

Before creating the input file, analyze the circuit's inputs:

Question: Are any inputs computed from other inputs?

Answer Action
YES Create a helper script in scripts/ to compute dependent values
NO Create inputs/*.json directly with valid example values

Examples of DEPENDENT Inputs (Need Helper Script)

  • Hash verification: hash = Poseidon(preimage) - hash depends on preimage
  • Merkle proofs: root = hash(hash(...leaves)) - root depends on leaves
  • Commitments: commitment = hash(secret, nullifier) - commitment depends on secrets

Examples of INDEPENDENT Inputs (No Script Needed)

  • Range proofs: value=50, min=0, max=100 - just numbers
  • Arithmetic: a=10, b=20, expectedSum=30 - just ensure math is correct
  • Age verification: age=25, minAge=18 - independent values

File Structure

circuits/
├── <circuit_name>.circom           # The circuit

scripts/
├── compute_<name>_input.ts         # Helper script (only if inputs are dependent)

inputs/
└── <circuit_name>_input.json       # Valid input file

Important Circom Rules

  1. All signals must be constrained - Every signal must appear in at least one constraint
  2. Use <== for assignment + constraint - Combines <-- and ===
  3. Use <-- only when necessary - Must add separate constraint with ===
  4. Declare public inputs in main - component main {public [input1, input2]} = Template();
  5. Use strings for large numbers in JSON to avoid precision issues

CRITICAL: zkVerify Public Signal Limit

zkVerify has a limit of 64 total public signals (inputs + outputs) for Groth16 proofs submitted via the Kurier API.

Total Public Signals Result
≤ 64 Works
> 64 FAILS (optimisticVerify: failed)

This limit is NOT documented by zkVerify. Proofs with >64 public signals will verify locally with snarkjs but fail on zkVerify with no useful error message.

How to Count Public Signals

Total Public Signals = Public Inputs + Public Outputs

Example:

  • component main {public [a, b, c]} = MyCircuit(); with 1 output = 4 total signals

If Your Circuit Exceeds 64 Public Signals

Use hash commitments to reduce public inputs:

Instead of:

// BAD: 81 public inputs (puzzle grid)
signal input puzzle[9][9];  // All public

Do this:

// GOOD: 1 public input (hash of puzzle)
signal input puzzleHash;           // Public: just the hash
signal input puzzle[9][9];         // Private: actual puzzle
// Prove: Poseidon(puzzle) === puzzleHash

Circuits That Often Exceed the Limit

Use Case Naive Approach Problem Solution
Sudoku 81 public inputs (puzzle) 81 > 64 Hash the puzzle
Voting N public voter IDs N could be large Merkle tree of voters
Batch proofs Many public values Sum exceeds 64 Aggregate with hashes

After Creating Circuit

  1. If helper script was created: Run it to generate valid inputs

    npm install circomlibjs ts-node typescript @types/node
    npx ts-node scripts/compute_<name>_input.ts <args>
    
  2. Install circomlib if circuit uses library components:

    npm install circomlib
    
  3. Next step: Run /groth16-compile to compile the circuit

Checklist

  • Circuit file created in circuits/
  • Analyzed input dependencies
  • Helper script created (if inputs are dependent)
  • Input file has VALID values (not placeholders)
  • Reminded user of next steps

Additional Resources

For detailed examples and reference material, see:

  • examples.md - Complete circuit examples with helper scripts (hash preimage, range proof, Merkle proof, age check)
  • reference.md - Circom syntax reference, circomlib components, and common errors
Install via CLI
npx skills add https://github.com/HorizenLabs/hl-claude-marketplace --skill groth16-circuit
Repository Details
star Stars 1
call_split Forks 0
navigation Branch main
article Path SKILL.md
More from Creator