uniprotptmpy
Python library for parsing and querying the UniProt post-translational modification (PTM) controlled vocabulary.
- Zero core dependencies
- Bundled PTM data (748 entries) — works offline out of the box
- Typed, immutable data models (
py.typed/ PEP 561) - TSV/CSV export and round-trip
ptmlist.txtwriter - Optional FastAPI / Model Context Protocol server (
pip install uniprotptmpy[server])
Online Viewer
Click Me!
The same database is also reachable as a hosted REST + MCP service — see HTTP API and MCP Server below.
Installation
pip install uniprotptmpy
Or with uv:
uv add uniprotptmpy
Requires Python 3.12+. No third-party dependencies.
Quick Start
from uniprotptmpy import load
# Load the bundled PTM database
db = load()
print(len(db)) # 748
# Look up by accession
entry = db.get_by_id("PTM-0450")
print(entry.name) # (2-aminosuccinimidyl)acetic acid (Asn-Gly)
# Look up by name (case-insensitive)
entry = db.get_by_name("phosphoserine")
print(entry.id) # PTM-0253
# Free-text search across name, ID, target, and keywords
results = db.search("acetylation")
# Dict-style access (raises KeyError if not found)
entry = db["PTM-0450"]
# Iterate all entries
for entry in db:
print(entry.id, entry.name)
Chemical Formulas
entry = db.get_by_id("PTM-0476") # 3-hydroxyproline
print(entry.correction_formula) # O1
print(entry.dict_composition) # {'O': 1}
print(entry.proforma_formula) # O
Exporting to TSV/CSV
# Write all entries to a tab-separated file
db.write_tsv("ptms.tsv")
# Or CSV
db.write_tsv("ptms.csv", delimiter=",")
# Standalone function also available
from uniprotptmpy import write_tsv
write_tsv(db, "ptms.tsv")
Writing back to ptmlist.txt format
# Round-trip: write entries back to the original UniProt flat-file format
db.write_ptmlist("out/ptmlist.txt")
# Re-parse the written file — identical entry count and field values
from uniprotptmpy import parse_ptm_list
db2 = parse_ptm_list("out/ptmlist.txt")
# Standalone function
from uniprotptmpy import write_ptmlist
write_ptmlist(db, "out/ptmlist.txt")
Downloading the Latest Data
from uniprotptmpy import download, load
path = download() # downloads to ~/.cache/uniprotptmpy/ptmlist.txt
db = load(path) # load from the downloaded file
HTTP API and MCP Server
The optional [server] extra ships a FastAPI app that exposes the same
database over a JSON REST API and over the
Model Context Protocol so language-model
tools can query the UniProt PTM vocabulary directly.
pip install uniprotptmpy[server]
uvicorn uniprotptmpy.server.app:app --reload
REST endpoints
| Method & path | Returns |
|---|---|
GET /api/health |
Service metadata and entry count. |
GET /api/entries?limit=&offset= |
Paginated full entries. |
GET /api/entries/{id} |
One full entry by accession (PTM-0450 or 0450). |
GET /api/entries/by-name/{name} |
One full entry by exact name. |
GET /api/search?q=&limit= |
Search hits as lightweight summaries. |
Search responses contain just {id, name, feature_type, target, monoisotopic_mass} to keep token cost low; call /api/entries/{id} on any
hit for the full record (including taxonomic ranges and cross-references).
MCP server
The same FastAPI app mounts an MCP endpoint at POST /mcp with three tools:
| Tool | Purpose |
|---|---|
get_by_id(id) |
Look up a single PTM by accession. |
get_by_name(name) |
Exact name lookup. |
search(query, limit=25) |
Free-text search returning summaries. |
Tool responses use MCP's structured-output mechanism: the server emits an
outputSchema per tool in tools/list and returns both structuredContent
(typed Pydantic instance) and content (text fallback) on tools/call, so
LLM clients can parse the response without re-reading the JSON string.
Configure your MCP-aware client to point at http://localhost:8000/mcp
(or wherever you deploy the app). Example with the Anthropic CLI:
claude mcp add uniprot-ptm http://localhost:8000/mcp --transport http
API Overview
| Symbol | Description |
|---|---|
load(source=None) |
Load the PTM database. Uses bundled data by default. |
download(dest=None) |
Download the latest ptmlist.txt from UniProt FTP. |
parse_ptm_list(path) |
Parse a ptmlist.txt file into a PtmDatabase. |
write_tsv(entries, path, *, delimiter) |
Write entries to a TSV (or CSV) file. |
write_ptmlist(entries, path) |
Write entries back to UniProt ptmlist.txt flat-file format. |
PtmDatabase |
Indexed collection with get_by_id(), get_by_name(), search(), write_tsv(), write_ptmlist(), iteration, and len(). |
PtmEntry |
Frozen dataclass with all PTM fields, plus dict_composition and proforma_formula properties. |
FeatureType |
StrEnum: CROSSLNK, MOD_RES, LIPID, CARBOHYD, DISULFID. |
CrossReference |
Frozen dataclass with database and accession fields. |
TaxonomicRange |
Frozen dataclass with taxon_name, tax_id, description, and raw fields. |
Development
just install # install dependencies with uv
just lint # ruff check
just format # ruff format
just ty # ty type check
just test # pytest
just check # lint + type check + test
Related Projects
| Package | Description |
|---|---|
| unimodpy | Parse and query the UNIMOD mass spectrometry modifications database |
| psimodpy | Parse and query the PSI-MOD protein modification ontology |
License
Release files for uniprotptmpy 0.2.0
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | |
|---|---|---|---|
| uniprotptmpy-0.2.0.tar.gz | 126.7 kB | Details |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| uniprotptmpy-0.2.0-py3-none-any.whl | Python 3 | none | any | Details |
Total release size: 198.1 kB
Release files / uniprotptmpy-0.2.0.tar.gz
| Download URL | uniprotptmpy-0.2.0.tar.gz |
|---|---|
| Size | 126.7 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
5c4d2128c004924e9fa92393c84e99a4e4cae3a5026b2b4b7baefcfd70816970
|
|
BLAKE2b-256 checksum How to use checksums |
a48f21e6f149099db85d7afab3aff95fcff07dacbf2cf14509a5d6cd80e676fc
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/7.0.0 CPython/3.13.14
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Sep 23, 2026.
Transparency logRelease files / uniprotptmpy-0.2.0-py3-none-any.whl
| Download URL | uniprotptmpy-0.2.0-py3-none-any.whl |
|---|---|
| Size | 71.5 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
47266896983dfc71b3140182230aa45a14674c0c97a202b1652f47025362d1a8
|
|
BLAKE2b-256 checksum How to use checksums |
97e4566e56a7fbd6e2bc6f9c0e3494f12728162a043e1470cb5c4533d0d92fbd
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/7.0.0 CPython/3.13.14
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Sep 23, 2026.
Transparency log