@cyanheads/pubmed-mcp-server

中文文档
2.12.0发布于 2026/11/03Apache-2.0TypeScriptES Module近 30 天下载 1.6万

Search PubMed/Europe PMC, fetch articles and full text (PMC/EPMC/Unpaywall), citations, MeSH terms via MCP. STDIO or Streamable HTTP.

原始使用文档
文档目录29 节
  1. Overview
  2. Tools
  3. Resources
  4. Prompts
  5. Capability reference
  6. pubmed_search_articles tool
  7. pubmed_fetch_articles tool
  8. pubmed_fetch_fulltext tool
  9. pubmed_europepmc_search tool
  10. pubmed_europepmc_fetch tool
  11. pubmed_fetch_citation_metrics tool
  12. pubmed_format_citations tool
  13. pubmed_find_related tool
  14. pubmed_spell_check tool
  15. pubmed_lookup_mesh tool
  16. pubmed_lookup_citation tool
  17. pubmed_convert_ids tool
  18. pubmed://database/info resource
  19. research_plan prompt
  20. Features
  21. Getting started
  22. Configuration
  23. Running the server
  24. Local development
  25. Docker
  26. Project structure
  27. Development guide
  28. Contributing
  29. License

@cyanheads/pubmed-mcp-server

Search PubMed/Europe PMC, fetch articles and full text (PMC/EPMC/Unpaywall), citations, MeSH terms via MCP. STDIO or Streamable HTTP.

12 Tools • 1 Resource • 1 Prompt

Version License Docker MCP SDK npm TypeScript Bun

Install in Claude Desktop Install in Cursor Install in VS Code

Framework

Public Hosted Server: https://pubmed.caseyjhand.com/mcp


Overview

