Writing the methods section for a single-cell paper (with a template)

What reviewers check in a single-cell methods section, a fill-in template covering every parameter that gets asked about, and the omissions that trigger revision.

Updated 2026-07-31

Do this on your own data: the methods paragraph needs the actual thresholds and cell counts from your run. The free QC report gives you those numbers on your own matrix, ready to paste: omics.hstgenomics.com/qc-check. An example report with the methods paragraph written for a manuscript: omics.hstgenomics.com/sample.

Want it done rather than explained? We do analysis only — send a count matrix, an h5ad or Seurat object, Cell Ranger output or a public accession and get publication-ready results with the code that produced them, at a fixed price agreed before any work starts: omics.hstgenomics.com/quote.

The methods section is written last, in a hurry, by whoever remembers least about what was run. It is also the part reviewers use to decide whether the analysis can be trusted. Below is what has to be in it, and a template you can fill in.

One sentence that settles the most common objection: state the unit of replication explicitly — "n refers to donors, not cells". If quality thresholds were data-driven rather than copied, name the rule too (for example median ± 3 MAD per sample); naming a rule is what turns "arbitrary cut-offs" into a defensible choice.

The rule that saves the most time

A methods section is reproducible if a competent stranger could get your numbers from your raw data. Everything below is a consequence of that rule, and if you write the section while analysing rather than afterwards, it costs you nothing.

What has to be there

  1. Software and versions. Cell Ranger, Seurat or scanpy, and every package that touched the result, with version numbers. "Analysis was performed in Seurat" is not a method.
  2. Filtering criteria and their effect. The thresholds and how many cells they removed, per sample.
  3. Doublet and ambient handling. Tool, expected rate, observed rate. If not done, say so.
  4. Normalisation. Which method, which target, whether regression of covariates was applied.
  5. Feature selection and dimensionality. Number of variable genes, number of components used, and why.
  6. Clustering. Algorithm, resolution, and the neighbourhood parameters.
  7. Annotation. Marker sources, reference datasets, and whether automated labelling was used blind.
  8. Statistics. The test, the unit of replication, covariates in the model, and the multiple-testing correction. This is the sentence reviewers read most carefully.
  9. Data and code availability. Accession, and where the analysis code lives.

A template to fill in

Reads were aligned and counted with Cell Ranger vX.Y against the GRCh38-XXXX reference. Downstream analysis used Scanpy vX.Y (or Seurat vX.Y) in Python vX.Y. Barcodes with fewer than A detected genes, more than B detected genes, or more than C% of counts from mitochondrial genes were removed, retaining N of M cells (per-sample counts in Supplementary Table SX). Ambient RNA was estimated and removed with [SoupX/CellBender vX.Y] (mean contamination D%); doublets were identified with [scDblFinder/ Scrublet vX.Y] at an expected rate of E%, removing F barcodes. Counts were normalised to G per cell and log1p-transformed. The H most variable genes were selected; [total counts and mitochondrial fraction were regressed out;] data were scaled with values clipped at I. Principal component analysis was computed and the first J components used to build a k-nearest-neighbour graph (k = K), followed by UMAP embedding and Leiden clustering at resolution L, yielding P clusters. Cluster markers were identified with [Wilcoxon rank-sum] tests. Cell identities were assigned from [marker panel / reference] and verified with [CellTypist/SingleR vX.Y, model name] applied without access to the manual labels. For differential expression between conditions, counts were aggregated per sample and cell type into pseudobulk profiles and tested with [DESeq2 vX.Y] using the model ~ [covariates] + condition; genes with Benjamini–Hochberg adjusted p < 0.05 and |log2 fold change| > Q were considered differentially expressed. Analysis code is available at [repository/DOI].

The omissions that trigger revision

  • No unit of replication. If the text does not say whether the test was per cell or per subject, a reviewer will ask — and the answer usually requires re-running. Why it matters.
  • Thresholds without effect sizes. Give the cells removed, not only the cut-offs.
  • Silent doublet handling. Saying nothing reads as doing nothing.
  • Resolution unstated. Cluster count is meaningless without it.
  • "Data available on request." Increasingly not accepted; deposit and cite the accession.

One paragraph you should also write

A short limitations note — sample size, batch structure, populations that were threshold-dependent. It reads as competence rather than weakness, and it pre-empts the reviewer who was going to point it out anyway. Our example deliverable includes one, and every project we deliver ships the filled-in methods paragraph so this is not the thing standing between you and submission.

Need this done rather than explained?

We do analysis only — send a count matrix, an h5ad/Seurat object or a public accession and get publication-ready results with the code that produced them. Fixed price agreed before work starts.

→ Get a fixed quote  ·  See a full sample deliverable

More guides