pbcheck audit of 'scaled_liver_atlas.h5ad'
pbcheck 0.1.0, generated 2026-09-01T12:00:00Z.
Status: naive_only (no counts matrix passed the raw-count check)
This is a pbcheck v0.1.0 audit of one stratum of one file. It measures how a naive per-cell test and a donor-pseudobulk test behave on this data under a donor-permutation null. It is run outside pbcheck's pre-registered Phase 0 protocol, is not a Phase 0 measurement, and makes no claim about any publication or about whether any reported result is true.
Under donor permutation, with no true signal to find, the naive per-cell test calls a median of 41 genes (0.5% of the 6120-gene universe; Monte-Carlo SE 0.63) over 1000 permutations; on the real labels it calls 63. Both counts are corrected over the whole universe on their own (solo BH).
The naive arm's inflation factor lambda is 3.21 (IQR 0.44): above the band 0.9 to 1.1, which is the donor-pseudobulk arm's band, shown here to describe the naive number and not as the naive arm's own criterion.
The donor-pseudobulk arm was not run: no counts matrix passed the raw-count check.
11 donors in 'lupus_nephritis', 10 in 'healthy'; 352716 distinct donor splits exist.
Real-label calls over the permutation floor: the per-cell arm calls 1.54 times its own floor, both counts corrected over the whole universe on their own (solo BH).
Amendment 3 declares an operating envelope for the pseudobulk arm on synthetic oracles. For each donor-variance point it states the donor count per group at which the power target is reached, and each row says what the committed grid supports there: a point measured on the grid, or a count derived or extrapolated from it.
sigma_donor 0.2: at least 4 donors per group (power at least 0.6 at log2FC 1.0 in 200 genes; grid support 'not in the grid; Amendment 1 frontier only')
sigma_donor 0.35: at least 8 donors per group (power at least 0.6 at log2FC 1.0 in 200 genes; grid support 'ebayes power 0.793 at 8v8 (calibrated) -> n* <= 8')
sigma_donor 0.5: at least 13 donors per group (power at least 0.6 at log2FC 1.0 in 200 genes; grid support 'ebayes power 0.486 at 12v12, the largest n tested -> n* > 12')
sigma_donor 0.7: at least 23 donors per group (power at least 0.6 at log2FC 1.0 in 200 genes; grid support 'ebayes power 0.003 at 8v8 -> n* far above 8')
The arm's calibration was evaluated at one hard regime (sigma_donor 0.5, 8 against 8 donors) and nowhere else. pbcheck does not estimate sigma_donor for real data, so whether this stratum lies inside that envelope is not determined here.
Everything in this report is a diagnostic of this file: the naive arm's inflation factor and permutation floor, the pseudobulk arm's inflation factor, floor and false-positive rate as its negative control, and the bookkeeping of the shared gene universe. None of it is a Phase 0 result, and pbcheck does not rate this file against the Phase 0 decision rule.
The count matrix failed the raw-count check ('3812 of 4,000,000 scanned values are not integers'). The pseudobulk arm was dropped, never rounded, so this run has no negative control. The naive arm was run on the matrix as found, with the naive pipeline's own normalisation and log transform applied on top of it; its numbers describe that pipeline on this matrix and are not comparable to a run on raw counts.
No cell type was selected, so all cells were pooled into one stratum; the file has a column that looks like a cell-type annotation ('cell_type'). Pooling mixes composition shifts between conditions into the contrast; rerun with --celltype 'cell_type' --celltype-value <level> for a per-cell-type audit.
lambda: the genomic inflation factor: the ratio of observed test statistics to the null expectation, with 1.0 meaning no inflation.
permutation floor: the number of genes a test calls under donor permutation, when condition labels carry no real signal; it is the test's own false-positive baseline on this data.
donor-permutation null: the null distribution built by reassigning condition labels between donors, keeping every donor's cells together, and rerunning the test on each reassignment.
gene universe: the fixed set of genes both arms are tested and corrected over, frozen before either arm sees the real labels.
replication unit: the unit whose independent draws the statistics assume; for donor data that unit is the donor, not the cell.
thin-donor filter: the rule that drops a donor's pseudobulk profile when it is built from too few cells or too few counts, rather than keeping a noisy profile.
operating envelope: the region of donor count and donor-to-donor variability that Amendment 3 declares for the pseudobulk arm on synthetic data; each of its points states the donor count per group at which the power target is reached, on the committed grid or by the derivation the grid support of that point names.
sigma_donor: a knob of pbcheck's synthetic simulator for how much donors differ from each other; it cannot be measured on your data, which is why the envelope question is left open.
Monte-Carlo SE: the standard error of a quantity estimated from a finite number of permutations; it shrinks as more permutations are drawn.
BH convention (solo vs paired): solo BH corrects an arm's p-values over the whole gene universe on its own; paired BH corrects both arms together over the genes common to both, so their real-label counts are directly comparable.
| group | donors (pre-filter) | pseudobulk profiles (post-filter) |
|---|---|---|
| lupus_nephritis | 11 | n/a |
| healthy | 10 | n/a |
| donor | cells |
|---|---|
| donor_00 | 620 |
| donor_01 | 605 |
| donor_02 | 590 |
| donor_03 | 575 |
| donor_04 | 560 |
| donor_05 | 545 |
| donor_06 | 530 |
| donor_07 | 515 |
| donor_08 | 500 |
| donor_09 | 485 |
| donor_10 | 470 |
| donor_11 | 455 |
| donor_12 | 440 |
| donor_13 | 425 |
| donor_14 | 410 |
| donor_15 | 395 |
| donor_16 | 380 |
| donor_17 | 365 |
| donor_18 | 350 |
| donor_19 | 335 |
No batch columns were provided.
| Field | Value |
|---|---|
| donor nests in condition | True |
| imbalance ratio | 1.07 |
| usable for pseudobulk | True |
| flags | none |
| Field | Value |
|---|---|
| dropped, other condition | 1500 |
| dropped, other cell type | 600 |
| dropped, missing donor | 90 |
| dropped, missing condition | 40 |
| dropped, missing cell type | 20 |
| Field | Value |
|---|---|
| source | n/a |
| passed | False |
| reason | 3812 of 4,000,000 scanned values are not integers |
| dtype | float32 |
| values scanned | 4000000 |
Examples of the values checked: 0.0, 1.34, 2.71, 0.0.
| Field | Value |
|---|---|
| real-label calls, solo BH | 63 |
| gene | pval | padj | log2fc | pct group | pct reference |
|---|---|---|---|---|---|
| GOLGA8A | 2.1e-06 | 0.00014 | 1.83 | 71.2 | 22.5 |
| <b> | 3.4e-05 | 0.00089 | -1.21 | 12 | 44.3 |
| TXN2 | 9e-05 | 0.0019 | 0.97 | 55.5 | 30.1 |
| Field | Value |
|---|---|
| lambda | 3.21 |
| lambda IQR | 0.44 |
| class | above_band |
| Field | Value |
|---|---|
| median count | 41 |
| median fraction | 0.005 |
| IQR count | 12 |
| bh mode | solo |
| Monte-Carlo SE | 0.63 |
The paired floor is not shown: the pseudobulk arm left 6120 genes without a value, so a paired correction over the two arms would not cover the same genes; the solo floor above stands alone.
| Field | Value |
|---|---|
| requested | 1000 |
| achieved | 1000 |
Machinery check of the permutation engine, not a criterion of any kind: the inflation factor of the empirical permutation p-values is 1.02.
Donor-pseudobulk arm: not run, because no counts matrix passed the raw-count check.
| Field | Value |
|---|---|
| size | 6120 |
| minimum size | 200 |
| builder | naive_detection_fallback |
Builder rule: a gene is kept when it has a value greater than 0 in at least one cell of at least half the donors, computed on the matrix as found; no count-sum rule applies to a non-integer matrix
Thin-donor filter: not run.
| Field | Value |
|---|---|
| common tested | 0 |
| dropped for fairness | 0 |
| no value in naive arm | 0 |
| no value in pseudobulk arm | 6120 |
| pseudobulk arm complete for every gene | False |
| Field | Value |
|---|---|
| real split inside permutation range | n/a |
| real split percentile in permutations | n/a |
| setting | value |
|---|---|
| n_perm_requested | 1000 |
| n_perm_pb_requested | 200 |
| seed | 0 |
| top_n | 20 |
| design_only | no |
| naive_method | wilcoxon |
| naive_engine | fast |
| pseudobulk_method | moderated_ebayes |
| trend | no |
| min_donors_per_group | 3 |
| universe_min_total_count | 15 |
| universe_min_prop | 0.5 |
| fallback_universe_min_prop | 0.5 |
| fallback_universe_min_size | 200 |
| min_profiles_per_group_after_thin_filter | 3 |
| protocol constant | value |
|---|---|
| alpha | 0.05 |
| lambda_band | [0.9, 1.1] |
| min_universe_size | 200 |
| min_cells | 10 |
| min_counts | 1000 |
| sigma_donor | min donors per group | grid support |
|---|---|---|
| 0.2 | 4 | not in the grid; Amendment 1 frontier only |
| 0.35 | 8 | ebayes power 0.793 at 8v8 (calibrated) -> n* <= 8 |
| 0.5 | 13 | ebayes power 0.486 at 12v12, the largest n tested -> n* > 12 |
| 0.7 | 23 | ebayes power 0.003 at 8v8 -> n* far above 8 |
| package | version |
|---|---|
| numpy | 1.26.4 |
| scipy | 1.13.1 |
| pandas | 2.2.2 |
| anndata | 0.10.7 |
| scanpy | 1.10.1 |
| statsmodels | 0.14.2 |
| decoupler | 1.7.0 |
| pydeseq2 | 0.4.10 |
| Field | Value |
|---|---|
| platform | Windows-10-10.0.26200 |
| python | 3.12.4 |
| stage | seconds |
|---|---|
| load | 3.1 |
| prepare | 0.4 |
| design | 0.2 |
| counts | 0.6 |
| pseudobulk_build | 1.8 |
| universe | 0.3 |
| real_label | 5.2 |
| permutation_null | 30.9 |
| render | 0.2 |
The engine was measured on one synthetic oracle point (sigma_donor 0.5, 8 against 8 donors, 1500 genes), recorded in pilot/gate/synthetic_gate_2026-08-15.json; that measurement is not repeated on this file. Of the settings below, only the ones listed as protocol constants are pre-registered values taken from pbcheck.gate_config (alpha, lambda_band, min_universe_size, min_cells, min_counts); the permutation counts, the universe filter parameters, the fallback universe rule and the display settings are the tool's own and are not protocol values.
Generated by pbcheck 0.1.0. Protocol: docs/PHASE0_SPEC.md and docs/AMENDMENTS.md in the pbcheck repository.