# fly-brain: a whole-brain fruit fly model measured across six simulators

> fly-brain turns the FlyWire connectome of the adult Drosophila brain into a leaky integrate-and-fire simulation and runs it on six backends, Brian2, Brian2CUDA, PyTorch, NEST GPU, GeNN and Brian2GeNN. The interesting part is not the model but the harness, which times each backend, checks it against Brian2 on CPU, and publishes the spike data for comparison.

**eonsystemspbc/fly-brain** — Emulation of the Drosophila Fly brain: Brian2, Brian2CUDA, PyTorch, NEST GPU, and neuromorphic chips

- Repository: https://github.com/eonsystemspbc/fly-brain
- Stars: 1,005 · Forks: 148
- Language: Python
- License: GPL-2.0
- Published: 2026-10-20 · Updated: 2026-10-20 · Language: en
- Canonical page: https://hysenlabs.com/projects/eonsystemspbc-fly-brain

## The model is a single spiking regime over a real connectome

The scope is narrow and deliberate. fly-brain is a whole-brain leaky integrate-and-fire model of the adult fruit fly, built from the FlyWire connectome, which the documentation describes as roughly 138 thousand neurons and about five million synapses. The model follows the paper by Shiu and colleagues on a leaky integrate-and-fire computational model based on the connectome of the entire adult brain, and the later Nature version of that work reported 91 percent prediction accuracy against experimental Drosophila data.

The user-facing operations are only two. Neurons can be activated at a fixed frequency to model optogenetic activation, which triggers Poisson spiking in the target neurons, and two sets of neurons with distinct frequencies can be defined in one run. A second operation silences a set of neurons to model optogenetic silencing, and the implementation of that is blunt: it sets all synaptic connections to and from those neurons to zero. The output of a run is the spike times and rates of all affected neurons.

This is a spiking model with one neuron type and one synaptic rule. Anyone expecting plasticity, inhibition dynamics or multiple cell classes should look elsewhere. The value of the project is that the network is a measured connectome rather than a generated one, and that the simulation of it can be run on hardware the authors did not write.

## main.py is a benchmark launcher, not a simulation script

The entry point parses command line arguments and then hands over to a central orchestrator, code/benchmark.py, which dispatches to framework specific runners: run_brian2_cuda.py, run_pytorch.py, run_nestgpu.py and run_genn.py, with run_brian2_genn.py as an optional extra. In practice you drive everything through main.py.

A plain invocation runs the five main environment frameworks with the default durations and trial counts:

```bash
python main.py
```

The grid can be set explicitly, and a single framework can be isolated, which is how you debug a backend before it goes into a full run:

```bash
python main.py --t_run 0.1 1 10 --n_run 1
```

```bash
python main.py --nestgpu --t_run 1 --n_run 1
```

```bash
python main.py --genn --t_run 1 --n_run 1
```

```bash
python main.py --brian2genn --t_run 1 --n_run 1
```

Frameworks can also be combined in a single invocation, and the paper mode runs the five round benchmark suite over a fixed grid of durations and trial counts with the label nature_2026_07:

```bash
python main.py --brian2-cpu --pytorch --t_run 0.1 1 --n_run 1 4 8 16 32
```

```bash
python main.py --paper --run-label nature_2026_07
```

```bash
python main.py --brian2genn --paper --run-label nature_2026_07
```

## Setup time and simulation time are kept apart

The measurement design is where this project is more careful than most simulation benchmarks, and it is the detail to read before comparing any numbers.

Results are written incrementally to data/benchmark-results.csv as each benchmark completes, so a long run does not lose everything if it is interrupted. The CSV keeps setup time, which covers loading and compilation, separate from simulation time, which the documentation calls the always-on cost. Those two numbers answer different questions. A backend that compiles for two minutes and then simulates faster may still be the wrong choice for a batch of thousands of short runs, and a CSV that conflates the two would hide that.

Spike timing exports are written to parquet files outside the timed simulation section, explicitly so that file input and output does not contaminate the simulation measurement. GeNN gets a special case: it flushes bounded on-device spike recording windows during long batched runs, and that transfer time is tracked as result collection rather than as simulation time.

Repeated paper runs keep the original rows and append new ones keyed by run_label and round, and the path of the matching spike file is recorded in a spike_path column. The canonical timing column in new exports is time_ms, alongside trial, neuron_index, flywire_id and exp_name, and the older t column is retained so that existing analysis scripts keep working.

## Brian2 on CPU is the reference every backend is scored against

Brian2 running on the CPU is the ground truth for neural accuracy in this project, because it implements the canonical leaky integrate-and-fire model from the Nature paper. Every backend also saves per-neuron spike trains under data/results, and a comparison script measures how closely the others reproduce Brian2's output.

```bash
python code/compare_ground_truth.py
```

```bash
python code/compare_ground_truth.py --t_run 10 --n_run 4
```

```bash
python code/compare_ground_truth.py --run-label nature_2026_07 --round 1
```

That script computes three things: active-neuron overlap using the Jaccard index, per-neuron firing-rate correlation, and spike-count ratios. Results are written in structured form to data/ground-truth-comparison.json.

For all-framework pairwise comparison, including firing-rate parity rows and spike-time matches inside a tolerance window, there is a second script:

```bash
python code/compare_spike_outputs.py \
  --run-label nature_2026_07 \
  --round 1 \
  --output-dir data/results/nature_2026_07/comparisons
```

