Skip to content

Contributing Circuits

This guide walks you through creating, validating, and publishing a quantum circuit on QubitHub. By the end, your circuit will be browsable, forkable, and executable by anyone on the platform.

Every circuit on QubitHub is a small repository with three files:

my-circuit/
├── circuit.py # Your quantum circuit code
├── qubithub.toml # Manifest describing the circuit
└── README.md # Documentation (used locally; platform generates from description)

Optional files like params.json or circuit.qasm can be included too.


If you’re already familiar with quantum circuits and just want to publish:

Terminal window
# 1. Scaffold
qubithub circuits init my-circuit --framework qiskit
# 2. Edit circuit.py, qubithub.toml, README.md
# 3. Push (creates the circuit if it doesn't exist)
cd my-circuit/
qubithub circuits push --create

Read on for the full walkthrough.


The CLI generates a starter project with all three required files:

Terminal window
qubithub circuits init my-circuit --framework qiskit

Options:

FlagDefaultDescription
--frameworkqiskitqiskit, pennylane, cirq, or openqasm3
--qubits2Number of qubits
--titleDerived from nameHuman-readable title

This creates a my-circuit/ directory with templates for circuit.py, qubithub.toml, and README.md.


Your circuit.py should define a function that creates and returns a quantum circuit. The convention is create_circuit() for Qiskit and Cirq, and circuit() for PennyLane (matching each framework’s idiom).

"""
My Circuit
==========
Brief description of what this circuit does.
Category: algorithm
Difficulty: beginner
Framework: Qiskit
Qubits: 2
"""
from qiskit import QuantumCircuit
def create_circuit() -> QuantumCircuit:
"""Create and return the quantum circuit."""
qc = QuantumCircuit(2)
qc.h(0)
qc.cx(0, 1)
return qc
import pennylane as qml
from pennylane import numpy as np
dev = qml.device("default.qubit", wires=2)
@qml.qnode(dev)
def circuit():
"""Build and return the quantum circuit."""
qml.Hadamard(wires=0)
qml.CNOT(wires=[0, 1])
return qml.counts(wires=range(2))
import cirq
def create_circuit() -> cirq.Circuit:
"""Create and return the quantum circuit."""
q0, q1 = cirq.LineQubit.range(2)
return cirq.Circuit([
cirq.H(q0),
cirq.CNOT(q0, q1),
cirq.measure(q0, q1, key="result"),
])

The qubithub.toml manifest is the single source of truth for your circuit’s metadata. It uses a progressive complexity model — start minimal, add detail as needed.

schema_version = "1.0.0"
[project]
name = "my-circuit"
title = "My Circuit"
type = "circuit"
framework = "qiskit"
entry_point = "circuit.py"
qubits = 2

These 6 fields are all you need to push.

Add execution defaults, difficulty, and tags for discoverability:

schema_version = "1.0.0"
[project]
name = "my-circuit"
title = "My Circuit"
type = "circuit"
framework = "qiskit"
entry_point = "circuit.py"
qubits = 2
depth = 4
gates = ["H", "CX", "RY"]
category = "algorithm"
difficulty = "intermediate"
tags = ["variational", "optimization"]
description = "A brief description of what this circuit does and why."
[execution]
default_backend = "aer_simulator"
default_shots = 1024
timeout_seconds = 30

Add educational content, expected output, hardware notes, and references:

schema_version = "1.0.0"
[project]
name = "bell-state"
title = "Bell State"
type = "circuit"
framework = "qiskit"
framework_version = "1.3.0"
entry_point = "circuit.py"
qubits = 2
depth = 2
gates = ["H", "CX"]
category = "entanglement"
difficulty = "beginner"
tags = ["entanglement", "epr", "foundational", "bell-pair"]
description = """
Creates the Bell state |Phi+> = (|00> + |11>)/sqrt(2), the simplest \
demonstration of quantum entanglement.\
"""
[execution]
default_backend = "aer_simulator"
default_shots = 1024
timeout_seconds = 10
[hardware]
connectivity = "any"
min_qubits = 2
required_gates = ["h", "cx"]
[educational]
level = "beginner"
concepts = ["entanglement", "superposition", "measurement"]
prerequisites = []
learning_outcomes = [
"Create a maximally entangled two-qubit state",
"Understand correlated measurement outcomes",
]
estimated_time = "10 minutes"
next_circuits = ["ghz-state", "quantum-teleportation"]
[expected_output]
dominant_states = ["00", "11"]
probability_range = [0.45, 0.55]
# Note: forbidden_states is not part of the validated spec but is
# conventionally included as documentation for readers
[[references.papers]]
title = "On the Einstein Podolsky Rosen Paradox"
authors = ["Bell, J.S."]
year = 1964
doi = "10.1103/PhysicsPhysiqueFizika.1.195"
[[references.textbooks]]
title = "Quantum Computation and Quantum Information"
authors = ["Nielsen, M.A.", "Chuang, I.L."]
section = "Section 1.3.6"

