Skip to main content

Drop-in Rust acceleration of scVelo for single-cell RNA velocity.

Project description

scvelo-rs

CI Wheels PyPI Python versions License Downloads

A Rust + PyO3 port of scVelo.

Rust implementation of heavy-weight bottlenecks like recover_dynamics & velocity_graph - bit-exact to the original scVelo.

Highlights

  • 30–40× faster than the original scVelo on representative atlases (5k–100k cells), and ~2–4× lower peak memory. See Benchmarks.
  • Bit-exact equivalence to scVelo on 99.9% of genes — the residual drift is at f64 ULP scale (per-gene Pearson r = 1.0000 across fit_alpha, fit_beta, fit_gamma, fit_t_).
  • Drop-in: import scvelo_rs.patch and every downstream call to scv.tl.{recover_dynamics, velocity, velocity_graph} routes to Rust. Or import scvelo_rs as scv for the full API.
  • Cross-platform wheels for Linux x86_64/aarch64, macOS arm64, Windows x86_64. Single abi3-py310 wheel covers Python 3.10–3.13.
  • CPU-only. Runs anywhere Python runs — laptop, HPC, Docker, ARM. No CUDA. No Numba. No JIT warmup.
# Option 1 — drop-in import.
import scvelo_rs as scv

adata = scv.datasets.pancreas()
scv.pp.filter_and_normalize(adata); scv.pp.moments(adata)
scv.tl.recover_dynamics(adata)            # ~35× faster than the original scvelo
scv.tl.velocity(adata, mode="dynamical")
scv.tl.velocity_graph(adata)
scv.pl.velocity_embedding_stream(adata, basis="umap")
# Option 2 — monkey-patch. Keep your existing `import scvelo as scv`;
# only the three patched hot paths get the Rust kernel.
import scvelo as scv
import scvelo_rs.patch  # noqa: F401   # patches scv.tl.{recover_dynamics, velocity, velocity_graph}

scv.tl.recover_dynamics(adata)         # bit-exact, no other code change needed

Installation

pip install scvelo-rs

scVelo and scanpy are runtime dependencies (used for plotting, dataset I/O, DPT/PAGA pass-through). They are pulled in automatically.

Quick start

Three usage patterns, in order of how invasive the migration is.

1. Monkey-patch (zero code changes)

Add one line at the top of your existing scVelo script:

import scvelo as scv
import scvelo_rs.patch  # noqa: F401   # swaps scv.tl.{recover_dynamics, velocity, velocity_graph}

adata = scv.datasets.pancreas()
scv.pp.filter_and_normalize(adata)
scv.pp.moments(adata)
scv.tl.recover_dynamics(adata)         # now Rust-backed
scv.tl.velocity(adata, mode="dynamical")
scv.tl.velocity_graph(adata)

Originals are preserved at scv.tl.<name>_original for A/B comparison.

2. Drop-in import

Replace import scvelo as scv with import scvelo_rs as scv. The scvelo_rs.{tl, pp, pl, datasets} namespaces expose scVelo's full public API; the hot loops route through Rust, everything else passes through scVelo unchanged.

import scvelo_rs as scv

adata = scv.datasets.pancreas()
scv.pp.filter_and_normalize(adata)
scv.pp.moments(adata)
scv.tl.recover_dynamics(adata)
scv.tl.velocity(adata, mode="dynamical")
scv.tl.velocity_graph(adata)
scv.pl.velocity_embedding_stream(adata, basis="umap")

3. Direct call

import scvelo_rs
scvelo_rs.recover_dynamics(adata)      # same signature as scv.tl.recover_dynamics

See examples/ for runnable end-to-end scripts.

Benchmarks

Measured locally on standard datasets.

Wall time

benchmark cells genes scvelo scvelo-rs speedup
recover_dynamics (5k cells, 50 genes) 5,000 50 43.24 s 1.03 s 42.0×
recover_dynamics + velocity (20k, 100) 20,000 100 380.02 s 10.09 s 37.7×
recover_dynamics + velocity + velocity_graph (20k, 100) 20,000 100 389.54 s 10.79 s 36.1×
full pipeline (50k, 100) 50,000 100 1202.26 s 34.35 s 35.0×
recover_dynamics (100k, 30) 100,000 30 671.65 s 22.85 s 29.4×

