protein-mcp-server
About
Protein structures (PDB, UniProt)
Details
- Transport
- SSE
Explore
Setting up with Highlight
This MCP is not yet compatible with Highlight’s one-click setup. However, you can still use it with Highlight by following these steps:
- Download and install Highlight from highlightai.com/download
- Navigate to the plugins tab and select "Add Custom Plugin"
-
Configure the plugin with the settings below
Plugin Name
protein-mcp-serverCommand (node, npx, python, etc.)Please refer to the README for specific instructions on how to obtain API keys or other required environment variables.
- Enable "Start Automatically" if you want the plugin to start when Highlight launches
protein_search_structures
Search experimental (PDB) and predicted (computed-model) protein structures by free text, protein sequence (triggers an mmseqs2 similarity search), and/or organism, method, and resolution filters. Returns ranked hits; the experimental page is enriched with title, method, resolution, and organism. Chain hit IDs into protein_get_structure. Optionally returns a facet breakdown (counts by method / organism / release year / …) alongside the hits at no extra call. A facet on a dimension you are alr…
protein_get_structure
Fetch structures with metadata and coordinate-file URLs. source "experimental" takes PDB entry IDs (batched in one call); "predicted" takes UniProt accessions (AlphaFold, with pLDDT/PAE confidence); "best_available" takes UniProt accessions and returns the top federated model — the highest-resolution experimental structure if one exists (optimizing resolution, not biological representativeness, so it can return an engineered mutant over the wild-type entry), else the best prediction. Resolves…
protein_find_similar
Find structurally or evolutionarily related proteins. by:"sequence" runs an RCSB mmseqs2 sequence-similarity search (synchronous) over a sequence — supplied directly, or pulled from a PDB ID or UniProt accession. by:"structure" runs a Foldseek fold-similarity search (asynchronous) against experimental and predicted databases; if the job is still computing when the poll budget elapses, the response reports status "computing" with a ticket — re-call with ticket_id set to that value to resume th…
protein_track_ligands
Ligand discovery and binding-site analysis across the PDB. mode "find_ligand" resolves a name or formula to chemical component IDs with metadata (formula, weight, SMILES), ranked by deposition frequency — most-deposited component first, so the top hit is the most common match for the name, not necessarily an exact name-string match. mode "structures_with_ligand" returns PDB entries containing a ligand (by exact component ID — get the ID from find_ligand first), highest-resolution first, each …
protein_compare_structures
Structurally align multiple structures (up to the configured batch cap) via the RCSB Structural Comparison service (TM-align / jFATCAT). reference:"first" aligns every structure to the first; reference:"all_pairs" computes the full pairwise matrix. Each pair is an independent async alignment job, fanned out with a concurrency cap and per-pair partial success — a pair still computing when the budget elapses returns status "computing" with its job UUID, and a failed pair degrades its row withou…
protein_analyze_collection
Profile the PDB into distributions and trends over an optional scoping query: counts by method, organism, or polymer composition; resolution and molecular-weight histograms; release-year timelines; and multidimensional cross-tabs (e.g. method × release_year). Aggregation runs server-side at RCSB — one call returns compact buckets, no row pull. Pass one group_by dimension for a single breakdown, or two for a cross-tab (the first nests the second).
protein_get_annotations
Sequence and functional annotation for a protein: UniProt features (domains, binding sites, PTMs), natural variants, and InterPro domain/family memberships (Pfam, PROSITE, …) with GO terms. Provide a UniProt accession directly, or a PDB ID — it is resolved to its UniProt accession via the structure's sequence cross-reference. A multi-chain PDB entry can map to several accessions; the default pick is deterministic (lowest author chain ID) and the alternatives are listed in "ambiguity" — pass "…
Claude Desktop / Cursor
Paste into your MCP client config file to install this server.
{
"mcpServers": {
"protein-mcp-server": {
"server": {
"command": "npx",
"args": [
"-y",
"protein-mcp-server",
"run",
"start:stdio"
],
"env": {
"MCP_LOG_LEVEL": ""
}
}
}
}
}
McpServers
{
"server": {
"command": "npx",
"args": [
"-y",
"protein-mcp-server",
"run",
"start:stdio"
],
"env": {
"MCP_LOG_LEVEL": ""
}
}
}
Transport
"stdio"
Package
"protein-mcp-server"
Registry
"npm"
Public Hosted Server:https://protein.caseyjhand.com/mcp
Seven tools spanning the structure-research arc — discover, fetch, find homologs, track ligands, compare, profile the corpus, and annotate — over experimental (PDB) and predicted (AlphaFold) structures from one surface:
Federated search across experimental (PDB) and predicted (computed-model) structures via RCSB Search v2.
- Free-text, protein-sequence (triggers an mmseqs2 similarity search), and organism / method / resolution filters
- content_typescopes the search toexperimental,predicted, orall— the defaultallis a genuine union of both universes, so computed models appear alongside PDB entries
- Every hit names itssource; experimental hits are enriched with title, method, resolution, and organism, while computed models carry the UniProt accession parsed from their ID
- Optionalfacetsreturn a method / organism / release-year breakdown alongside the hits at no extra call, each reporting how many matches carry no value for that dimension; each dimension may be listed once
- Chain hit IDs straight intoprotein_get_structure
Fetch structures with metadata and coordinate-file URLs, resolving across providers bysource.
- source: experimentaltakes PDB entry IDs, batched in one RCSB GraphQL call; it also resolves the computed-model IDs search returns (AF_/MA_), which come back assource: predictedcredited to their modelling provider
- source: predictedtakes UniProt accessions and returns the AlphaFold model with pLDDT/PAE confidence
- source: best_availabletakes UniProt accessions and returns the top federated model (experimental if one exists, else the best prediction)
- Per-ID partial success — unresolved IDs are listed infailed[], not a batch-level error
- include_coordsinlines coordinate content; when a batch overflows the response budget it returns a per-structure size outline, so you can re-call withsections: [ids]for specific structures
- Every response carries anattributionblock naming the upstream data licenses and citations (seeUpstream data licensing)
Find structurally or evolutionarily related proteins, by sequence or by fold.
- by: sequenceruns a synchronous RCSB mmseqs2 search;by: structureruns an asynchronous Foldseek search against experimental and predicted databases
- Query from a raw one-letter sequence, a PDB ID, or a UniProt accession
- Foldseek targets default topdb100+afdb50; override viadatabases(e.g.afdb-swissprot,BFVD)
- Async jobs that exceed the poll budget returnstatus: computingwith aticketId— re-call withticket_idset to that value to poll the same job instead of resubmitting
- Each hit names the engine and source database it came from
Ligand discovery and binding-site analysis across the PDB.
- mode: find_ligandresolves a name or formula to chemical component IDs with formula, weight, SMILES, and InChIKey
- mode: structures_with_ligandreturns PDB entries containing a ligand by exact component ID
- mode: binding_sitereturns the protein residues lining a ligand's pocket in a structure, with contact distances
- Binding sites are experimental-only — computed from deposited coordinates (predicted models carry no bound ligands)
Structural alignment of multiple structures (up to the configuredPROTEIN_MAX_COMPARE_STRUCTUREScap) via the RCSB Structural Comparison service.
- Methods:tm-align,fatcat-rigid,fatcat-flexible
- reference: firstaligns every structure to the first;reference: all_pairscomputes the full pairwise matrix
- Optional per-structurechainrestricts the alignment to a single chain
- A structure repeated instructures[]is compared once — the repeat would only add a self-alignment and a mirrored pair, which the resume mechanism cannot tell apart from the original
- Each pair is an independent async job, fanned out with a concurrency cap and per-pair partial success — a pair still computing when the budget elapses returnsstatus: computingwith its jobuuid, and a failed pair degrades its row without sinking the others
- Re-call with a matching{ a, b, uuid }entry inresume[](copied from a prior response'spairs[]) to poll a computing pair's job instead of resubmitting
- Returns TM-score, RMSD, and aligned-residue count per pair, plusmodeledResiduesandcoverage— each a[a, b]tuple, with coverage a 0–100 percentage of that structure's own modeled-residue count
Profile the PDB into distributions and trends over an optional scoping query — backed by RCSB's server-side facet engine (one call, compact buckets, no row pull).
- Group bymethod,organism,polymer_type,resolution,release_year, ormolecular_weight
- Onegroup_bydimension for a breakdown, or two distinct dimensions for a cross-tab (the first nests the second); a repeated dimension is rejected
- intervalsets the bin width for value histograms or the period for date histograms (year/month/quarter)
- Scope with a free-textquery,organism,method, ormax_resolution;content_typeselects the structure universe
- bucket_limitcaps buckets per dimension level, not per response — a cross-tab applies it separately to the parent dimension and to the nested child inside each parent bucket, so up tobucket_limit × (1 + bucket_limit)buckets come back. Each level flags its own truncation, andbucketsReturnedgives the realized total
- Every dimension reportsmissingValueCount— matches in scope carrying no value for that attribute, which therefore fall in no bucket (aresolutionbreakdown does not cover NMR entries, and neithermethodnorresolutioncovers computed models)
Sequence and functional annotation for a protein.
- UniProt features (domains, binding sites, PTMs) and natural sequence variants
- InterPro domain/family memberships (Pfam, PROSITE, …) with associated GO terms
- Provide a UniProt accession directly, or a PDB ID — resolved to a UniProt accession via the structure's sequence cross-reference
- A multi-chain PDB entry can map to several accessions; the default is the deterministic lowest-author-chain pick, with the alternatives listed underambiguity. Passchain(an author chain ID, e.g.A) to select a specific one
- includescopes which annotation classes are fetched:features,domains,variants, orall
- Every response carries anattributionblock naming the upstream data licenses and citations (seeUpstream data licensing)
All resource data is also reachable via tools —pdb://{entry_id}mirrorsprotein_get_structureforsource: experimental, andaf://{uniprot}mirrors it forsource: predicted. Many MCP clients are tool-only and don't surface resources; the summaries remain reachable through the tools.
- Declarative tool and resource definitions — single file per primitive, framework handles registration and validation
- Unified error handling — handlers throw, framework catches, classifies, and formats
- Pluggable auth:none,jwt,oauth
- Swappable storage backends:in-memory,filesystem,Supabase,Cloudflare KV/R2/D1
- Structured logging with optional OpenTelemetry tracing
- STDIO and Streamable HTTP transports
- One federated surface over experimental (PDB) and predicted (AlphaFold / 3D-Beacons) structures — search, fetch, and compare treat both universes the same
- Keyless across every upstream — RCSB, AlphaFold DB, 3D-Beacons, UniProt, InterPro, and Foldseek, no API keys to provision
- Corpus analytics run server-side on RCSB's facet engine — distributions, histograms, and cross-tabs in one call, no row pull and no SQL workspace
- Async alignment and Foldseek jobs poll within a bounded budget and hand back a job ticket (ticketId/ per-pairuuid) instead of blocking — re-call withticket_idor aresume[]entry to poll the same job instead of resubmitting
- Provenance on every response — each hit carries asource(experimental/predicted), the engine and database that produced it, and effective-query / total-count echoes so agents can reason about coverage
- Graceful partial failure — batch fetches and pairwise comparisons return per-item rows (failed[], per-pairstatus) instead of failing the whole request, each with actionable recovery text
- Discriminated output contracts — typedsourceandstatusunions,computingresults with resume tickets, and budget-overflow outlines let callers branch on data, not string parsing
A public instance is available athttps://protein.caseyjhand.com/mcp— no installation required. Point any MCP client at it via Streamable HTTP:
{ "mcpServers": { "protein": { "type": "streamable-http", "url": "https://protein.caseyjhand.com/mcp" } } }
Add the following to your MCP client configuration file. No API key is required — every upstream provider is keyless.
{ "mcpServers": { "protein-mcp-server": { "type": "stdio", "command": "bunx", "args": ["@cyanheads/protein-mcp-server@latest"], "env": { "MCP_TRANSPORT_TYPE": "stdio", "MCP_LOG_LEVEL": "info" } } } }
{ "mcpServers": { "protein-mcp-server": { "type": "stdio", "command": "npx", "args": ["-y", "@cyanheads/protein-mcp-server@latest"], "env": { "MCP_TRANSPORT_TYPE": "stdio", "MCP_LOG_LEVEL": "info" } } } }
{ "mcpServers": { "protein-mcp-server": { "type": "stdio", "command": "docker", "args": ["run", "-i", "--rm", "-e", "MCP_TRANSPORT_TYPE=stdio", "ghcr.io/cyanheads/protein-mcp-server:latest"] } } }
For Streamable HTTP, set the transport and start the server:
MCP_TRANSPORT_TYPE=http MCP_HTTP_PORT=3010 bun run start:http # Server listens at http://localhost:3010/mcp
git clone https://github.com/cyanheads/protein-mcp-server.git
All upstream providers are keyless, so the server runs out of the box with no configuration. Every variable below is optional.
See.env.examplefor the full list of provider base-URL overrides and tuning limits.
# One-time build bun run rebuild # Run the built server bun run start:stdio # or bun run start:http
bun run devcheck # Lint, format, typecheck, security bun run test # Vitest test suite bun run lint:mcp # Validate MCP definitions against spec
docker build -t protein-mcp-server . docker run --rm -e MCP_TRANSPORT_TYPE=http -p 3010:3010 protein-mcp-server
The Dockerfile defaults to HTTP transport, stateless session mode, and logs to/var/log/protein-mcp-server. OpenTelemetry peer dependencies are installed by default — build with--build-arg OTEL_ENABLED=falseto omit them.
SeeCLAUDE.md/AGENTS.mdfor development guidelines and architectural rules. The short version:
- Handlers throw, framework catches — notry/catchin tool logic
- Usectx.logfor request-scoped logging,ctx.statefor tenant-scoped storage
- Register new tools and resources via the barrels insrc/mcp-server//definitions/index.ts
- Wrap external API calls: validate raw → normalize to domain type → return output schema; never fabricate missing fields
Issues and pull requests are welcome. Run checks and tests before submitting:
Structure and annotation data comes from public upstream databases, each under its own license.protein_get_structureandprotein_get_annotationscarry anattributionblock on every response — the license, citation, and homepage for each source that contributed to that specific response — so the attribution obligation travels with the data to downstream consumers rather than living only here. CC BY / CC BY-SA sources require attribution on redistribution; CC0 sources are citation-only (attribution encouraged, not required).
best_availablefederates predicted models through3D-Beacons, so theattributionblock credits the actual contributing provider (AlphaFold DB, SWISS-MODEL, BFVD, …); a provider without a curated license entry carries aSee provider termsfallback pointing back to 3D-Beacons rather than a fabricated license. InterPro's own domain/family classifications are CC0; the GO terms carried alongside them are separately CC BY 4.0, so each is credited independently only when it actually contributes. Full citations for each source travel in theattributionblock of the relevant tool responses. This covers upstreamdata*licensing — the server's own code is licensed separately (seeLicense).
Access and interact with Allen Institute for Neural Dynamics (AIND) metadata directly within your IDE.
A high-performance JavaScript server for the Alliance of Genome Resources (AGR) MCP.
Access the AlphaFold Protein Structure Database for protein structure prediction and analysis.
Interface with Biomart, a biological data query tool, using the pybiomart Python package.
Agent-first rewrite of genomeoncology's BioMCP in TypeScript to provide next-gen biomedical data access for agents.
Perform complex queries on the DANDI Archive, a platform for neurophysiology data.
Interact with DROMA drug-omics association analysis databases using natural language.
A bridge to the Drug Gene Interaction Database (DGIdb) API, enabling AI clients to query drug-gene interaction data.
A search server for PubMed, the biomedical literature database, using a pure Node.js implementation.
Query the Materials Project database using the mp_api client. Requires an MP_API_KEY environment variable.
Sign in to leave a review
Use Google, GitHub, or an email account so ratings stay tied to real people.
No reviews posted yet.