Biomedical literature from PubMed, PubMed Central, and Europe PMC. Search it, fetch metadata and full text, resolve identifiers and partial citations, format references, and ground queries in MeSH vocabulary. Runs as a stdio process, a local Streamable HTTP server, or the public hosted endpoint above. Ships the pubmed-guide agent skill (skill://pubmed-guide/SKILL.md), which MCP clients read for PubMed query syntax, DOI-to-PMID routes outside PMC, reference-list resolution, citation counts, and full-text misses.

Tools

ToolDescription
pubmed_search_articlesSearch PubMed with full query syntax, structured filters, date ranges, and optional summaries
pubmed_fetch_articlesFetch article metadata by PMID: abstract, authors, journal, MeSH terms, databank accessions such as trial registration IDs, grants, a collective author's investigators on request, linked retraction and correction notices
pubmed_fetch_fulltextFetch full text by PMID, PMCID, or DOI, falling back from PMC to Europe PMC to Unpaywall
pubmed_europepmc_searchSearch Europe PMC for preprints, patents, Agricola, and open-access records PubMed doesn't carry
pubmed_europepmc_fetchFetch complete Europe PMC records, including the untruncated abstract, as records: [{ source, epmcId }]
pubmed_fetch_citation_metricsFetch NIH iCite citation metrics by PMID: Relative Citation Ratio, NIH percentile, citation counts and rates
pubmed_format_citationsFormat citations in APA 7th, MLA 9th, BibTeX, RIS, or Vancouver (ICMJE/NLM), with linked retraction and correction notices
pubmed_find_relatedFind similar articles, citing articles, or references for a PMID
pubmed_spell_checkCorrect a misspelled PubMed query via NCBI ESpell
pubmed_lookup_meshLook up MeSH headings with tree numbers, scope notes, and entry terms
pubmed_lookup_citationResolve partial references, up to 25 at a time, to PMIDs via ECitMatch
pubmed_convert_idsConvert between DOI, PMID, and PMCID via the PMC ID Converter

Resources

ResourceDescription
pubmed://database/infoPubMed database metadata via EInfo (field list, record count, last update)

Prompts

PromptDescription
research_planGenerate a structured four-phase biomedical research plan

Capability reference

pubmed_search_articles tool

  • Full PubMed query syntax plus filters (author, journal, MeSH, publication type, language, species, abstract, free full text) and publication/modification/Entrez date ranges
  • query is optional: with an author, journal, MeSH, or publication-type filter, the filters alone make the search (a journal's output over a date range, for example)
  • Up to 1,000 results per page and offsets up to 9,998, or maxResults: 0 for the match count alone; summaryCount adds briefs for up to 50 hits. A larger page size is served at the cap with a notice naming where to continue
  • Reports totalCount, the effectiveQuery PubMed ran, and the appliedFilters
  • Rejects blank filter values, impossible dates, and reversed date ranges before PubMed is called

pubmed_fetch_articles tool

  • Up to 200 PMIDs per call; misses are listed in unavailablePmids
  • Abstract, authors, journal, DOI, publication types, linked retraction/erratum/comment notices, and links; MeSH terms on by default, grants via includeGrants, and the members of a collective author (its InvestigatorList, thousands on some consortium trials) via includeInvestigators
  • A retracted, corrected, or questioned article opens with the same notice block as pubmed_format_citations, directly under its title
  • dataBanks lists the record's trial registrations and data deposits (ClinicalTrials.gov NCT IDs, GenBank and PDB accessions, Dryad DOIs) verbatim; search pubmed_search_articles for <accession>[si] to find other records citing one
  • recordType separates journal articles from Bookshelf chapters and books; opt-in maxResponseCharacters defers overflow to deferred.ids

pubmed_fetch_fulltext tool

  • pmcids, pmids, and dois in any mix, up to 50 distinct identifiers per call: the first 10 are fetched and the rest returned in overLimit for a follow-up call. Each is tried against PMC, then Europe PMC, then Unpaywall (needs UNPAYWALL_EMAIL); an article several of them name is fetched and returned once, and viaSource names the tier that answered
  • source: "pmc" returns sections (the body, then back matter such as acknowledgments, declarations, and appendices), tables, and figures; source: "unpaywall" returns a best-effort HTML or PDF text body
  • Europe PMC full text is fetched for records Europe PMC marks open access, preprints included; articles carry the licenses their PMC JATS states
  • Misses carry a typed reason and triedTiers; sections, maxSections, maxCharacters, overflowMode, and maxResponseCharacters bound the response, truncation reports what was cut, and sectionCap names the sections maxSections cut

pubmed_europepmc_search tool

  • Adds preprints (PPR), patents (PAT), and Agricola (AGR) to MED and PMC; defaults to MED, PMC, PPR
  • Cursor pagination via cursorMark / nextCursorMark, up to 100 per page; a larger page size is served at the cap with a notice naming where to continue. Abstracts arrive as 400-character snippets
  • Optional sort of comma-separated <field> asc|desc keys; relevance is the default order, and a sort Europe PMC cannot use fails as europepmc_invalid_input
  • Hits carry license and hasFullTextXml
  • Not registered when EUROPEPMC_ENABLED=false

pubmed_europepmc_fetch tool

  • Up to 25 records per call as records: [{ source, epmcId }], each pair copied from a search hit, with the full abstract, license, and hasFullTextXml; unresolved ids land in notFound; opt-in maxResponseCharacters defers overflow to deferred.records
  • Not registered when EUROPEPMC_ENABLED=false

pubmed_fetch_citation_metrics tool

  • Up to 1,000 PMIDs per call; the first 200 distinct are fetched and the rest returned in overLimit, PMIDs NIH iCite has no record for in unavailablePmids
  • Relative Citation Ratio (with a provisional flag), NIH percentile, citation count and rates, Approximate Potential to Translate, MeSH category shares, and clinical citations
  • iCite does not flag retractions; check pubmed_fetch_articles for notices
  • Source: NIH iCite

pubmed_format_citations tool

  • Up to 50 PMIDs per call, in any mix of apa, mla, bibtex, ris, and vancouver
  • Bookshelf records cite as edited books, each chapter dated by its own last revision or contribution date; PMIDs that can't be fetched are reported as unavailable
  • Vancouver writes page ranges in elided Citing Medicine form (1637-1645 → 1637-45); BibTeX issn and RIS SN carry the journal's linking ISSN, and RIS TI drops its trailing period
  • Retractions, errata, and expressions of concern NCBI links to an article come back as notices and are shown ahead of its citations; Vancouver adds a Retraction in: / Erratum in: note and APA a retraction parenthetical

pubmed_find_related tool

  • similar, cited_by, or references, up to 50 per page with offset pagination. A larger page size is served at the cap with a notice naming where to continue
  • Falls back to Europe PMC, then OpenAlex, and names the provider that answered; fails as all_providers_failed if none can

pubmed_spell_check tool

  • Returns original, corrected, and hasSuggestion; corrections land in place, so field tags, operators, spacing, and gene symbols stay as written, and a single letter such as an author initial is never swapped for another
  • Values of indexed field tags (aged[mh], zhang y[au], free full text[sb]) are kept as written; free-text fields ([tiab], [ti], [tw]) are still corrected
  • Run it after a zero-hit or thin search, then retry pubmed_search_articles with corrected

pubmed_lookup_mesh tool

  • Descriptors by name or free-text term, with an exact heading match pinned first (the descriptor, for a drug-class heading); up to 50 per page, continued via nextOffset. A larger page size is served at the cap with a notice naming where to continue
  • Records carry their MeSH unique ID (meshId, e.g. D000072657) beside the Entrez UID; includeDetails (default on) adds tree numbers, scope notes, and entry terms

pubmed_lookup_citation tool

  • Up to 25 partial citations per call; a journal or a four-digit year is required, and volume, first page, and author sharpen the match
  • Each is matched independently and comes back matched, not_found, or ambiguous, with recovery detail

pubmed_convert_ids tool

  • Up to 50 ids per call, all of one declared idType (doi, pmid, pmcid); only PMC-indexed articles resolve
  • One success or error row per id, in order, so a partial batch never fails

pubmed://database/info resource

  • Live EInfo call for the pubmed database, returned as application/json
  • count, lastUpdate, and fields[], whose names are the search tags pubmed_search_articles accepts

research_plan prompt

  • Arguments: title, goal, and keywords required; organism and includeAgentPrompts optional
  • Returns a four-phase research plan; includeAgentPrompts: "true" adds an agent-guidance block under each of its nine sub-steps, two of which point at tools: the literature review names pubmed_search_articles and pubmed_lookup_mesh, and the interpretation step names pubmed_search_articles

Features

Built on @cyanheads/mcp-ts-core: stdio and Streamable HTTP transports, pluggable auth (none / jwt / oauth), swappable storage (in-memory, filesystem, Supabase, Cloudflare KV/R2/D1), structured logging with optional OpenTelemetry tracing.

PubMed-specific:

  • NCBI E-utilities (ESearch, EFetch, ESummary, ELink, ESpell, EInfo, ECitMatch) and the PMC ID Converter, with Europe PMC, OpenAlex, and Unpaywall filling the gaps
  • Shared NCBI request queue: paced request starts, capped concurrency, a cooldown that holds every caller after an NCBI 429, and one deadline covering queue wait and retries
  • XML parsing built for PubMed's inconsistent records: structured abstracts, missing fields, varying date formats
  • Forgiving identifiers: a zero-padded PMID resolves as the PMID it spells in every tool that takes one; pubmed_fetch_fulltext also matches DOIs case-insensitively and PMC IDs with or without the PMC prefix
  • Hand-rolled citation formatters (APA, MLA, BibTeX, RIS, Vancouver) with no dependencies

Agent-friendly output:

  • Provenance in responses: source labels, license fields on full-text and Europe PMC results, best-effort warnings on Unpaywall results, and effective-query echo on searches, so agents can judge what to trust
  • Graceful partial failure: batch tools return per-item success/error rows instead of failing the request, with structured status codes and actionable next-step text
  • Discriminated output contracts: source: "pmc" | "unpaywall", typed unavailable reasons, viaSource and triedTiers fields, so callers branch on data, not string parsing

Getting started

Connect to the hosted instance, no install:

claude mcp add --transport http pubmed-mcp-server https://pubmed.caseyjhand.com/mcp

Or run it locally:

claude mcp add pubmed-mcp-server -- npx -y @cyanheads/pubmed-mcp-server

For other clients, add this to the MCP config file:

{
  "mcpServers": {
    "pubmed-mcp-server": {
      "command": "npx",
      "args": ["-y", "@cyanheads/pubmed-mcp-server"]
    }
  }
}

An NCBI API key in NCBI_API_KEY raises the rate limit from 3 to 10 requests per second (-e NCBI_API_KEY=your-key, or an env entry). For Docker or a source build, see Running the server.

Configuration

VariableDescriptionDefault
NCBI_API_KEYNCBI API key; raises the rate limit from 3 to 10 req/s. NCBI counts the limit per key (per IP address without one), so processes sharing a key or an address share it.none
NCBI_ADMIN_EMAILContact email sent with NCBI requests, as NCBI recommends.none
NCBI_REQUEST_DELAY_MSMinimum gap between NCBI request starts, in ms.400 (120 with a key)
NCBI_MAX_CONCURRENTMax concurrent in-flight NCBI requests.8
NCBI_MAX_RETRIESRetry attempts for failed NCBI requests.6
NCBI_TIMEOUT_MSPer-request HTTP timeout, in ms.30000
NCBI_TOTAL_DEADLINE_MSDeadline for one NCBI call across queue wait, retries, and backoff, in ms. A call that can't start in time is rejected at once.60000
UNPAYWALL_EMAILContact email for Unpaywall. Setting it enables the Unpaywall tier of pubmed_fetch_fulltext for non-PMC DOIs.none
UNPAYWALL_TIMEOUT_MSPer-request timeout for Unpaywall lookups and content fetches, in ms.20000
EUROPEPMC_ENABLEDSet false to disable every Europe PMC call: both Europe PMC tools go unregistered, pubmed_fetch_fulltext skips that tier, and pubmed_find_related skips that fallback.true
EUROPEPMC_EMAILOptional contact email sent with Europe PMC requests.none
EUROPEPMC_REQUEST_DELAY_MSMinimum gap between Europe PMC request starts, in ms.200
EUROPEPMC_MAX_RETRIESRetry attempts for failed Europe PMC requests.3
EUROPEPMC_TIMEOUT_MSPer-request timeout for Europe PMC calls, in ms.20000
MCP_TRANSPORT_TYPETransport: stdio or http.stdio
MCP_HTTP_PORTHTTP server port.3010
MCP_SESSION_MODEHTTP session mode: stateless, stateful, or auto.stateless
MCP_AUTH_MODEAuthentication: none, jwt, or oauth.none
MCP_LOG_LEVELLog level (debug, info, warning, error, etc.).info
LOGS_DIRDirectory for log files (Node.js only).<app-root>/logs
STORAGE_PROVIDER_TYPEStorage backend: in-memory, filesystem, supabase, cloudflare-kv/r2/d1.in-memory
OTEL_ENABLEDEnable OpenTelemetry.false

See .env.example for every server setting and the common framework overrides.

Running the server

Local development

Requires Bun v1.4.0 or higher (or Node.js v24+).

  • Clone and install:

    git clone https://github.com/cyanheads/pubmed-mcp-server.git
    cd pubmed-mcp-server && bun install
    cp .env.example .env   # set NCBI_API_KEY, NCBI_ADMIN_EMAIL, and UNPAYWALL_EMAIL as needed
    
  • Build and run the production version:

    # One-time build
    bun run rebuild
    
    # Run the built server
    bun run start:http
    # or
    bun run start:stdio
    
  • Run checks and tests:

    bun run devcheck  # Lints, formats, type-checks, and more
    bun run test      # Runs the test suite
    

Docker

docker run --rm -p 3010:3010 ghcr.io/cyanheads/pubmed-mcp-server:latest

The image defaults to HTTP transport, stateless session mode, and logs to /var/log/pubmed-mcp-server. To run it over stdio from an MCP client, use "command": "docker" with "args": ["run", "-i", "--rm", "-e", "MCP_TRANSPORT_TYPE=stdio", "ghcr.io/cyanheads/pubmed-mcp-server:latest"]. To build locally, docker build -t pubmed-mcp-server .; OpenTelemetry peer dependencies are installed by default — build with --build-arg OTEL_ENABLED=false to omit them.

Project structure

DirectoryPurpose
src/mcp-server/toolsTool definitions (*.tool.ts). Twelve tools across PubMed, PMC, Europe PMC, and NIH iCite.
src/mcp-server/resourcesResource definitions. Database info resource.
src/mcp-server/promptsPrompt definitions. Research plan prompt.
src/services/ncbiNCBI E-utilities service layer — API client, queue, parser, formatter.
src/services/europe-pmcEurope PMC service — search + fullTextXML JATS retrieval. Reuses the NCBI JATS parser.
src/services/unpaywallUnpaywall service — DOI → OA location resolution and content fetch (HTML/PDF).
src/services/openalexOpenAlex service — last-resort provider for pubmed_find_related.
src/configServer-specific environment variable parsing and validation with Zod.
tests/Unit and integration tests, mirroring the src/ structure.
skills/The published pubmed-guide agent skill, served over MCP and shipped in the package, the .mcpb bundle, and the Docker image.

Development guide

See CLAUDE.md for development guidelines and architectural rules. The short version:

  • Handlers throw, framework catches — no try/catch in tool logic
  • Use ctx.log for logging, ctx.state for storage
  • Register new tools and resources in the createApp() arrays in src/index.ts
  • Wrap external API calls: validate raw → normalize to domain type → return output schema; never fabricate missing fields

Contributing

Issues are welcome. Run checks and tests before submitting:

bun run devcheck
bun run test

License

This project is licensed under the Apache 2.0 License. See the LICENSE file for details.

版本与发布记录

@cyanheads/pubmed-mcp-server 共发布 121 个版本,首次发布于 2025/05/24;过去 12 个月发布了 100 个版本。

版本发布日期距今
2.12.0latest2026/11/037 天前
2.11.12026/10/2616 天前
2.11.02026/10/2516 天前
2.10.232026/10/2318 天前
2.10.222026/10/1329 天前
2.10.212026/10/101 个月前

关于 @cyanheads/pubmed-mcp-server 的常见问题

@cyanheads/pubmed-mcp-server 是什么?

Search PubMed/Europe PMC, fetch articles and full text (PMC/EPMC/Unpaywall), citations, MeSH terms via MCP. STDIO or Streamable HTTP.

如何安装 @cyanheads/pubmed-mcp-server?

在项目目录运行 npm install @cyanheads/pubmed-mcp-server,或使用 pnpm add / yarn add / bun add。它还提供命令行工具 pubmed-mcp-server,可以用 npx pubmed-mcp-server 直接运行。

@cyanheads/pubmed-mcp-server 支持 TypeScript 吗?

支持。包内自带 TypeScript 类型声明(package.json 声明了 types 入口),安装后即可获得类型提示,无需再安装 @types 包。

@cyanheads/pubmed-mcp-server 支持 ESM 还是 CommonJS?

以 ES Module 形式发布,推荐使用 import 引入。在 CommonJS 项目中,Node.js 20.19+ / 22.12+ 可以直接 require() 不含顶层 await 的 ES Module,更早的版本需要改用动态 import()。

@cyanheads/pubmed-mcp-server 需要什么版本的 Node.js?

package.json 的 engines 字段要求 Node.js >=24.0.0。版本不符时 npm 默认只给出警告,开启 engine-strict 后会拒绝安装。

@cyanheads/pubmed-mcp-server 可以商用吗?

@cyanheads/pubmed-mcp-server 使用 Apache-2.0 许可。宽松许可:允许商业使用、修改和再分发,并附带明确的专利授权;分发时需保留许可与 NOTICE 文件,修改过的文件要注明改动。以上为概括,不构成法律意见,请以许可原文为准。

@cyanheads/pubmed-mcp-server 的下载量有多少?

根据 npm 官方下载统计,@cyanheads/pubmed-mcp-server 在 2026/10/11 – 2026/11/09 这 30 天内被下载 15,646 次,日均约 522 次。下载量会把 CI 构建、镜像同步和作为其他包依赖的安装一并计入,适合横向比较热度,不能直接等同于使用人数。

@cyanheads/pubmed-mcp-server 还在维护吗?

最新版本 2.12.0 发布于 2026/11/03(7 天前);至今共发布 121 个版本,其中过去 12 个月发布了 100 个;首次发布于 2025/05/24。发布频率只是参考信号:功能稳定的工具可能很少需要更新,建议结合源码仓库的 issue 和提交记录判断。