National Parks MCP Server
Click on "Deploy Server".
Wait a few minutes for the server to deploy. Once ready, it will show a "Started" state.
In the chat, type
@followed by the MCP server name and your instructions, e.g., "@National Parks MCP ServerFind parks in Montana"
That's it! The server will respond to your query, and you can continue using it as needed.
Here is a step-by-step guide with screenshots.
Public Hosted Server: https://national-parks.caseyjhand.com/mcp
Overview
US National Park Service trip planning over the NPS Data API. Resolve a park to its parkCode, then check alerts and closures, find campgrounds, and browse activities and events — coverage is US NPS sites only (national parks, monuments, historic sites, seashores), not state parks, Forest Service, or BLM land. Runs as a stdio process, a local Streamable HTTP server, or the public hosted endpoint above.
Tools
Tool | Description |
| Resolve a place name, US state, or free-text query to parks — the required first step. Returns each park's |
| Full detail for up to ten parks in one batched call: description, activities, fees & passes, hours, contacts, directions, weather overview, images. |
| Current alerts for a park or state — closures, hazards, caution, information — with category and recency surfaced first. |
| Campgrounds at a park or state: amenities, reservable vs. first-come site counts, reservation info, accessibility, and fees. |
| Curated things to do and points of interest: title, duration, location, accessibility, and fee/pet/reservation flags. |
| Scheduled events within a date range: dates/times, location, category, fee, and registration links. |
Related MCP server: National Parks MCP Server
Capability reference
nps_find_parks tool
Free-text
query, two-letterstateCode(or a comma-separated list such as"WY,MT,ID"), and an optionalactivityfilter;limit1–50 (default 10) with astartoffsetEach park carries its
parkCodeplus designation, states, description, coordinates, headline activities, lowest entrance fee, and NPS page; exactparkCodeor name matches rank first, andtotalCountcounts every match
nps_get_park tool
Up to 10
parkCodes per call; the optionalfieldsselector (activities,topics,fees,hours,contacts,directions,images) trims the payload to the sections you needAlways returns name, designation, states, description, coordinates, weather overview, and NPS page; fees and passes by category, hours by area and season, contacts, and up to 5 images (
imagesTruncatedwhen the park has more)Codes that match no site come back as
missingCodes; the call fails (no_parks_found) only when none resolve
nps_get_alerts tool
Filter by
parkCode,stateCode, free-textquery, andcategory(Danger,Caution,Information,Park Closure);limit1–50 (default 20) with astartoffsetMost-recent-first, each alert with its category,
lastIndexedDaterecency, and detail;categoryBreakdowncounts the returned alerts by severityThe notice tells an all-clear (no alerts at that location) apart from a filter that matched nothing and a page past the end
nps_find_campgrounds tool
Filter by
parkCode,stateCode, or free-textquery;limit1–50 (default 15) with astartoffsetPer campground: amenities (potable water, showers, dump station, toilets, trash collection, RV access) as yes, no, or unknown; reservable, first-come, and total site counts; reservation guidance and booking URL; lowest fee, accessibility, coordinates, and NPS page
nps_get_activities tool
A single
parkCodeor a singlestateCodeis required, plus an optionalquery;limit1–50 (default 15) with astartoffsetPer activity: title, short description, time commitment, location, coordinates, accessibility, season, reservation-required and pets-permitted flags, fee description, and NPS page
nps_find_events tool
Filter by
parkCode,stateCode, orquerywithin adateStart/dateEndwindow (YYYY-MM-DD); pages bypageNumberandpageSize(1–50, default 15), not by offsetPer event: title, date range,
occurrenceDatesinside the window (isRecurringmarks a series), time slots, location, category, fee, and registration and info URLsErrors NPS reports alongside results fold into the notice instead of failing the call
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.
NPS-specific:
One service wrapping the NPS Data API (
developer.nps.gov/api/v1,X-Api-Keyauth) across six trip-planning endpointsAggressive normalization of NPS's inconsistent payloads — numeric and boolean fields returned as strings, nested values (
campsites.totalSites), array-typed amenity fields, and the distinct/eventsenvelope with lowercased field names — coerced to clean domain types before they reach handlersnps_get_parkbatches up to ten park codes into a single upstream requestLight retry on transient upstream failures (5xx / network); a missing or invalid key fails loud and names
NPS_API_KEYCoordinates returned by
nps_find_parks/nps_get_parkfeed weather servers (nws-weather,open-meteo) for a forecast
Agent-friendly output:
Result-set context on every response —
totalCount, truncation (truncated/shown/cap), applied-filter echo, and empty-result notices reach both the structured and text surfacesMany parks list no campgrounds, curated activities, or events; an empty result comes back with a notice on where else to look, never as an error
The
parkCode-first workflow is encoded in every tool description;nps_get_parkreturnsmissingCodesso a wrong code self-correctsUncertainty preserved, never fabricated — missing coordinates, directions, fees, and amenity values come back
null, not a guess; coordinates are never invented for downstream weather lookups
Getting started
Public Hosted Instance
A public instance is available at https://national-parks.caseyjhand.com/mcp — no installation required. Point any MCP client at it via Streamable HTTP, with this client config:
{
"mcpServers": {
"national-parks-mcp-server": {
"type": "streamable-http",
"url": "https://national-parks.caseyjhand.com/mcp"
}
}
}Self-Hosted / Local
Add the following to your MCP client configuration file. A free NPS Data API key is required — instant signup here.
{
"mcpServers": {
"national-parks-mcp-server": {
"type": "stdio",
"command": "bunx",
"args": ["@cyanheads/national-parks-mcp-server@latest"],
"env": {
"MCP_TRANSPORT_TYPE": "stdio",
"MCP_LOG_LEVEL": "info",
"NPS_API_KEY": "your-api-key"
}
}
}
}Or with npx (no Bun required):
{
"mcpServers": {
"national-parks-mcp-server": {
"type": "stdio",
"command": "npx",
"args": ["-y", "@cyanheads/national-parks-mcp-server@latest"],
"env": {
"MCP_TRANSPORT_TYPE": "stdio",
"MCP_LOG_LEVEL": "info",
"NPS_API_KEY": "your-api-key"
}
}
}
}Or with Docker:
{
"mcpServers": {
"national-parks-mcp-server": {
"type": "stdio",
"command": "docker",
"args": [
"run", "-i", "--rm",
"-e", "MCP_TRANSPORT_TYPE=stdio",
"-e", "NPS_API_KEY=your-api-key",
"ghcr.io/cyanheads/national-parks-mcp-server:latest"
]
}
}
}For Streamable HTTP, set the transport and start the server:
MCP_TRANSPORT_TYPE=http MCP_HTTP_PORT=3010 NPS_API_KEY=... bun run start:http
# Server listens at http://localhost:3010/mcpPrerequisites
Bun v1.4 or higher (or Node.js v24+).
A free NPS Data API key — instant signup. The server fails to start without it.
Installation
Clone the repository:
git clone https://github.com/cyanheads/national-parks-mcp-server.gitNavigate into the directory:
cd national-parks-mcp-serverInstall dependencies:
bun installConfigure environment:
cp .env.example .env
# edit .env and set NPS_API_KEYConfiguration
All configuration is validated at startup via Zod schemas. Key environment variables:
Variable | Description | Default |
| Required. NPS Data API key, sent as the | — |
| NPS Data API base URL override (testing / proxy). |
|
| Transport: |
|
| Port for the HTTP server. |
|
| Path where the MCP server is mounted. |
|
| Session handling: |
|
| Auth mode: |
|
| Log level (RFC 5424). |
|
| Directory for log files (Node.js only). |
|
| Log each failed tool call's arguments and result, redacted by key name and capped at |
|
| Storage backend: |
|
| Enable OpenTelemetry instrumentation (spans, metrics, completion logs). |
|
See .env.example for the full list of optional overrides.
Running the server
Local development
Build and run:
# One-time build bun run rebuild # Run the built server bun run start:stdio # or bun run start:httpRun checks and tests:
bun run devcheck # Lint, format, typecheck, security bun run test # Vitest test suite bun run lint:mcp # Validate MCP definitions against spec
Docker
docker build -t national-parks-mcp-server .
docker run --rm -e NPS_API_KEY=your-key -p 3010:3010 national-parks-mcp-serverThe Dockerfile defaults to HTTP transport, stateless session mode, and logs to /var/log/national-parks-mcp-server. OpenTelemetry peer dependencies are installed by default — build with --build-arg OTEL_ENABLED=false to omit them.
Project structure
Directory | Purpose |
|
|
| Server-specific environment variable parsing and validation with Zod. |
| Tool definitions ( |
| NPS Data API service — HTTP client, retry boundary, error-envelope detection, and all upstream normalization. |
| Unit and integration tests mirroring |
Development guide
See AGENTS.md / CLAUDE.md for development guidelines and architectural rules. The short version:
Handlers throw, framework catches — no
try/catchin tool logicUse
ctx.logfor request-scoped logging,ctx.statefor tenant-scoped storageRegister new tools in the
createApp()arraysWrap the external API: validate raw → normalize to domain type → return output schema; never fabricate missing fields
Data & attribution
Data is retrieved from the NPS Data API operated by the U.S. National Park Service. Content produced by NPS employees in their official capacity is a U.S. Government work in the public domain (17 U.S.C. §§ 101 and 105). No claim to original U.S. Government works.
Not all content returned by the API is government-authored. Some images and materials carry third-party copyright or other restrictions — check individual item rights before reuse.
The NPS Arrowhead symbol is a restricted mark protected under 18 U.S.C. § 701. It must not be reproduced or reused without written permission from the NPS Director.
Contributing
Issues are welcome. Run checks and tests before submitting:
bun run devcheck
bun run testLicense
Apache-2.0 — see LICENSE for details.
This server cannot be deployed
Maintenance
Related MCP Connectors
Recreation.gov MCP — wraps the Recreation Information Database (RIDB) API v1
NPS MCP — US National Park Service (free key, generous limits)
Query FDA data on drugs, food, devices, and recalls via openFDA. STDIO or Streamable HTTP.
Live US campground availability, wildfire and river conditions, and trails on public land.
Related MCP Servers
- AlicenseNot gradedqualityDmaintenanceFacilitates retrieval of National Park Services data using the NPS API, allowing users to list national parks by state and access detailed information about specific parks.44,731 npm3MIT
- AlicenseBqualityDmaintenanceProvides real-time information about U.S. National Parks through the NPS API, enabling users to search parks, check details, alerts, visitor centers, campgrounds, and upcoming events.6142 npm41MIT
- AlicenseNot gradedqualityDmaintenancePython based with all 29 tools that's available to developers from National Park Services (NPS)MIT
- AlicenseNot gradedqualityDmaintenanceProvides access to the National Park Service API to search for U.S. national parks, view park details, check alerts and closures, find visitor centers, campgrounds, and upcoming events.142 npmMIT