Metadata-Version: 2.4
Name: msiverse
Version: 0.1.0
Summary: Pure-Python MSI analysis with Cardinal-compatible imzML matrix construction
Author: msiverse contributors
License: BSD-3-Clause AND Artistic-2.0 AND GPL-2.0-or-later
Project-URL: Repository, https://github.com/aqgy2749/MSI-DataProcess-Package
Keywords: mass-spectrometry-imaging,MALDI,MSI,imzML,anndata
Classifier: Development Status :: 2 - Pre-Alpha
Classifier: Intended Audience :: Science/Research
Classifier: License :: OSI Approved :: BSD License
Classifier: Programming Language :: Python :: 3
Classifier: Programming Language :: Python :: 3.10
Classifier: Programming Language :: Python :: 3.11
Classifier: Programming Language :: Python :: 3.12
Classifier: Topic :: Scientific/Engineering :: Bio-Informatics
Requires-Python: <3.13,>=3.10
Description-Content-Type: text/markdown
Requires-Dist: numpy>=1.22
Requires-Dist: scipy>=1.9
Requires-Dist: pandas>=1.5
Requires-Dist: anndata>=0.9
Requires-Dist: mudata>=0.2
Requires-Dist: scikit-learn>=1.2
Requires-Dist: annoy<2,>=1.17
Requires-Dist: pyarrow>=12
Requires-Dist: pyimzML>=1.5
Provides-Extra: images
Requires-Dist: Pillow>=9; extra == "images"
Provides-Extra: lipids
Requires-Dist: pygoslin<2.3,>=2.2.5; extra == "lipids"
Provides-Extra: plots
Requires-Dist: matplotlib>=3.6; extra == "plots"
Requires-Dist: seaborn>=0.12; extra == "plots"
Requires-Dist: plotly>=5.18; extra == "plots"
Requires-Dist: ipywidgets>=8; extra == "plots"
Requires-Dist: anywidget>=0.9; extra == "plots"
Requires-Dist: networkx>=3; extra == "plots"
Provides-Extra: metaspace
Requires-Dist: Pillow>=9; extra == "metaspace"
Requires-Dist: pypng>=0.20220715.0; extra == "metaspace"
Requires-Dist: requests>=2.28; extra == "metaspace"
Provides-Extra: ms1-id
Requires-Dist: ms1_id==0.2.1; extra == "ms1-id"
Provides-Extra: alignment
Requires-Dist: torch==2.0.0; extra == "alignment"
Requires-Dist: pynrrd==1.0.0; extra == "alignment"
Provides-Extra: all
Requires-Dist: Pillow>=9; extra == "all"
Requires-Dist: pypng>=0.20220715.0; extra == "all"
Requires-Dist: pygoslin<2.3,>=2.2.5; extra == "all"
Requires-Dist: matplotlib>=3.6; extra == "all"
Requires-Dist: seaborn>=0.12; extra == "all"
Requires-Dist: plotly>=5.18; extra == "all"
Requires-Dist: ipywidgets>=8; extra == "all"
Requires-Dist: anywidget>=0.9; extra == "all"
Requires-Dist: networkx>=3; extra == "all"
Requires-Dist: requests>=2.28; extra == "all"
Requires-Dist: ms1_id==0.2.1; extra == "all"
Requires-Dist: torch==2.0.0; extra == "all"
Requires-Dist: pynrrd==1.0.0; extra == "all"
Provides-Extra: dev
Requires-Dist: pytest>=7.0; extra == "dev"
Requires-Dist: pytest-cov>=4.0; extra == "dev"
Requires-Dist: ruff>=0.1; extra == "dev"

# MSIverse 0.1.0

MSIverse is a pure-Python port of the user-facing analysis, plotting, and
interactive functions in SpaMTP 1.1.0.9000. Single-modality data use `AnnData`; aligned
spatial metabolomics/transcriptomics use `MuData`.

The imzML reader and public-axis matrix construction are pure-Python ports of
Cardinal 3.14.0, CardinalIO 1.10.0, and matter 2.14.0. There is no R/rpy2
runtime dependency.

## Install

Run these commands from the project directory containing `pyproject.toml`.

```bash
python -m pip install -e .
python -m pip install -e '.[all]'
python -m pip install -e '.[ms1-id]'
```

Python 3.10–3.12 is supported. `pyimzML` is installed for imzML writing;
Plotting/Notebook controls, METASPACE, Pillow, and pygoslin remain optional
extras so importing the core analysis package stays lightweight.

## Data conventions

- `adata.X`: current analysis matrix.
- `adata.layers["counts"]`: unnormalised intensity loaded from the source.
- `adata.var["mz"]`: common m/z feature axis.
- `adata.obsm["spatial"]`: x/y coordinates.
- `adata.obsm`, `adata.varm`, and `adata.obsp`: reductions, loadings, and graphs.
- `adata.uns["msi"]`: schema and input/spectrum modes.
- `adata.uns["read_imzml"]`, `["peak_align"]`, `["bin_spectra"]`: input and common-axis records.
- `adata.uns["normalize"]`, `["pca"]`, `["spatial_pca"]`, etc.: functional records with
  `params`, `provenance`, `outputs`, optional `resolved`, and function-specific results.
