Inspiration

Parkinson's genes like PINK1 and PRKN are studied in fruit flies, because a fly with a broken copy of the gene loses specific clusters of dopamine neurons. In 2024 the FlyWire consortium published the complete wiring diagram of an adult fly brain: about 139,000 neurons and millions of synaptic connections. Those two bodies of knowledge rarely meet. If exactly these dopamine neurons die, which other circuits lose their input, and is that more than you would expect from losing any dopamine neurons?

Answering that in a lab takes months of imaging. We wanted a tool where a researcher picks a disease gene and, a minute later, gets a ranked and testable list of circuits to look at next, with every step traceable back to a paper.

What it does

neuroSim is a Disease Circuit Simulator.

  1. Gene to neurons. Human gene → fly ortholog (DIOPT score) → the dopamine clusters lost in published fly models of that gene → FlyWire cell types → individual neurons. Every link shows its citation and a confidence (ortholog × evidence tier × cell-type match).
  2. Simulate the loss. The seed neurons lose their output, and the engine measures, for every other neuron in the whole brain, how much of its input disappears, directly and within 3 synapses.
  3. Compare with chance. Each result is scored against 200 runs that remove the same number of random dopamine neurons, so a region only counts as vulnerable if it is hit harder than dopamine loss in general would hit it.
  4. See it. A mapping chain with the evidence, the direct targets of the lost neurons, an Overview with a one-sentence takeaway, ranked z-score bars, a network "flow by synapse" view, a 3D connectome that replays degeneration over time, and a gene-vs-gene comparison (PINK1 vs PRKN).
  5. Ask Gemma. A chat agent built on Gemma 4 calls the same tools the screens use: it reads the mapping chain, runs what-if simulations itself (the screen updates when it does), compares genes, explains why a neuron was hit, and describes what is on the 3D view. It writes a one-click run summary, and it reads uploaded papers (PDF, pasted text or DOI) to propose new evidence rows that a person approves before they seed a run.
  6. Your own disease. Parkinson's is built in, but anyone can add a disease as a small table (CSV or typed rows: gene, fly gene, affected neurons, tier) and run it through the same pipeline. An example (Huntington's, HTT → htt) is one click away.

Example result. PINK1 knockout seeds 66 dopamine neurons (PPL1, PPM1/2, PPM3, PAL and PPL2). Against 200 random sets of 66 dopamine neurons, the lateral complex (z = 7.1) and the mushroom body (z = 5.8), the fly's learning and memory centre, lose far more input than chance.

How we built it

Data. FlyWire FAFB v783 proofread connections from Zenodo (an 852 MB feather file) plus the FlyWire v3.2.0 annotations. We sum synapses per neuron pair across neuropils and then keep pairs with at least 5 synapses: 139,262 neurons, 2.7 million edges, 34.2 million synapses, 610 dopamine neurons. Kait's biology tables add the evidence rows, an expression atlas (Davis et al. 2020) and a one-hop target table covering about 1,560 FlyWire cell types.

The engine. We turn synapse counts \( W \) into input fractions, so a weight means "share of neuron \( j \)'s input that comes from neuron \( i \)":

$$A_{ji} = \frac{W_{ij}}{\sum_k W_{kj}}$$

A knockout sets a deficit \( x_0 = 1 \) on the seed neurons, which then propagates linearly for 3 hops with decay \( d = 0.5 \):

$$h_1 = A x_0, \qquad h_{k+1} = A h_k, \qquad I = h_1 + d\,h_2 + d^2 h_3$$

Impact is averaged per region, super region, cell type and super class (seeds excluded, groups under 5 neurons not ranked). Each group mean is compared with the same pipeline run on 200 size-matched random dopamine seed sets:

$$z = \frac{\bar I_{\text{obs}} - \mu_{\text{null}}}{\sigma_{\text{null}}}, \qquad p = \frac{1 + n_{\ge}}{1 + 200}$$

where \( n_{\ge} \) is the number of null runs that score at least the observed mean, with Benjamini–Hochberg FDR across groups; a group is "above chance" when \( q < 0.05 \) and \( z > 0 \). The 200 null deficit vectors are stacked as columns of one sparse matrix, so the whole baseline is three sparse matrix multiplications and takes seconds. Because the model is linear, halving the output exactly halves every impact, and the per-cluster contributions add up exactly to the total.

Degeneration and 3D. For the 3D view, a Wilson–Cowan neural mass model (neurolib) runs over the most affected regions while the drive into seed regions ramps down, and the frontend replays that time series on the connectome with Three.js and React Three Fiber.

App. FastAPI and Pydantic on the backend; Next.js 15, React 19, TypeScript, Tailwind CSS and shadcn/ui on the front, with TanStack Query, Plotly charts and Cytoscape.js networks. Frontend types are generated from the API's OpenAPI schema, and a snapshot mode replays saved responses so the demo survives a backend crash.

Agent. Gemma 4 (gemma-4-26b-a4b-it, falling back to gemma-4-31b-it) through the free Gemini API with function calling. Its tools are list_diseases, get_gene_chain, get_direct_targets, run_simulation, compare_runs, explain_neuron and describe_network_view. Its main rule: every number, neuron name and citation it says must come from a tool result in the conversation, and each tool call shows up as a chip you can open. For papers, the PDF becomes text with page markers, Gemma proposes rows with a verbatim quote, and the app checks each one (quote found word for word and on which page, cluster names mapped, duplicates, confidence) before a person can approve it.

Team. Built in 48 hours by three people: Kait (biology data: the evidence table, expression and target tables, agent rules), Mohana (simulation math, the 3D view, degeneration dynamics) and Winnie (infrastructure: data pipeline, API, Gemma agent, paper upload, custom diseases, frontend).

Challenges we ran into

  • Free tier, $0 budget. Overloaded 500/503 responses and rate limits were constant. We added retries, a fallback model, time caps per chat turn, readable error messages and a "Try again" button.
  • Mislabelled neurons. FlyWire's predicted neurotransmitter (top_nt) calls about 5,170 Kenyon cells dopaminergic. That would have put thousands of the wrong neurons into the random baseline. We use the curated known_nt label first, which gives the expected 610 dopamine neurons.
  • Names that don't match. Papers say "PPL1 cluster", "DL1" or "PPM1/2"; FlyWire says PPL101 to PPL108. We built a crosswalk from paper names to FlyWire cell types, and inferred matches (PPM3 has no FlyWire name) get a lower confidence that the UI shows.
  • 64-bit neuron IDs. FlyWire root IDs such as 720575940629024527 are larger than \( 2^{53} \), so JavaScript silently rounded them and the paths panel could not find the neuron. IDs now travel as strings end to end.
  • An honest baseline. Dopamine neurons as a class project heavily to the mushroom body, so a random-neuron baseline would make every Parkinson's gene "discover" it. Comparing against random dopamine neurons is what makes a result specific to the gene.

What we learned

  • The baseline is the result. Raw impact always points at densely connected hubs; only the comparison with chance says something about the gene.
  • A small open model is enough for a useful scientific agent when it is grounded in tools and forbidden from inventing numbers, and when a person approves anything it writes into the data.
  • Simple, linear and explainable beats realistic and opaque in 48 hours: anyone can check our worked example by hand.

What's next

Signed (excitatory vs inhibitory) propagation, the BANC connectome (brain plus nerve cord) for motor output, Alzheimer's and Huntington's built in, and a biology review of every inferred cell-type match.

neuroSim measures structural dependency in one fly connectome. Its results are hypotheses about fly circuits, not predictions of symptoms in flies or people.

Built With

Share this project:

Updates

Submission history