For the complete field reference, see qubithub.toml Reference.


A good README is the difference between a circuit people use and one they skip. Structure yours in four layers:

Start with a plain-English explanation. Use analogies. No math yet.

“The Bell state is like flipping two magic coins that always land the same way — both heads or both tails, never one of each.”

Explain what the circuit does step by step. Include a circuit diagram:

┌───┐
q_0: ┤ H ├──■──
└───┘┌─┴─┐
q_1: ─────┤ X ├
└───┘

Show the state evolution for readers who want the math:

|00⟩ → H⊗I → (|0⟩+|1⟩)/√2 ⊗ |0⟩ → CNOT → (|00⟩+|11⟩)/√2

Explain code-level choices: why these gates, why this ordering, what the parameters mean.

# My Circuit
Brief description (1-2 sentences).
| Property | Value |
|----------|-------|
| Level | Beginner / Intermediate / Advanced |
| Framework | Qiskit |
| Qubits | 2 |
| Depth | 4 |
| Time | ~10 minutes |
## What You'll Learn
- Learning outcome 1
- Learning outcome 2
## Background
Plain-English explanation of the algorithm or concept.
## Circuit
Step-by-step walkthrough with circuit diagram.
## Expected Output
| State | Probability |
|-------|------------|
| `00` | ~50% |
| `11` | ~50% |
## Try It Yourself
1. Variation to try (e.g., "Change the initial state to |01⟩")
2. Extension (e.g., "Add a third qubit to make a GHZ state")
## References
- Author (Year). "Title." Journal. DOI.

Before pushing, check your manifest parses correctly:

Terminal window
# View parsed metadata from qubithub.toml
qubithub circuits metadata my-circuit/

To test your circuit on QubitHub after pushing, use execute with the remote repo name:

Terminal window
qubithub execute alice-q/my-circuit --shots 1024 --watch

The CLI validates your qubithub.toml automatically during push and will report any errors.


Terminal window
cd my-circuit/
qubithub circuits push --create -m "Initial circuit"

Flags:

FlagDescription
--createCreate the circuit on QubitHub if it doesn’t exist yet
--nameOverride the circuit name (default: from qubithub.toml)
-mCommit message for this version

The CLI validates your files, then uploads them. You’ll see each file’s upload status:

Validating my-circuit/... ✓
Uploading circuit.py... ✓ (v1)
Uploading qubithub.toml... ✓ (v1)
Skipping README.md (not a pushable extension)
Circuit published: https://qubithub.co/alice-q/my-circuit

Push again without --create:

Terminal window
qubithub circuits push -m "Add parameterized rotation"

Each push creates a new version. Version history is visible on the circuit’s page.


The CLI checks these rules before uploading:

RuleRequirement
Required filescircuit.py, README.md, and either qubithub.toml or metadata.json must be present locally (README.md is validated but not uploaded)
TOML syntaxMust be valid TOML
Required fieldsname, title, type, framework, entry_point, qubits
Name formatLowercase, hyphens only, 1-100 characters
Frameworkqiskit, pennylane, cirq, or openqasm3
Difficultybeginner, intermediate, or advanced (if specified)
GatesUse gate names from your circuit’s framework (Qiskit: CX, PennyLane/Cirq: CNOT)
Shots1-100,000 (if default_shots specified)
Timeout1-300 seconds (if timeout_seconds specified)
File extensions.py, .json, .qasm, .qpy, .toml (others are skipped)
File size10 MB per file maximum
ErrorFix
Missing required field: qubitsAdd qubits = N to [project]
Invalid framework: QiskitUse lowercase: framework = "qiskit"
Invalid difficulty: BeginnerUse lowercase: difficulty = "beginner"
probability_range must have exactly 2 elementsUse [0.45, 0.55] not [0.45, 0.50, 0.55]

Use this checklist before publishing to ensure your circuit meets quality standards.

  • Circuit executes without errors on the specified backend
  • qubithub.toml has all 6 required fields
  • README.md exists and is meaningful (not just the template)
  • Code defines the circuit function (create_circuit() for Qiskit/Cirq, circuit() for PennyLane)
  • README uses the 4-layer structure (intuition → functional → mathematical → implementation)
  • README is substantial (30+ lines with meaningful content)
  • qubithub.toml includes depth, gates, difficulty, and tags
  • [educational] section filled out (concepts, prerequisites, learning outcomes)
  • [expected_output] specifies dominant_states and probability_range
  • Code has a module-level docstring with metadata
  • Code follows framework best practices (type hints, docstrings)
  • Full [references] section with papers and/or textbooks
  • “Try It Yourself” exercises in the README
  • [hardware] section with connectivity and gate requirements
  • Multiple [implementations] across frameworks
  • [reproducibility] section with seed and transpilation settings