- `adata.uns["mz_annotation"]`: base candidates; `["annotation_evidence"]`: candidates
  augmented with MS1-ID support. Evidence integration preserves the `["ms1_id"]` run record.
- `mdata.mod["spm"]` / `mdata.mod["spt"]`: metabolomic/transcriptomic modalities.

Object-transforming functions modify in place by default and accept
`copy=True` when a separate object is required.

Named runs use `key_added`; readers select inputs explicitly (for example
`annotation_key="anno_hmdb"`). Normalization stores a custom run in both
`uns[key_added]` and `layers[key_added]`; PCA retains `X_<key_added>` and
`<key_added>_loadings`. Existing defaults and explicit matrix/column arguments
remain supported. Reusing a key replaces that run; unrelated operation keys
are rejected. These records are named results, not an automatic history log.

Old objects remain readable through package adapters. To convert their metadata
explicitly, use `io.migrate_uns(adata, copy=True, drop_legacy=False)`. Add
`return_report=True` to return `(converted, report)`. Migration is atomic on
conflicts and preserves unknown fields; it does not rewrite saved files.
Direct notebook access to old paths must be updated to the new layout.

## Modules

| Module | SpaMTP-derived capabilities |
|---|---|
| `msiverse.io` | Cardinal-compatible imzML parsing/alignment/binning, table loading, and output |
| `msiverse.preprocess` | normalization, TMM, subsetting, segmentation labels |
| `msiverse.annotate` | SpaMTP indexed annotation, isotope/adduct-network scoring, MALDI rules, FMP10, and official MS1-ID integration |
| `msiverse.analysis` | PCA, spatial KNN/GraphPCA, k-means, Cardinal-compatible unsupervised SSC, correlation and spatial variability |
| `msiverse.differential` | deterministic pseudo-bulk and moderated differential analysis |
| `msiverse.spatial` | coordinate mapping, precomputed/landmark affine and STalign LDDMM transforms, interactive alignment, ROI selection, images |
| `msiverse.multiomics` | modality merging and weighted-nearest-neighbour integration |
| `msiverse.pathway` | Fisher, regional, GESECA, pathway scoring, annotation statistics, pathway plots |
| `msiverse.network` | pathway topology construction and interactive HTML rendering |
| `msiverse.plotting` | spatial, spectrum, distribution, heatmap, density, and 3D plots |
| `msiverse.metaspace` | GraphQL annotations, ion images, feature matrices, and AnnData loading |

```python
from msiverse import annotate, io, preprocess, analysis

adata = io.read_imzml("sample.imzML", as_="annData")
preprocess.normalize(adata, method="tic")
analysis.run_pca(adata, n_components=20)
result = annotate.annotate(adata, polarity="negative", ppm=5, maldi_matrix="9-AA")

from msiverse import plotting
figure = plotting.image_mz_plot(adata, mzs=[400.2], pixel=True)
interactive = plotting.density_map(adata, output_html="density.html")
```

To specify the spectrum representation explicitly, use `spectrum_mode`:

```python
adata = io.read_imzml("sample.imzML", as_="annData", spectrum_mode="centroid")
# For profile spectra, use spectrum_mode="profile".
```

The default `spectrum_mode="auto"` uses file-level or spectrum-level declarations.
For non-continuous data, only a detected centroid declaration selects peak
alignment; profile or undeclared spectra use a regular axis with linear resampling.
Explicit `"centroid"`/`"profile"` overrides the declaration for either output type.
Continuous data still uses its existing shared m/z axis. `parse_only=True`
returns the original declarations, even when an explicit mode is supplied.

For large processed imzML files, keep the binary arrays lazy and materialize
only the pixels needed for an exploratory comparison. The reference m/z axis
is still estimated from a uniform sample of the full acquisition.

```python
arrays = io.read_imzml(
    "sample.imzML", memory=False, as_="arrays", spectrum_mode="centroid"
)
adata = io.convert_arrays_to_experiment(
    arrays, guess_max=1000, pixel_indices=range(min(1000, len(arrays)))
)
```

See [MSIverse_User_Guide.md](MSIverse_User_Guide.md) for usage and
[SPAMTP_PARITY.md](SPAMTP_PARITY.md) for the complete SpaMTP API map.

## Bundled data and licensing

The Python-native Parquet snapshots were converted from SpaMTP's bundled
reference resources. They retain their upstream restrictions, including
non-commercial/academic conditions for HMDB and KEGG-derived content. Review
`THIRD_PARTY_NOTICES.md` before redistribution.
