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.
Looking for how to change someone else’s circuit? See Contributing to a circuit you don’t own.
Contributing to a circuit you don’t own
Section titled “Contributing to a circuit you don’t own”Short answer: fork it. Forking is how contribution works on QubitHub, and a fork is a finished contribution — not a workaround for a missing step.
QubitHub has no pull requests. There is no way to propose a change back into someone else’s circuit, and no merge queue. This is a deliberate choice, not a gap waiting to be filled — see why below.
What you can and can’t do
Section titled “What you can and can’t do”| Action | On your own circuits | On someone else’s public circuit |
|---|---|---|
git clone | ✅ | ✅ (no account needed) |
| Run it | ✅ | ✅ |
git push | ✅ | ❌ 403 Write access required |
| Fork it | ✅ | ✅ |
| Push to your fork | ✅ | ✅ — it’s yours |
| Propose a change back | — | ❌ not supported |
Org-owned circuits follow the same rule with org membership: active OWNER and ADMIN members can push; everyone else forks.
The workflow
Section titled “The workflow”# 1. Fork on the circuit page, or from the CLIqubithub circuits fork alice-q/vqe-ansatz
# 2. Clone your fork and work in itgit clone https://qubithub.co/your-name/vqe-ansatz.gitcd vqe-ansatz
# 3. Push to your fork — an API key goes in the password fieldgit pushYour fork keeps the full git history of the original and carries a “forked from” link back to it, shown on your circuit’s page. That link is the provenance record: readers can see what your work is built on, and the original’s fork count reflects that someone built on it.
Credit the original in your README.md and link its URL. If the original carries a LICENSE file, follow it — absent a LICENSE, content is publicly visible but not licensed for redistribution (the same default GitHub applies).
Check the license before you fork, not after. It’s shown next to the Fork button on every circuit page. Circuits created before licensing shipped may show No license; that means nobody chose, and it carries the all-rights-reserved default — ask the owner rather than assuming. Your fork inherits the original’s license, since the LICENSE file is copied with the code. See Licensing.
If you found a bug in a circuit
Section titled “If you found a bug in a circuit”- In a
QubitHub/*circuit (the curated collection) — use the feedback widget on the site. It reaches the maintainers. - In someone else’s circuit — QubitHub does not currently carry a message to a circuit’s owner. There’s no in-app inbox and profiles don’t expose contact details. Your options are to fork and fix it in your copy, or reach the author through whatever contact they put in their own README.
Why forking instead of pull requests
Section titled “Why forking instead of pull requests”A circuit is usually a published result, not a shared codebase. When someone improves an ansatz or changes a parameter, they have produced a new result that deserves its own attribution, not a patch to yours — and merging it would quietly change the artifact a paper or blog post points at. Forking with visible lineage gives the derived work its own identity and keeps the original citable and stable.
If that stops being the right trade-off, we’ll say so and build the alternative. Until then, this is the model and it’s the whole model.
What’s in a circuit repo
Section titled “What’s in a circuit repo”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 shown on the circuit pageOptional files like params.json or circuit.qasm can be included too.
Quick start
Section titled “Quick start”If you’re already familiar with quantum circuits and just want to publish:
# 1. Scaffoldqubithub 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 --createRead on for the full walkthrough.
Step 1: Scaffold a circuit
Section titled “Step 1: Scaffold a circuit”The CLI generates a starter project with all three required files:
qubithub circuits init my-circuit --framework qiskitOptions:
| Flag | Default | Description |
|---|---|---|
--framework | qiskit | qiskit, pennylane, cirq, or openqasm3 |
--qubits | 2 | Number of qubits |
--title | Derived from name | Human-readable title |
This creates a my-circuit/ directory with templates for circuit.py, qubithub.toml, and README.md.
Step 2: Write your circuit
Section titled “Step 2: Write your circuit”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).
Qiskit
Section titled “Qiskit”"""My Circuit==========Brief description of what this circuit does.
Category: algorithmDifficulty: beginnerFramework: QiskitQubits: 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 qcPennyLane
Section titled “PennyLane”import pennylane as qmlfrom 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"), ])Step 3: Write the manifest
Section titled “Step 3: Write the manifest”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.
Tier 1: Minimal (required)
Section titled “Tier 1: Minimal (required)”schema_version = "1.0.0"
[project]name = "my-circuit"title = "My Circuit"type = "circuit"framework = "qiskit"entry_point = "circuit.py"qubits = 2These 6 fields are all you need to push.
Tier 2: Standard (recommended)
Section titled “Tier 2: Standard (recommended)”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 = 2depth = 4gates = ["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 = 1024timeout_seconds = 30Tier 3: Complete (for exemplary circuits)
Section titled “Tier 3: Complete (for exemplary circuits)”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 = 2depth = 2gates = ["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 = 1024timeout_seconds = 10
[hardware]connectivity = "any"min_qubits = 2required_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 = 1964doi = "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.
Step 4: Write the README
Section titled “Step 4: Write the README”A good README is the difference between a circuit people use and one they skip. Structure yours in four layers:
1. Intuition
Section titled “1. Intuition”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.”
2. Functional
Section titled “2. Functional”Explain what the circuit does step by step. Include a circuit diagram:
┌───┐q_0: ┤ H ├──■── └───┘┌─┴─┐q_1: ─────┤ X ├ └───┘3. Mathematical
Section titled “3. Mathematical”Show the state evolution for readers who want the math:
|00⟩ → H⊗I → (|0⟩+|1⟩)/√2 ⊗ |0⟩ → CNOT → (|00⟩+|11⟩)/√24. Implementation
Section titled “4. Implementation”Explain code-level choices: why these gates, why this ordering, what the parameters mean.
README template
Section titled “README template”# 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.Step 5: Validate locally
Section titled “Step 5: Validate locally”Before pushing, check your manifest parses correctly:
# View parsed metadata from qubithub.tomlqubithub circuits metadata my-circuit/To test your circuit on QubitHub after pushing, use execute with the remote repo name:
qubithub execute alice-q/my-circuit --shots 1024 --watchThe CLI validates your qubithub.toml automatically during push and will report any errors.
Step 6: Push to QubitHub
Section titled “Step 6: Push to QubitHub”cd my-circuit/qubithub circuits push --create -m "Initial circuit"Flags:
| Flag | Description |
|---|---|
--create | Create the circuit on QubitHub if it doesn’t exist yet |
--name | Override the circuit name (default: from qubithub.toml) |
-m | Commit 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-circuitUpdating an existing circuit
Section titled “Updating an existing circuit”Push again without --create:
qubithub circuits push -m "Add parameterized rotation"Each push creates a new version. Version history is visible on the circuit’s page.
Validation rules
Section titled “Validation rules”The CLI checks these rules before uploading:
| Rule | Requirement |
|---|---|
| Required files | circuit.py, README.md, and either qubithub.toml or metadata.json must be present locally (README.md is validated but not uploaded) |
| TOML syntax | Must be valid TOML |
| Required fields | name, title, type, framework, entry_point, qubits |
| Name format | Lowercase, hyphens only, 1-100 characters |
| Framework | qiskit, pennylane, cirq, or openqasm3 |
| Difficulty | beginner, intermediate, or advanced (if specified) |
| Gates | Use gate names from your circuit’s framework (Qiskit: CX, PennyLane/Cirq: CNOT) |
| Shots | 1-100,000 (if default_shots specified) |
| Timeout | 1-300 seconds (if timeout_seconds specified) |
| File extensions | .py, .json, .qasm, .qpy, .toml (others are skipped) |
| File size | 10 MB per file maximum |
Common validation errors
Section titled “Common validation errors”| Error | Fix |
|---|---|
Missing required field: qubits | Add qubits = N to [project] |
Invalid framework: Qiskit | Use lowercase: framework = "qiskit" |
Invalid difficulty: Beginner | Use lowercase: difficulty = "beginner" |
probability_range must have exactly 2 elements | Use [0.45, 0.55] not [0.45, 0.50, 0.55] |
Quality checklist
Section titled “Quality checklist”Use this checklist before publishing to ensure your circuit meets quality standards.
Required
Section titled “Required”- Circuit executes without errors on the specified backend
-
qubithub.tomlhas all 6 required fields -
README.mdexists and is meaningful (not just the template) - Code defines the circuit function (
create_circuit()for Qiskit/Cirq,circuit()for PennyLane)
Recommended
Section titled “Recommended”- README uses the 4-layer structure (intuition → functional → mathematical → implementation)
- README is substantial (30+ lines with meaningful content)
-
qubithub.tomlincludesdepth,gates,difficulty, andtags -
[educational]section filled out (concepts, prerequisites, learning outcomes) -
[expected_output]specifiesdominant_statesandprobability_range - Code has a module-level docstring with metadata
- Code follows framework best practices (type hints, docstrings)
Exemplary (for featured circuits)
Section titled “Exemplary (for featured circuits)”- 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
Difficulty classification
Section titled “Difficulty classification”Choose the right difficulty level for your circuit:
| Level | Qubits | Depth | Gates | Parameterized? | Examples |
|---|---|---|---|---|---|
| Beginner | 1-3 | ≤10 | Basic (H, X, Y, Z, CX, CZ) | No | Bell State, Deutsch-Jozsa, Superdense Coding |
| Intermediate | 2-10 | ≤50 | + Rotation (RX, RY, RZ) | Often | VQE, QAOA, Grover’s Search, QFT |
| Advanced | 4+ | Any | Complex sequences | Usually | Quantum Kernels, Research reproductions, Custom ansatze |
Categories
Section titled “Categories”Tag your circuit with the most specific category:
| Category | Description |
|---|---|
entanglement | Bell states, GHZ, W states |
algorithm | Grover’s, Shor’s, Deutsch-Jozsa |
chemistry | VQE, molecular simulation |
optimization | QAOA, MaxCut, TSP |
machine_learning | Quantum kernels, QNNs, classifiers |
error_correction | Bit-flip, Shor code, surface code |
communication | Teleportation, superdense coding, QKD |
transform | QFT, QPE |
cryptography | QKD protocols, post-quantum primitives |
simulation | Hamiltonian simulation, Trotterization |
utility | State preparation, oracle construction |
ansatz | Hardware-efficient, UCCSD, problem-specific |
research | Paper reproductions, novel circuits |
Example: complete beginner circuit
Section titled “Example: complete beginner circuit”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: EntanglementDifficulty: BeginnerFramework: QiskitQubits: 2Depth: 2Gates: 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 qcqubithub.toml:
schema_version = "1.0.0"
[project]name = "bell-state"title = "Bell State"type = "circuit"framework = "qiskit"entry_point = "circuit.py"qubits = 2depth = 2gates = ["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 readersREADME.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 thesame 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⟩)/√22. **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 state3. Add `qc.measure_all()` and run with 4096 shotsCLI reference
Section titled “CLI reference”| Command | Description |
|---|---|
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 REPO | Fork to your account (--name CUSTOM_NAME) |
qubithub circuits list | Browse public circuits (--framework, --tag, --sort, --limit) |
qubithub circuits info REPO | View circuit details |
qubithub circuits metadata [DIR] | Show parsed manifest (--format json|toml) |
qubithub execute REPO | Run a circuit remotely (--framework, --backend, --backend-type, --shots, --watch) |
For full CLI documentation, see CLI Quickstart.
Next steps
Section titled “Next steps”- qubithub.toml Reference — complete manifest specification
- API Reference — upload endpoints and programmatic access
- CLI Quickstart — full CLI command reference
- FAQ — common questions about circuits and execution