SnapATAC2

repository·main·Indexed 43 days ago

https://github.com/scverse/snapatac2

A high-performance Python/Rust framework for single-cell epigenomics and multi-omics analysis, capable of scaling to tens of millions of cells. Version 2.10.0 supports preprocessing, dimension reduction, clustering, and motif analysis, and integrates with Scanpy via backed AnnData objects.

Tokens
31.8K
Snippets
122
Records
151
Agent score
53%

What's inside SnapATAC2

  1. Overview of SnapATAC2 capabilities

    main

    SnapATAC2 is a Python/Rust-based framework designed for scalable single-cell omics analysis. It is optimized to handle datasets exceeding 10 million cells and supports various modalities including single-cell ATAC-seq, RNA-seq, Hi-C, and methylation.

    Key features include:

    • High-performance preprocessing: Fast conversion of BAM files to fragment files and count matrix generation.
    • Matrix-free spectral embedding: An algorithm applicable to multiple single-cell omics types.
    • Multi-omics integration: Scalable co-embedding algorithms for integrating different data modalities.
    • End-to-end ATAC-seq pipeline: Covers preprocessing, dimension reduction, clustering, integration, peak calling, differential analysis, motif analysis, and regulatory network analysis.
    • Ecosystem integration: Seamlessly works with Scanpy and implements fully backed AnnData objects for efficient memory management.
  2. Calculate quality control metrics in SnapATAC2

    main
    SnapATAC2 provides several functions within the snapatac2.metrics module to perform quality control (QC) on single-cell epigenomics data. These metrics help assess data quality through fragment size distributions, Transcription Start Site Enrichment (TSSE), and Fragment Enrichment of Immunoprecipitated DNA (FRIP).
  3. Perform motif analysis with SnapATAC2

    main

    SnapATAC2 provides tools for motif discovery and scanning in single-cell epigenomics data. The primary classes and functions available in the snapatac2 module for motif analysis are:

    • PyDNAMotif: Likely used for motif discovery or representation.
    • PyDNAMotifScanner: Used to scan DNA sequences for specific motifs.
    • PyDNAMotifTest: Used for statistical testing of motifs.
    • read_motifs: A utility function to load motif information from files.

    Refer to the specific API documentation for each of these symbols to understand their required input formats (such as DNA sequences or genomic intervals) and return types.

  4. Manipulate AnnData and AnnDataSet objects

    main
    SnapATAC2 provides support for AnnData and AnnDataSet objects for handling single-cell epigenomics data. AnnData is the standard format for single-cell data, while AnnDataSet is used for backed (on-disk) data manipulation to handle datasets that are too large to fit in memory.
  5. Understand the `tl` (tools) module in SnapATAC2

    main
    The tl module (tools) in snapatac2 is used for data transformations that are not considered preprocessing. While preprocessing functions typically modify the underlying data, a tool usually adds easily interpretable annotations to the data matrix. These annotations are designed to be used with corresponding plotting functions for visualization.
  6. Where to add new features in SnapATAC2

    main

    SnapATAC2 is composed of three distinct libraries. When developing new features, choose the library based on the feature's relevance and stability:

    1. snapatac2-contrib: This is the recommended location for most new features. Use this for additional functionality provided by external contributors.
    2. snapatac2-python (specifically snapatac2.experimental): If a feature is highly relevant to the main library but not yet stable, add it to the snapatac2.experimental module. Once the feature is sufficiently tested and stable, it will be moved from snapatac2.experimental to the main snapatac2 namespace.
    3. snapatac2-core: This contains core functions written in Rust. Only add features here if they are essential and highly relevant to the core library's low-level operations.
  7. Remove doublets with `pp`

    main

    To identify and remove doublet cells (two cells captured in one droplet), use the following functions in snapatac2.pp:

    • pp.scrublet: Implements the Scrublet algorithm to score potential doublets.
    • pp.filter_doublets: Filters the dataset based on doublet scores.
    import snapatac2 as sn
    # sn.pp.scrublet(...)
    # sn.pp.filter_doublets(...)
  8. Integrate datasets with `pp`

    main

    For multi-sample or multi-batch data integration, snapatac2.pp provides several methods to correct batch effects:

    • pp.mnc_correct: Multi-sample normalization and correction.
    • pp.harmony: Integration using the Harmony algorithm.
    • pp.scanorama_integrate: Integration using the Scanorama algorithm.
    import snapatac2 as sn
    # sn.pp.mnc_correct(...)
    # sn.pp.harmony(...)
    # sn.pp.scanorama_integrate(...)
  9. Build SnapATAC2 Docker images

    main

    SnapATAC2 provides two Dockerfile flavors to facilitate portability:

    1. snapatac2-default: Designed for running SnapATAC2 at scale (e.g., via HPC or Cloud).
    2. snapatac2-recommend-interactive: A ready-to-use Jupyter Lab environment including SnapATAC2 and recommended packages like scanpy and scvi-tools.

    Requirements

    • Docker Engine or Docker Desktop installed.
    • Docker Engine version 23.0 or higher (to support BuildKit).

    Build Steps

    1. Navigate to the desired directory: ./default/ or ./snapatac2-recommend-interactive/.
    2. Execute the build command using DOCKER_BUILDKIT=1.

    Customization

    You can use build arguments to customize the image:

    • BASE_PYTHON_IMAGE: Specify a different Python base image.
    • SNAP_ATAC_VERSION: Specify a different version of SnapATAC2.

    Warning: Customizing these arguments may result in untested or non-functional images.

    # Build the default flavor
    DOCKER_BUILDKIT=1 docker build --platform linux/amd64 --tag snapatac2:v2.6.0-default-py3.11 .
    
    # Build the recommended interactive flavor
    DOCKER_BUILDKIT=1 docker build --platform linux/amd64 --tag snapatac2:v2.6.0-recommend-interactive-py3.11 .
    
    # Example: Custom build with specific Python and SnapATAC2 versions
    DOCKER_BUILDKIT=1 docker build --platform linux/amd64 \
      --build-arg BASE_PYTHON_IMAGE=python:3.12-slim \
      --build-arg SNAP_ATAC_VERSION=v2.5.1 \
      --tag snapatac2:v2.5.1-default-py3.12 .
  10. Atlas-Scale Human Chromatin Accessibility Analysis Workflow

    main

    This workflow describes how to process large-scale scATAC-seq fragment files into a human chromatin accessibility atlas. The pipeline follows a specific hierarchy: processing individual samples first, then combining them into a backed AnnDataSet for atlas-level analysis.

    Key Workflow Steps:

    1. Import Fragments: Convert fragment files into backed AnnData objects using snap.pp.import_fragments.
    2. Sample Processing: Build tile matrices, select features, and perform doublet removal (scrublet and filter_doublets) on a per-sample basis.
    3. Aggregation: Combine samples into a single snap.AnnDataSet.
    4. Atlas Analysis: Perform feature selection, spectral embedding, batch correction (mnc_correct), and clustering (KNN, Leiden, UMAP) on the combined dataset.
    5. Subclustering (Optional): Convert a specific cluster to an in-memory AnnData object using .to_adata() for higher-resolution analysis.

    Best Practices for Large Datasets:

    • Use Backed Files: Always use backed files for both per-sample AnnData and the combined AnnDataSet to manage memory.
    • Coarse Binning: Use a larger bin_size (e.g., 5000 bp) for atlas-scale workflows to reduce memory and runtime requirements.
    • Unique Barcodes: Ensure cell barcodes are unique across samples (e.g., by prefixing with the sample name) before combining them into an AnnDataSet.
    • Early Filtering: Apply min_num_fragments and min_tsse during the import stage to remove low-quality barcodes early.
    import os
    import numpy as np
    import snapatac2 as snap
    
    # 1. Configure input and output locations.
    data_dir = "/path/to/fragment/files"
    output_dir = "h5ad_output"
    os.makedirs(output_dir, exist_ok=True)
    
    fragment_files = [
        os.path.join(data_dir, filename)
        for filename in os.listdir(data_dir)
        if filename.endswith(".bed.gz")
    ]
    
    # 2. Import each fragment file into a backed AnnData object.
    outputs = []
    for fragment_file in fragment_files:
        sample_name = os.path.basename(fragment_file).split(".bed.gz")[0]
        outputs.append(os.path.join(output_dir, sample_name + ".h5ad"))
    
    adatas = snap.pp.import_fragments(
        fragment_files,
        file=outputs,
        genome=snap.genome.hg38,
        min_num_fragments=1000,
        min_tsse=7,
    )
    
    # 3. Build sample-level tile matrices, select features, and remove doublets.
    snap.pp.add_tile_matrix(adatas, bin_size=5000)
    snap.pp.select_features(adatas)
    snap.pp.scrublet(adatas)
    snap.pp.filter_doublets(adatas)
    
    # 4. Combine samples into an AnnDataSet and make barcodes unique.
    adataset = snap.AnnDataSet(
        adatas=[(adata.filename.split("/")[-1].split(".h5ad")[0], adata) for adata in adatas],
        filename="data.h5ads",
    )
    adataset.obs_names = np.array(adataset.obs["sample"]) + "+" + np.array(adataset.obs_names)
    
    # 5. Select atlas-level features and compute the initial embedding.
    snap.pp.select_features(adataset, n_features=250000)
    snap.tl.spectral(adataset)
    
    # 6. Correct sample effects while preserving broad tissue groups.
    adataset.obs["tissue"] = [sample.split(":")[0] for sample in adataset.obs["sample"]
    
    snap.pp.mnc_correct(
        adataset,
        batch="sample",
        groupby="tissue",
        key_added="X_spectral",
    )
    
    # 7. Cluster and visualize the atlas.
    snap.pp.knn(adataset)
    snap.tl.leiden(adataset)
    snap.tl.umap(adataset, n_comps=3)
    snap.pl.umap(adataset, color="leiden", interactive=False)
    
    # 8. Optional: convert to in-memory AnnData for subclustering one major cluster.
    adata = adataset.to_adata()
    adata_c0 = adata[adata.obs["leiden"] == "0"].copy()
    
    snap.pp.select_features(adata_c0, n_features=250000)
    snap.tl.spectral(adata_c0)
    snap.pp.mnc_correct(
        adata_c0,
        batch="sample",
        groupby="tissue",
        key_added="X_spectral",
    )
    snap.pp.knn(adata_c0)
    snap.tl.leiden(adata_c0)
    snap.tl.umap(adata_c0)
    snap.pl.umap(adata_c0, color="leiden", interactive=False)
    snap.pl.umap(adata_c0, color="sample", interactive=False)
  11. Run the SnapATAC2 interactive Jupyter Lab image on Linux/MacOS (amd64)

    main

    To run the snapatac2:v2.6.0-recommend-interactive-py3.11 image as an interactive Jupyter Lab environment, use the docker run command with volume mappings for your notebooks and data.

    GPU Support

    To enable CUDA (GPU) functionality, you must:

    1. Install the Nvidia container toolkit.
    2. Include the --gpus flag in your docker run command.

    Execution

    Run the following command, replacing <path_to_local_machine_notebooks> and <path_where_you_want_data_saved> with your local paths:

    1. Execute the docker run command.
    2. Access Jupyter Lab via the browser at http://127.0.0.1:8888/lab?token=<jupyter-lab-token> (the token is found in the container logs).
    docker run --interactive --tty --rm \
      --env LOCAL_USER_ID=`id -u $USER` \
      --publish 8888:8888 \
      --volume <path_to_local_machine_notebooks>:/notebooks \
      --volume <path_where_you_want_data_saved>:/data \
      snapatac2:v2.6.0-recommend-interactive-py3.11
  12. Install the stable version of SnapATAC2

    main

    The easiest way to install SnapATAC2 is via PyPI. Precompiled binaries are available for x86_64 Linux and macOS. If no precompiled binary is available for your system, pip will attempt to build it from source, which requires cmake >= 3.5.1 and the Rust compiler.

    pip install snapatac2