It produces pairwise_summary.csv, pairwise_summary.json, parity_rates.csv and missing_inputs.json, with one row per framework pair and per duration and trial combination. A third script compares one backend against Brian2 CPU across all five labelled rounds:

```bash
python code/compare_backend_to_brian2.py \
  --run-label nature_2026_07 \
  --backend brian2genn \
  --output-dir data/results/nature_2026_07/comparisons
```

Its optional include-timing flag enables greedy spike-time matching, which the documentation recommends only for smaller targeted checks where the matching is both scientifically useful and computationally reasonable.

## The spike data is deliberately outside Git

The published bundle is a real dataset, and its storage is a design decision worth copying. The full nature_2026_07 spike parquet bundle contains 600 files, which is 20 grid points for each of six frameworks across five rounds. A no_io subfolder holds a one round, 120 row timing dataset collected with spike probing and output switched off, so it contains no spike parquet files at all and can be used to study timing without the data volume.

Because the bundle is too large for ordinary Git tracking, the parquet files are intentionally gitignored. What stays in the repository is the metadata: a manifest.csv and a checksums.sha256 file, with the full bundle held on Google Drive. Anyone who downloads the folder can verify it locally:

```bash
cd data/results/nature_2026_07
sha256sum -c checksums.sha256
```

A manifest plus checksums, a download location and a verification command is a better answer to the reproducibility question than a large binary in a repository, and it is the pattern to expect from other data-producing projects.

The per-file format is simple: one row per spike, with the timing column and the identifiers that let you trace a spike back to a neuron and a trial. Reading those parquet files with pandas or pyarrow is all that stands between a download and an analysis, and the legacy t column means older analysis scripts do not need to be rewritten.

## Two conda environments, one dependency conflict

Installation is handled with two conda environment files, and the reason for the split is documented rather than incidental.

```bash
conda env create -f environment.yml
conda activate brain-fly
```

That environment covers the Brian2, Brian2CUDA, PyTorch, NEST GPU and GeNN backends, including CUDA enabled PyTorch and PyGeNN. On Ubuntu or WSL, the source build of PyGeNN additionally needs the system pkg-config binary and libffi headers:

```bash
sudo apt-get install -y pkg-config libffi-dev
```

The optional sixth backend, Brian2GeNN, lives in a separate conda environment, and the reason is a version conflict stated in the documentation: Brian2GeNN 1.7.0 pins Brian2 below 2.6, while Brian2CUDA uses Brian2 2.8.0. The two cannot coexist in one environment, so run_brian2_genn.py is invoked from brain-fly-brian2genn instead of brain-fly. The repository root holds both environment files, environment.yml and environment-brian2genn.yml.

That split is a small operational tax and a useful warning. It means a run that mixes frameworks, in particular the paper mode with the Brian2GeNN backend added, crosses an environment boundary, and the numbers you compare span two different Brian2 versions. When you add the sixth backend to a paper run, record that you did, because a parity row against a reference computed on a different Brian2 release is not a like-for-like comparison.

## Conclusion

fly-brain is for computational neuroscientists who need a reproducible cross-backend comparison on a real connectome rather than a toy network, and the benchmark scaffolding around the model is as reusable as the model itself. It is not a tool for training networks, and it is not a substitute for the original Shiu and colleagues work, which the project cites rather than replaces. Before you rely on a run, check that the Brian2 version in your environment matches the one the reference numbers came from, run the checksum verification on any downloaded bundle, and read the ground truth comparison JSON for your configuration before treating a parity row as a pass.

## FAQ

### What is fly-brain and how large is the network it simulates?

It is a whole-brain leaky integrate-and-fire model of the adult Drosophila fruit fly built from the FlyWire connectome, described as roughly 138 thousand neurons and about five million synapses. The project follows the computational model published by Shiu and colleagues.

### How do I install the environments needed to run fly-brain?

Create the main conda environment with conda env create -f environment.yml and activate it with conda activate brain-fly. The optional Brian2GeNN backend needs a second environment because Brian2GeNN 1.7.0 pins Brian2 below 2.6 while Brian2CUDA uses Brian2 2.8.0.

### How do I check whether a backend reproduces the reference simulation?

Run python code/compare_ground_truth.py, optionally with --t_run and --n_run for longer averaged runs. It computes active-neuron overlap by the Jaccard index, per-neuron firing-rate correlation and spike-count ratios against Brian2 on CPU, and writes the results to data/ground-truth-comparison.json.

### Where are the published spike results stored, and how do I verify them?

The full bundle of 600 spike parquet files is too large for Git tracking, so the parquet files are gitignored and the data is held on Google Drive, while manifest.csv and checksums.sha256 stay in the repository. After downloading the folder into data/results/nature_2026_07, run sha256sum -c checksums.sha256 to verify it.

## Sources

- [eonsystemspbc/fly-brain on GitHub](https://github.com/eonsystemspbc/fly-brain)
- [Issues](https://github.com/eonsystemspbc/fly-brain/issues)
- [License: GPL-2.0](https://github.com/eonsystemspbc/fly-brain/blob/main/LICENSE)
- [README](https://github.com/eonsystemspbc/fly-brain/blob/main/README.md)

---

Hysen Labs editorial analysis, written from the project's own repository and release notes. Cite the canonical page: https://hysenlabs.com/projects/eonsystemspbc-fly-brain
