changeset 0:1c52ce622590 draft default tip

planemo upload for repository https://github.com/galaxyproject/tools-iuc/tree/master/tools/snapatac2 commit 1e34deee1e39c0c65e1e29a9d28becc7aaf23a4f
author iuc
date Thu, 23 May 2024 15:19:50 +0000
parents
children
files macros.xml peaks_and_motif_analysis.xml
diffstat 2 files changed, 675 insertions(+), 0 deletions(-) [+]
line wrap: on
line diff
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/macros.xml	Thu May 23 15:19:50 2024 +0000
@@ -0,0 +1,190 @@
+<macros>
+    <token name="@TOOL_VERSION@">2.5.3</token>
+    <token name="@VERSION_SUFFIX@">1</token>
+    <token name="@PROFILE@">23.0</token>
+    <xml name="requirements">
+        <requirement type="package" version="@TOOL_VERSION@">snapatac2</requirement>
+        <requirement type="package" version="5.18.0">plotly</requirement>
+        <requirement type="package" version="0.2.1">python-kaleido</requirement>
+        <requirement type="package" version="0.19.19">polars</requirement>
+        <requirement type="package" version="14.0.1">pyarrow</requirement>
+        <requirement type="package" version="0.11.3">python-igraph</requirement>
+        <requirement type="package" version="0.8.33">hdbscan</requirement>
+        <requirement type="package" version="0.0.9">harmonypy</requirement>
+        <requirement type="package" version="1.7.4">scanorama</requirement>
+        <requirement type="package" version="3.0.1">macs3</requirement>
+        <requirement type="package" version="0.70.16">multiprocess</requirement>
+        <requirement type="package" version="0.10.2">leidenalg</requirement>
+        <yield />
+    </xml>
+
+    <token name="@PREP_ADATA@"><![CDATA[
+        cp '$method.adata' 'anndata.h5ad' &&
+        ]]>
+    </token>
+
+    <token name="@CMD@"><![CDATA[
+        cat '$script_file' > '$hidden_output' &&
+        python '$script_file' >> '$hidden_output' &&
+        touch 'anndata_info.txt' &&
+        cat 'anndata_info.txt' @CMD_prettify_stdout@
+        ]]>
+    </token>
+
+    <token name="@CMD_prettify_stdout@"><![CDATA[ | sed -r '1 s|AnnData object with (.+) = (.*)\s*|\1: \2|g' | sed "s|'||g"  | sed -r 's|^\s*(.*):\s(.*)|[\1]\n-    \2|g' | sed 's|, |\n-    |g'
+    ]]></token>
+
+    <token name="@CMD_imports@"><![CDATA[
+import snapatac2 as sa
+import os
+    ]]>
+    </token>
+    <xml name="sanitize_query" token_validinitial="string.printable">
+        <sanitizer>
+            <valid initial="@VALIDINITIAL@">
+                <remove value="&apos;" />
+            </valid>
+        </sanitizer>
+    </xml>
+
+    <xml name="inputs_anndata">
+        <param name="adata" type="data" format="h5ad" label="Annotated data matrix"/>
+    </xml>
+
+    <token name="@CMD_read_inputs@"><![CDATA[
+
+adata = sa.read('anndata.h5ad', backed = None)
+]]>
+    </token>
+
+    <xml name="dimentions_plot">
+        <param argument="width" type="integer" value="500" label="Width of the plot"/>
+        <param argument="height" type="integer" value="400" label="Height of the plot"/>
+    </xml>
+
+    <xml name="param_groupby">
+        <param argument="groupby" type="text" label="The key of the observation grouping to consider">
+            <expand macro="sanitize_query" />
+        </param>
+    </xml>
+
+    <xml name="out_file">
+        <param name="out_file" type="select" optional="true" label="Type of output plot">
+            <option value="png" selected="true">PNG</option>
+            <option value="svg">SVG</option>
+            <option value="pdf">PDF</option>
+        </param>
+    </xml>
+    <token name="@CMD_anndata_write_outputs@"><![CDATA[
+adata.write('anndata.h5ad')
+with open('anndata_info.txt','w', encoding='utf-8') as ainfo:
+    print(adata, file=ainfo)
+]]>
+    </token>
+    <xml name="inputs_common_advanced">
+        <section name="advanced_common" title="Advanced Options" expanded="false">
+            <param name="show_log" type="boolean" checked="false" label="Output Log?" />
+        </section>
+    </xml>
+    <xml name="params_render_plot">
+        <param argument="width" type="integer" value="600" label="Width of the plot"/>
+        <param argument="height" type="integer" value="400" label="Height of the plot"/>
+        <expand macro="out_file"/>
+    </xml>
+    <xml name="param_shift">
+        <param argument="shift_left" type="integer" value="4" label="Insertion site correction for the left end" help="Note this has no effect on single-end reads"/>
+        <param argument="shift_right" type="integer" value="-5" label="Insertion site correction for the right end" help="Note this has no effect on single-end reads"/>
+    </xml>
+    <xml name="param_chunk_size" tokens="size">
+        <param argument="chunk_size" type="integer" value="@SIZE@" label="chunk size"/>
+    </xml>
+    <xml name="min_max_frag_size">
+        <param argument="min_frag_size" type="integer" optional="true" value="" label="Minimum fragment size to include"/>
+        <param argument="max_frag_size" type="integer" optional="true" value="" label="Maximum fragment size to include"/>
+    </xml>
+    <xml name="params_data_integration">
+        <param argument="use_rep" type="text" value="X_spectral" label="The key for the matrix"/>
+        <param argument="use_dims" type="text" optional="true" value="" label="The dimensions used for computation">
+            <expand macro="sanitize_query"/>
+        </param>
+        <param argument="groupby" type="text" optional="true" value="" label="The key of the observation grouping to consider">
+            <expand macro="sanitize_query" />
+        </param>
+        <param argument="key_added" type="text" optional="true" value="" label="If specified, add the result to adata.obsm with this key"/>
+    </xml>
+    <xml name="param_n_comps">
+        <param argument="n_comps" type="integer" value="30" label="Number of dimensions to keep" help="The result is insensitive to this parameter when `weighted_by_sd` is set, as long as it is large enough, e.g. 30."/>
+    </xml>
+    <xml name="param_random_state">
+        <param argument="random_state" type="integer" value="0" label="Seed of the random state generator"/>
+    </xml>
+    <xml name="param_key_added" tokens="key_added">
+        <param argument="key_added" type="text" value="@KEY_ADDED@"  label="`adata.obs` key under which t add cluster labels"/>
+    </xml>
+    <xml name="param_use_rep">
+        <param argument="use_rep" type="text" value="X_spectral" label="Use the indicated representation in `.obsm`"/>
+    </xml>
+    <xml name="genome_fasta">
+        <param argument="genome_fasta" type="text" label="A fasta file containing the genome sequences or a Genome object"/>
+    </xml>
+    <xml name="background">
+        <param argument="background" type="text" optional="true" value="" label="A list of regions to be used as the background">
+            <expand macro="sanitize_query"/>
+        </param>
+    </xml>
+    <xml name="mat">
+        <param argument="peak_mat" type="data" format="h5ad" optional="true" label="AnnData or AnnDataSet object storing the cell by peak count matrix"/>
+        <param argument="gene_mat" type="data" format="h5ad" optional="true" label="AnnData or AnnDataSet object storing the cell by gene count matrix"/>
+    </xml>
+    <xml name="param_network">
+        <param argument="network" type="text" label="network"/>
+    </xml>
+    <xml name="param_n_iterations">
+        <param argument="n_iterations" type="integer" value="-1" label="How many iterations of the Leiden clustering algorithm to perform"
+            help="Positive values above 2 define the total number of iterations to perform, -1 has the algorithm run until it reaches its optimal clustering."/>
+    </xml>
+
+    <xml name="citations">
+        <citations>
+            <citation type="doi">10.1038/s41592-023-02139-9</citation>
+        </citations>
+    </xml>
+    <xml name="render_plot_test">
+        <param name="width" value="650"/>
+        <param name="height" value="450"/>
+    </xml>
+    <xml name="render_plot_matching_text">
+        <has_text_matching expression="width = 650"/>
+        <has_text_matching expression="height = 450"/>
+    </xml>
+    <xml name="param_counting_strategy">
+        <param argument="counting_strategy" type="select" label="he strategy to compute feature counts">
+            <option value="fragment">fragment</option>
+            <option value="insertion" selected="true">insertion</option>
+            <option value="paired-insertion">paired-insertion</option>
+        </param>
+    </xml>
+
+    <token name="@CMD_params_data_integration@"><![CDATA[
+use_rep = '$method.use_rep',
+#if $method.use_dims != ''
+#set $dims = ([x.strip() for x in str($method.use_dims).split(',')])
+use_dims=$dims,
+#end if
+#if $method.groupby != ''
+#set $groupby = ([x.strip() for x in str($method.groupby).split(',')])
+groupby=$groupby,
+#end if
+#if $method.key_added != ''
+key_added = '$method.key_added',
+#end if
+    ]]>
+    </token>
+
+    <token name="@CMD_params_render_plot@"><![CDATA[
+    width = $method.width,
+    height = $method.height,
+    out_file = 'plot.$method.out_file',
+    ]]>
+    </token>
+</macros>
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/peaks_and_motif_analysis.xml	Thu May 23 15:19:50 2024 +0000
@@ -0,0 +1,485 @@
+<tool id="peaks_and_motif" name="SnapATAC2 peaks and motif" version="@TOOL_VERSION@+galaxy@VERSION_SUFFIX@" profile="@PROFILE@">
+    <description>analysis</description>
+    <macros>
+        <import>macros.xml</import>
+    </macros>
+    <requirements>
+        <expand macro="requirements"/>
+    </requirements>
+    <command detect_errors="exit_code"><![CDATA[
+export NUMBA_CACHE_DIR="\${TEMP:-/tmp}";
+@PREP_ADATA@
+@CMD@
+    ]]></command>
+    <configfiles>
+        <configfile name="script_file"><![CDATA[
+@CMD_imports@
+@CMD_read_inputs@
+
+#if $method.method == 'tl.macs3'
+if __name__ == '__main__': ## a temporary fix https://github.com/kaizhang/SnapATAC2/issues/298
+    sa.tl.macs3(
+        adata,
+        #if $method.groupby != ''
+        groupby = '$method.groupby',
+        #end if
+        qvalue = $method.qvalue,
+        #if $method.replicate
+        replicate = '$method.replicate',
+        #end if
+        #if $method.replicate_qvalue
+        replicate_qvalue = $method.replicate_qvalue,
+        #end if
+        #if $method.max_frag_size
+        max_frag_size = $method.max_frag_size,
+        #end if
+        nolambda = $method.nolambda,
+        shift = $method.shift,
+        extsize = $method.extsize,
+        #if $method.blacklist
+        blacklist = '$method.blacklist',
+        #end if
+        key_added = '$method.key_added',
+        inplace = True,
+        tempdir = '.',
+        n_jobs = 1
+    )
+
+#else if $method.method == 'tl.merge_peaks'
+import json
+import pandas as pd
+import csv
+with open('$method.chrom_sizes') as f:
+    chr_sizes = {x[0]:int(x[1]) for x in csv.reader(f, delimiter='\t')}
+
+peaks = sa.tl.merge_peaks(
+    adata.uns['$method.macs_key'],
+    chrom_sizes = chr_sizes,
+    half_width = $method.half_width
+)
+peaks.write_csv('merged_peaks.tabular', separator = '\t')
+
+#else if $method.method == 'pp.make_peak_matrix'
+import polars
+peaks = polars.read_csv('$method.merged_peaks', separator='\t')
+sa.pp.make_peak_matrix(
+    adata,
+    use_rep = peaks['Peaks'],
+    chunk_size = $method.chunk_size,
+    use_x = $method.use_x,
+    #if $method.min_frag_size
+    min_frag_size = $method.min_frag_size,
+    #end if
+    #if $method.max_frag_size
+    max_frag_size = $method.max_frag_size,
+    #end if
+    ##counting_strategy = '$method.counting_strategy'
+    count_frag_as_reads = $method.count_frag_as_reads
+)
+
+#else if $method.method == 'tl.marker_regions'
+marker_peaks = sa.tl.marker_regions(
+    adata,
+    groupby = '$method.groupby',
+    pvalue = $method.pvalue
+)
+sa.pl.regions(
+    adata,
+    groupby = '$method.groupby',
+    peaks = marker_peaks,
+    @CMD_params_render_plot@
+)
+
+
+#else if $method.method == 'tl.diff_test'
+import numpy as np
+import polars
+peaks = polars.read_csv('$method.merged_peaks', separator='\t')
+group_key = '$method.group_key'
+    #if $method.compare.with == 'single_group'
+group1 = '$method.compare.group1_value'
+group1_cells = adata.obs[group_key] == group1
+group2 = '$method.compare.group2_value'
+group2_cells = adata.obs[group_key] == group2
+peaks_selected = np.logical_or(
+    peaks[group1].to_numpy(),
+    peaks[group2].to_numpy(),
+)
+    #else if $method.compare.with == 'background_group'
+group1 = '$method.compare.group1_value'
+group1_cells = adata.obs[group_key] == group1
+barcodes = np.array(adata.obs_names)
+group2_cells = []
+for i in np.unique(adata.obs[group_key]):
+    if i != group1:
+        cells = np.random.choice(barcodes[adata.obs[group_key] == i], size=$method.compare.number_of_cells, replace=False)
+        group2_cells.append(cells)
+group2_cells = np.concatenate(group2_cells)
+peaks_selected = peaks[group1].to_numpy()
+    #end if
+
+diff_peaks = sa.tl.diff_test(
+    adata,
+    cell_group1 = group1_cells,
+    cell_group2 = group2_cells,
+    features = peaks_selected,
+    direction = '$method.direction',
+    min_log_fc = $method.min_log_fc,
+    min_pct = $method.min_pct
+)
+diff_peaks.write_csv('diff_peaks.tabular', separator = '\t')
+
+diff_peaks = diff_peaks.filter(polars.col('adjusted p-value') < $method.cutoff_p_adj)
+
+    #if $method.compare.with == 'single_group'
+peaks_to_plot = {
+    group1: diff_peaks.filter(polars.col("log2(fold_change)") > $method.cutoff_l2fc)['feature name'].to_numpy(),
+    group2: diff_peaks.filter(polars.col("log2(fold_change)") < $method.cutoff_l2fc)['feature name'].to_numpy(),
+    }
+    #else if $method.compare.with == 'background_group'
+peaks_to_plot = {
+    group1: diff_peaks['feature name'].to_numpy()
+    }
+    #end if
+
+sa.pl.regions(
+    adata,
+    groupby = group_key,
+    peaks = peaks_to_plot,
+    @CMD_params_render_plot@
+)
+
+#end if
+@CMD_anndata_write_outputs@
+    ]]></configfile>
+    </configfiles>
+    <inputs>
+        <conditional name="method">
+            <param name="method" type="select" label="Tool">
+                <option value="tl.macs3">Call peaks using MACS3, using 'tl.macs3'</option>
+                <option value="tl.merge_peaks">Merge peaks from different groups, using 'tl.merge_peaks'</option>
+                <option value="pp.make_peak_matrix">Generate cell by peak count matrix, using 'pp.make_peak_matrix'</option>
+                <option value="tl.marker_regions">A quick-and-dirty way to get marker regions, using 'tl.marker_regions'</option>
+                <option value="tl.diff_test">Identify differentially accessible regions,using 'tl.diff_test'</option>
+            </param>
+            <when value="tl.macs3">
+                <expand macro="inputs_anndata"/>
+                <param argument="groupby" type="text" value="" optional="true" label="Group cells before peak calling based on key in `.obs`"/>
+                <param argument="qvalue" type="float" value="0.05" label="qvalue cutoff used in MACS3"/>
+                <param argument="replicate" type="text" value="" optional="true" label="Replicate information based on key in `.obs`"/>
+                <param argument="replicate_qvalue" type="float" value="" optional="true" label="qvalue cutoff used in MACS3 for calling peaks in replicates"/>
+                <param argument="max_frag_size" type="integer" value="" optional="true" label="Maximum fragment size"
+                    help="This is used to remove fragments that are not from nucleosome-free regions."/>
+                <param argument="nolambda" type="boolean" checked="false" truevalue="True" falsevalue="False" label="If True, macs3 will use the background lambda as local lambda"/>
+                <param argument="shift" type="integer" value="-100" label="The shift size in MACS"/>
+                <param argument="extsize" type="integer" value="200" label="The extension size in MACS"/>
+                <param argument="blacklist" type="data" format="bed" optional="true" label="Blacklist file in BED format"
+                    help="If provided, regions in the blacklist will be removed."/>
+                <param argument="key_added" type="text" value="macs3"  label="`.uns` key under which to add peak information"/>
+            </when>
+            <when value="tl.merge_peaks">
+                <expand macro="inputs_anndata"/>
+                <param name="macs_key" type="text" value="macs3" label="`.uns` key under which peak information was added while peak calling"/>
+                <param argument="chrom_sizes" type="data" format="tabular" label="Chromosome sizes"/>
+                <param argument="half_width" type="integer" value="250" label="Half width of the merged peaks"/>
+            </when>
+            <when value="pp.make_peak_matrix">
+                <expand macro="inputs_anndata"/>
+                <param argument="use_rep" type="text" optional="true" value="" label="Used to read peak information from .uns[use_rep]">
+                    <expand macro="sanitize_query"/>
+                </param>
+                <param argument="merged_peaks" type="data" format="tabular" label="Merged peaks file"/>
+                <expand macro="param_chunk_size" size="500"/>
+                <param argument="use_x" type="boolean" truevalue="True" falsevalue="False" checked="false" label="If True, use the matrix stored in .X as raw counts"/>
+                <expand macro="min_max_frag_size"/>
+                <!--expand macro="param_counting_strategy"/-->
+                <param argument="count_frag_as_reads" type="boolean" truevalue="True" falsevalue="False" checked="true" label="Whether to count fragments as reads"/>
+            </when>
+            <when value="tl.marker_regions">
+                <expand macro="inputs_anndata"/>
+                <expand macro="param_groupby"/>
+                <param argument="pvalue" type="float" value="0.01" label="P-value threshold"/>
+                <expand macro="params_render_plot"/>
+            </when>
+            <when value="tl.diff_test">
+                <expand macro="inputs_anndata"/>
+                <param argument="merged_peaks" type="data" format="tabular" label="Merged peaks file"/>
+                <param name="group_key" type="text" value="cell_type" label="key in `.obs` to select cell groups" help="for eg. cell_type"/>
+                <conditional name="compare">
+                    <param name="with" type="select" label="Test for differential accessibility in a group of cells compared to">
+                        <option value="single_group">Another group of cells</option>
+                        <option value="background_group">Background cell group built from random selection of cells from all other the groups</option>
+                    </param>
+                    <when value="single_group">
+                        <param name="group1_value" type="text" value="Naive B" label="name of the group 1 stored in .obs"/>
+                        <param name="group2_value" type="text" value="Memory B" label="name of the group 2 stored in .obs"/>
+                    </when>
+                    <when value="background_group">
+                        <param name="group1_value" type="text" value="Naive B" label="name of the group 1 stored in .obs"/>
+                        <param name="number_of_cells" type="integer" min="1" value="30" label="Number of cells to subsample from ther other groups"/>
+                    </when>
+                </conditional>
+                <param argument="direction" type="select" label="“positive”: return features that are enriched in group 1. “negative”: return features that are enriched in group 2">
+                    <option value="positive">“positive”: return features that are enriched in group 1</option>
+                    <option value="negative"> “negative”: return features that are enriched in group 2</option>
+                    <option value="both" selected="true">“both”: return features that are enriched in group 1 or group 2</option>
+                </param>
+                <param argument="min_log_fc" type="float" value="0.25" label="Limit testing to features which show, on average, at least this difference (log2-scale) between the two groups of cells"/>
+                <param argument="min_pct" type="float" value="0.05" label="Only test features that are detected in a minimum fraction of min_pct cells in either of the two population"/>
+                <expand macro="params_render_plot"/>
+                <param name="cutoff_p_adj" type="float" value="0.01" label="Adjusted p-value cutoff for plotting" help="This cutoff is applied for plotting only"/>
+                <param name="cutoff_l2fc" type="float" value="1" label="Log2 fold change cutoff for plotting" help="This cutoff is applied for plotting only"/>
+            </when>
+        </conditional>
+        <expand macro="inputs_common_advanced"/>
+    </inputs>
+    <outputs>
+        <data name="anndata_out" format="h5ad" from_work_dir="anndata.h5ad" label="${tool.name} (${method.method}) on ${on_string}: Annotated data matrix"/>
+        <data name="hidden_output" format="txt" label="Log file" >
+            <filter>advanced_common['show_log']</filter>
+        </data>
+        <data name="merged_peaks" format="tabular" from_work_dir="merged_peaks.tabular" label="${tool.name} (${method.method}) on ${on_string}: Merged peaks">
+            <filter>method['method'] == 'tl.merge_peaks'</filter>
+        </data>
+        <data name="out_png" format="png" from_work_dir="plot.png" label="PNG plot from ${tool.name} (${method.method}) on ${on_string}">
+            <filter>(method['method'] == 'tl.marker_regions' or method['method'] == 'tl.diff_test') and method['out_file'] == 'png'</filter>
+        </data>
+        <data name="out_pdf" format="pdf" from_work_dir="plot.pdf" label="PDF plot from ${tool.name} (${method.method}) on ${on_string}">
+            <filter>(method['method'] == 'tl.marker_regions' or method['method'] == 'tl.diff_test') and method['out_file'] == 'pdf'</filter>
+        </data>
+        <data name="out_svg" format="svg" from_work_dir="plot.svg" label="SVG plot from ${tool.name} (${method.method}) on ${on_string}">
+            <filter>(method['method'] == 'tl.marker_regions' or method['method'] == 'tl.diff_test') and method['out_file'] == 'svg'</filter>
+        </data>
+        <data name="diff_peaks" format="tabular" from_work_dir="diff_peaks.tabular" label="${tool.name} on ${on_string}: Differential peaks" >
+            <filter>method['method'] == 'tl.diff_test'</filter>
+        </data>
+    </outputs>
+    <tests>
+        <test expect_num_outputs="2">
+            <!-- tl.macs3 -->
+            <conditional name="method">
+                <param name="method" value="tl.macs3"/>
+                <param name="adata" location="https://zenodo.org/records/11260316/files/tl.leiden.modularity.pbmc_500_chr21.h5ad"/>
+                <param name="groupby" value="leiden"/>
+                <param name="qvalue" value="0.1"/>
+                <param name="shift" value="-100"/>
+                <param name="extsize" value="200"/>
+                <param name="key_added" value="macs3"/>
+                </conditional>
+            <section name="advanced_common">
+                <param name="show_log" value="true"/>
+            </section>
+            <output name="hidden_output">
+                <assert_contents>
+                    <has_text_matching expression="sa.tl.macs3"/>
+                    <has_text_matching expression="groupby = 'leiden'"/>
+                    <has_text_matching expression="qvalue = 0.1"/>
+                    <has_text_matching expression="shift = -100"/>
+                    <has_text_matching expression="extsize = 200"/>
+                    <has_text_matching expression="key_added = 'macs3'"/>
+                </assert_contents>
+            </output>
+            <output name="anndata_out" ftype="h5ad" compare="sim_size" delta="20000" location="https://zenodo.org/records/11260316/files/tl.macs3.pbmc_500_chr21.h5ad"/>
+        </test>
+        <test expect_num_outputs="3">
+            <!-- tl.merge_peaks -->
+            <conditional name="method">
+                <param name="method" value="tl.merge_peaks"/>
+                <param name="adata" location="https://zenodo.org/records/11260316/files/tl.macs3.pbmc_500_chr21.h5ad"/>
+                <param name="chrom_sizes" location="https://zenodo.org/records/11260316/files/chr21_size.tabular"/>
+                <param name="half_width" value="250"/>
+                </conditional>
+            <section name="advanced_common">
+                <param name="show_log" value="true" />
+            </section>
+            <output name="hidden_output">
+                <assert_contents>
+                    <has_text_matching expression="sa.tl.merge_peaks"/>
+                    <has_text_matching expression="half_width = 250"/>
+                </assert_contents>
+            </output>
+            <output name="anndata_out" location="https://zenodo.org/records/11260316/files/tl.merge_peaks.pbmc_500_chr21.h5ad" ftype="h5ad" compare="sim_size" delta_frac="0.1" />
+            <output name="merged_peaks" >
+                <assert_contents>
+                    <has_text_matching expression="chr21:5063027-5063528"/>
+                    <has_text_matching expression="chr21:19782380-19782881"/>
+                    <has_text_matching expression="chr21:29908867-29909368"/>
+                    <has_text_matching expression="chr21:37392823-37393324"/>
+                    <has_text_matching expression="chr21:44082467-44082968"/>
+                </assert_contents>
+            </output>
+        </test>
+        <test expect_num_outputs="2">
+            <!-- pp.make_peak_matrix -->
+            <conditional name="method">
+                <param name="method" value="pp.make_peak_matrix"/>
+                <param name="adata" location="https://zenodo.org/records/11260316/files/tl.merge_peaks.pbmc_500_chr21.h5ad"/>
+                <param name="merged_peaks" location="https://zenodo.org/records/11260316/files/merged_peaks.tabular"/>
+                <param name="chunk_size" value="500"/>
+                <param name="use_x" value="False"/>
+                <param name="count_frag_as_reads" value="True"/>
+                </conditional>
+            <section name="advanced_common">
+                <param name="show_log" value="true" />
+            </section>
+            <output name="hidden_output">
+                <assert_contents>
+                    <has_text_matching expression="sa.pp.make_peak_matrix"/>
+                    <has_text_matching expression="chunk_size = 500"/>
+                    <has_text_matching expression="use_x = False"/>
+                    <has_text_matching expression="count_frag_as_reads = True"/>
+                </assert_contents>
+            </output>
+            <output name="anndata_out" location="https://zenodo.org/records/11260316/files/pp.make_peak_matrix.pbmc_500_chr21.h5ad" ftype="h5ad" compare="sim_size" delta_frac="0.1" />
+        </test>
+        <test expect_num_outputs="3">
+            <!-- tl.marker_regions -->
+            <conditional name="method">
+                <param name="method" value="tl.marker_regions"/>
+                <param name="adata" location="https://zenodo.org/records/11260316/files/pp.make_peak_matrix.pbmc_500_chr21.h5ad"/>
+                <param name="groupby" value="leiden"/>
+                <param name="pvalue" value="0.1"/>
+                <param name="out_file" value="png"/>
+                <expand macro="render_plot_test"/>
+            </conditional>
+            <section name="advanced_common">
+                <param name="show_log" value="true" />
+            </section>
+            <output name="hidden_output">
+                <assert_contents>
+                    <has_text_matching expression="sa.tl.marker_regions"/>
+                    <has_text_matching expression="sa.pl.regions"/>
+                    <has_text_matching expression="groupby = 'leiden'"/>
+                    <has_text_matching expression="pvalue = 0.1"/>
+                    <expand macro="render_plot_matching_text"/>
+                </assert_contents>
+            </output>
+            <output name="anndata_out" location="https://zenodo.org/records/11260316/files/tl.marker_regions.pbmc_500_chr21.h5ad" ftype="h5ad" compare="sim_size" delta_frac="0.1" />
+            <output name="out_png" location="https://zenodo.org/records/11260316/files/tl.marker_regions.pbmc_500_chr21.png" ftype="png" compare="sim_size" delta_frac="0.1"/>
+        </test>
+        <test expect_num_outputs="4">
+            <!-- tl.diff_test single_group -->
+            <conditional name="method">
+                <param name="method" value="tl.diff_test"/>
+                <param name="adata" location="https://zenodo.org/records/11260316/files/tl.marker_regions.pbmc_500_chr21.h5ad"/>
+                <param name="merged_peaks" location="https://zenodo.org/records/11260316/files/merged_peaks.tabular"/>
+                <param name="group_key" value="leiden"/>
+                <conditional name="compare">
+                    <param name="with" value="single_group"/>
+                    <param name="group1_value" value="1"/>
+                    <param name="group2_value" value="2"/>
+                </conditional>
+                <param name="direction" value="both"/>
+                <param name="min_log_fc" value="0.25"/>
+                <param name="min_pct" value="0.05"/>
+            </conditional>
+            <section name="advanced_common">
+                <param name="show_log" value="true" />
+            </section>
+            <output name="hidden_output">
+                <assert_contents>
+                    <has_text_matching expression="sa.tl.diff_test"/>
+                    <has_text_matching expression="group_key = 'leiden'"/>
+                    <has_text_matching expression="group1 = '1'"/>
+                    <has_text_matching expression="group2 = '2'"/>
+                </assert_contents>
+            </output>
+            <output name="anndata_out" location="https://zenodo.org/records/11260316/files/tl.diff_test.single_group.pbmc_500_chr21.h5ad" ftype="h5ad" compare="sim_size" delta_frac="0.1" />
+            <output name="diff_peaks" >
+                <assert_contents>
+                    <has_text_matching expression="chr21:14215000-14220000\t-1.5951.*\t0.0016.*\t0.0563.*"/>
+                    <has_text_matching expression="chr21:17690000-17695000\t2.2792.*\t0.0996.*\t0.2127.*"/>
+                    <has_text_matching expression="chr21:13975000-13980000\t0.5423.*\t0.9829.*\t0.9829.*"/>
+                </assert_contents>
+            </output>
+            <output name="out_png" location="https://zenodo.org/records/11260316/files/tl.diff_test.single_group.pbmc_500_chr21.png" ftype="png" compare="sim_size" delta_frac="0.1"/>
+        </test>
+        <test expect_num_outputs="4">
+            <!-- tl.diff_test background_group -->
+            <conditional name="method">
+                <param name="method" value="tl.diff_test"/>
+                <param name="adata" location="https://zenodo.org/records/11260316/files/tl.marker_regions.pbmc_500_chr21.h5ad"/>
+                <param name="merged_peaks" location="https://zenodo.org/records/11260316/files/merged_peaks.tabular"/>
+                <param name="group_key" value="leiden"/>
+                <conditional name="compare">
+                    <param name="with" value="background_group"/>
+                    <param name="group1_value" value="1"/>
+                    <param name="number_of_cells" value="2"/>
+                </conditional>
+                <param name="direction" value="positive"/>
+                <param name="min_log_fc" value="0.25"/>
+                <param name="min_pct" value="0.05"/>
+                <param name="cutoff_p_adj" value="0.5"/>
+                <param name="cutoff_l2fc" value="0.5"/>
+            </conditional>
+            <section name="advanced_common">
+                <param name="show_log" value="true" />
+            </section>
+            <output name="hidden_output">
+                <assert_contents>
+                    <has_text_matching expression="sa.tl.diff_test"/>
+                    <has_text_matching expression="group_key = 'leiden'"/>
+                    <has_text_matching expression="group1 = '1'"/>
+                </assert_contents>
+            </output>
+            <output name="anndata_out" location="https://zenodo.org/records/11260316/files/tl.diff_test.background_group.pbmc_500_chr21.h5ad" ftype="h5ad" compare="sim_size" delta_frac="0.1" />
+            <output name="diff_peaks" >
+                <assert_contents>
+                    <has_text_matching expression="chr21:13880000-13885000"/>
+                </assert_contents>
+            </output>
+            <output name="out_png" location="https://zenodo.org/records/11260316/files/tl.diff_test.background_group.pbmc_500_chr21.png" ftype="png" compare="sim_size" delta_frac="0.5"/>
+        </test>
+    </tests>
+    <help><![CDATA[
+Call peaks using MACS3, using `tl.macs3`
+========================================
+
+Call peaks using MACS3.
+
+More details on the `SnapATAC2 documentation
+<https://kzhang.org/SnapATAC2/api/_autosummary/snapatac2.tl.macs3.html>`__
+
+Merge peaks from different groups, using `tl.merge_peaks`
+=========================================================
+
+Merge peaks from different groups.
+
+Merge peaks from different groups. It is typically used to merge results from `macs3`.
+
+This function initially expands the summits of identified peaks by `half_width` on both sides. Following this expansion, it addresses the issue of overlapping peaks through an iterative process. The procedure begins by prioritizing the most significant peak, determined by the smallest p-value. This peak is retained, and any peak that overlaps with it is excluded. Subsequently, the same method is applied to the next most significant peak. This iteration continues until all peaks have been evaluated, resulting in a final list of non-overlapping peaks, each with a fixed width determined by the initial extension.
+
+More details on the `SnapATAC2 documentation
+<https://kzhang.org/SnapATAC2/api/_autosummary/snapatac2.tl.merge_peaks.html>`__
+
+Generate cell by bin count matrix, using `pp.add_tile_matrix`
+=============================================================
+
+Generate cell by bin count matrix.
+
+This function is used to generate and add a cell by bin count matrix to the AnnData object.
+
+`import_data` must be ran first in order to use this function.
+
+More details on the `SnapATAC2 documentation
+<https://kzhang.org/SnapATAC2/api/_autosummary/snapatac2.pp.add_tile_matrix.html>`__
+
+A quick-and-dirty way to get marker regions, using `tl.marker_regions`
+======================================================================
+
+A quick-and-dirty way to get marker regions.
+
+More details on the `SnapATAC2 documentation
+<https://kzhang.org/SnapATAC2/api/_autosummary/snapatac2.tl.marker_regions.html>`__
+
+Identify differentially accessible regions, using `tl.diff_test`
+====================================================================
+
+Identify differentially accessible regions.
+
+More details on the `SnapATAC2 documentation
+<https://kzhang.org/SnapATAC2/api/_autosummary/snapatac2.tl.diff_test.html>`__
+    ]]></help>
+    <expand macro="citations"/>
+</tool>
+