Choose the right difficulty level for your circuit:

LevelQubitsDepthGatesParameterized?Examples
Beginner1-3≤10Basic (H, X, Y, Z, CX, CZ)NoBell State, Deutsch-Jozsa, Superdense Coding
Intermediate2-10≤50+ Rotation (RX, RY, RZ)OftenVQE, QAOA, Grover’s Search, QFT
Advanced4+AnyComplex sequencesUsuallyQuantum Kernels, Research reproductions, Custom ansatze

Tag your circuit with the most specific category:

CategoryDescription
entanglementBell states, GHZ, W states
algorithmGrover’s, Shor’s, Deutsch-Jozsa
chemistryVQE, molecular simulation
optimizationQAOA, MaxCut, TSP
machine_learningQuantum kernels, QNNs, classifiers
error_correctionBit-flip, Shor code, surface code
communicationTeleportation, superdense coding, QKD
transformQFT, QPE
cryptographyQKD protocols, post-quantum primitives
simulationHamiltonian simulation, Trotterization
utilityState preparation, oracle construction
ansatzHardware-efficient, UCCSD, problem-specific
researchPaper reproductions, novel circuits

Here’s the Bell State circuit as a complete example of all three files working together.

circuit.py:

"""
Bell State Circuit
==================
Creates the maximally entangled Bell state |Phi+> = (|00> + |11>)/sqrt(2).
Category: Entanglement
Difficulty: Beginner
Framework: Qiskit
Qubits: 2
Depth: 2
Gates: H, CX
"""
from qiskit import QuantumCircuit
def create_circuit() -> QuantumCircuit:
"""Create the Bell state |Phi+>."""
qc = QuantumCircuit(2)
qc.h(0) # Put qubit 0 in superposition
qc.cx(0, 1) # Entangle qubit 0 and qubit 1
return qc

qubithub.toml:

schema_version = "1.0.0"
[project]
name = "bell-state"
title = "Bell State"
type = "circuit"
framework = "qiskit"
entry_point = "circuit.py"
qubits = 2
depth = 2
gates = ["H", "CX"]
category = "entanglement"
difficulty = "beginner"
tags = ["entanglement", "epr", "foundational"]
description = "Creates the Bell state |Phi+>, the simplest demonstration of quantum entanglement."
[execution]
default_backend = "aer_simulator"
default_shots = 1024
[expected_output]
dominant_states = ["00", "11"]
probability_range = [0.45, 0.55]
# Note: forbidden_states is not part of the validated spec but is
# conventionally included as documentation for readers

README.md (abbreviated):

# Bell State
Creates the maximally entangled Bell state |Phi+⟩ = (|00⟩ + |11⟩)/√2.
| Property | Value |
|----------|-------|
| Level | Beginner |
| Framework | Qiskit |
| Qubits | 2 |
| Time | ~10 minutes |
## What You'll Learn
- Create a maximally entangled two-qubit state using H and CNOT gates
- Understand why entangled qubits always produce correlated measurements
## Background
The Bell state is like flipping two magic coins — they always land the
same way. Both heads or both tails, never one of each.
## Circuit
┌───┐
q_0: ┤ H ├──■──
└───┘┌─┴─┐
q_1: ─────┤ X ├
└───┘
1. **H gate** on qubit 0: creates superposition (|0⟩+|1⟩)/√2
2. **CX gate**: entangles qubit 0 and qubit 1
## Expected Output
| State | Probability |
|-------|------------|
| `00` | ~50% |
| `11` | ~50% |
| `01` | ~0% (forbidden) |
| `10` | ~0% (forbidden) |
## Try It Yourself
1. Change `qc.h(0)` to `qc.x(0); qc.h(0)` — which Bell state do you get?
2. Add a third qubit to create a GHZ state
3. Add `qc.measure_all()` and run with 4096 shots

CommandDescription
qubithub circuits init NAME [DIR]Scaffold a new circuit (--framework, --qubits, --title)
qubithub circuits push [DIR]Validate and upload (--create, --name, -m MESSAGE)
qubithub circuits clone REPO [DIR]Download a circuit locally
qubithub circuits fork REPOFork to your account (--name CUSTOM_NAME)
qubithub circuits listBrowse public circuits (--framework, --tag, --sort, --limit)
qubithub circuits info REPOView circuit details
qubithub circuits metadata [DIR]Show parsed manifest (--format json|toml)
qubithub execute REPORun a circuit remotely (--framework, --backend, --backend-type, --shots, --watch)

For full CLI documentation, see CLI Quickstart.