Peak memory

benchmark cells genes scvelo scvelo-rs saved
recover_dynamics (5k, 50) 5,000 50 108.4 MB 35.0 MB 73 MB
velocity_graph (20k, 100) 20,000 100 1727.5 MB 626.5 MB 1,101 MB
steady-state layers (5k, 200) 5,000 200 252.1 MB 66.2 MB 186 MB
full pipeline (50k, 100) 50,000 100 4831.6 MB 1879.3 MB 2,952 MB
recover_dynamics + velocity_graph (100k, 30) 100,000 30 7074.4 MB 2794.9 MB 4,280 MB

Build from source

Requires Rust 1.75+ and Python 3.10+.

git clone https://github.com/ilaykav/scvelo-rs
cd scvelo-rs
python -m venv .venv && source .venv/bin/activate   # or .venv\Scripts\activate on Windows
pip install -e ".[dev]"
maturin develop --release
pytest tests/unit tests/integration

The Rust crates nalgebra (SVD for PCA) and hnsw_rs (HNSW for KNN) are pure-Rust — no OpenBLAS, no vcpkg, no system C libraries. Cross-platform builds work out of the box.

Documentation

A full Sphinx site (Quick start, Installation, Migration from scVelo, Architecture, Numerical parity, Benchmarks) is in the works for v0.2. Until then, this README, the CHANGELOG, and the runnable scripts under examples/ and notebooks/ cover the same ground.

Contributing

Bug reports, PRs, and benchmark contributions welcome. See CONTRIBUTING.md — the short version is:

git clone https://github.com/ilaykav/scvelo-rs
cd scvelo-rs
pip install -e ".[dev]"
maturin develop --release
pytest tests/unit tests/integration

Bit-exact equivalence to scVelo is the contract for every Rust-backed function. PRs that move per-gene drift above 1e-9 need a documented reason.

License

Released under BSD-3-Clause. The Rust kernels are independent reimplementations of theislab's published algorithms — credit for the underlying methods belongs to La Manno et al. 2018 (RNA velocity, Nature, doi:10.1038/s41586-018-0414-6) and Bergen et al. 2020 (scVelo, Nat Biotechnol, doi:10.1038/s41587-020-0591-3).

Citing this work

scvelo-rs is a faithful port: the method is Bergen et al. 2020, the implementation is this repository. Always cite the original scVelo paper as the primary reference; cite the version of scvelo-rs you used as a software dependency (pip show scvelo-rs or scvelo_rs.__version__).

@article{bergen2020generalizing,
  title   = {Generalizing RNA velocity to transient cell states through dynamical modeling},
  author  = {Bergen, Volker and Lange, Marius and Peidli, Stefan and
             Wolf, F. Alexander and Theis, Fabian J.},
  journal = {Nature Biotechnology},
  year    = {2020},
  doi     = {10.1038/s41587-020-0591-3}
}

@software{scvelo_rs,
  title   = {scvelo-rs: a Rust acceleration of scVelo's dynamical model},
  author  = {Kavitzky, Ilay},
  year    = {2026},
  version = {0.1.0},
  url     = {https://github.com/ilaykav/scvelo-rs},
  note    = {Rust + PyO3 port of Bergen et al. 2020 (doi:10.1038/s41587-020-0591-3)}
}

Authored and maintained by Ilay Kavitzky. Contribution guidelines are in CONTRIBUTING.md.

Reporting bugs and feature requests

Open an issue at github.com/ilaykav/scvelo-rs/issues.

Bug reports — include:

  • scvelo-rs version (pip show scvelo-rs)
  • OS and Python version
  • A minimum reproducer (a small .h5ad slice + the calls that fail is usually enough)
  • What you expected vs what you got

Parity issues (a fitted parameter or velocity vector differs from the original scvelo): include both runs' values for the affected gene/cell, the relative drift, and which fixture you ran on.

Feature requests — describe the workflow you can't do today, not just the API you'd like. Atlas-scale parity reports are especially welcome.

For anything else, direct mail: ilay.kavitzky@gmail.com.

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

scvelo_rs-0.1.3.tar.gz (102.5 kB view details)

Uploaded Source

Built Distributions

If you're not sure about the file name format, learn more about wheel file names.

scvelo_rs-0.1.3-cp310-abi3-win_amd64.whl (1.6 MB view details)

Uploaded CPython 3.10+Windows x86-64

scvelo_rs-0.1.3-cp310-abi3-manylinux_2_28_x86_64.whl (1.7 MB view details)

Uploaded CPython 3.10+manylinux: glibc 2.28+ x86-64

scvelo_rs-0.1.3-cp310-abi3-manylinux_2_28_aarch64.whl (1.6 MB view details)

Uploaded CPython 3.10+manylinux: glibc 2.28+ ARM64

scvelo_rs-0.1.3-cp310-abi3-macosx_11_0_arm64.whl (1.5 MB view details)

Uploaded CPython 3.10+macOS 11.0+ ARM64

File details

Details for the file scvelo_rs-0.1.3.tar.gz.

File metadata

  • Download URL: scvelo_rs-0.1.3.tar.gz
  • Upload date:
  • Size: 102.5 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: maturin/1.13.2

File hashes

Hashes for scvelo_rs-0.1.3.tar.gz
Algorithm Hash digest
SHA256 d1090fc38b966f097fcb4089975f157e32008c003d0e5184a8f86d5111411ed2
MD5 a4fcce5eb252b51470276bb630985906
BLAKE2b-256 02f31416fcc022cf77459a728c6df80c4617a70d4f8a2981b0c094e72e5de456

See more details on using hashes here.

File details

Details for the file scvelo_rs-0.1.3-cp310-abi3-win_amd64.whl.

File metadata

File hashes

Hashes for scvelo_rs-0.1.3-cp310-abi3-win_amd64.whl
Algorithm Hash digest
SHA256 3d8f29721ce6cd366bf2582eebcc60950181b0eec410cbf6ecb8695beef32107
MD5 32f869d9dc1aa70b08ff298f23bb18b3
BLAKE2b-256 f90a88f91c5ac7246aebdffaf9210c01f37b839eb465fc70a7b1832e21efc1d2

See more details on using hashes here.

File details

Details for the file scvelo_rs-0.1.3-cp310-abi3-manylinux_2_28_x86_64.whl.

File metadata

File hashes

Hashes for scvelo_rs-0.1.3-cp310-abi3-manylinux_2_28_x86_64.whl
Algorithm Hash digest
SHA256 f88df9b383ee934051e8379c10592a77215e83959a8232c09a32f4c1e8653485
MD5 c75139f649aee5d8f6eb7201b6f5efed
BLAKE2b-256 92cf4eab7ff481311b30d146c84390d5090e6b779936f783367a5414ab60060f

See more details on using hashes here.

File details

Details for the file scvelo_rs-0.1.3-cp310-abi3-manylinux_2_28_aarch64.whl.

File metadata

File hashes

Hashes for scvelo_rs-0.1.3-cp310-abi3-manylinux_2_28_aarch64.whl
Algorithm Hash digest
SHA256 d932141d888e650e6c2921417527b0aaf8bc0ab187390aa807173c5fc79fa488
MD5 26f5e813435dcd7d28b4595a70a286d9
BLAKE2b-256 1e436f4ab7be3c0648fe51eb43f0b304eeeadbf79b7323621eae97ba92cecc0a

See more details on using hashes here.

File details

Details for the file scvelo_rs-0.1.3-cp310-abi3-macosx_11_0_arm64.whl.

File metadata

File hashes

Hashes for scvelo_rs-0.1.3-cp310-abi3-macosx_11_0_arm64.whl
Algorithm Hash digest
SHA256 aff29df5b3219acff74fa95a10f862b85242d7fbffdbf59c407884b656102095
MD5 11fe8f3e8a953d03dddd572faa37b934
BLAKE2b-256 3df6a1d8c748b1233f255c2f756e79ea81768f155a3230d818e92fdc82ce9fcc

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page