Ultimaps

com.ultimaps由 ultimaps.com 发布官方发布者v0.2.1更新于 Nov 8, 2026

Create choropleth, category and pin maps of countries, states, counties and ZIP codes as images.

已验证Streamable HTTP可网页运行数据与分析媒体与设计

概览

AI 生成的概览

Ultimaps 让助手把数据渲染成国家、州、县和邮编区域的地图图片,支持分级填色、分类填色和标记点。

可以做什么
  • 根据数值、类别或指定颜色渲染地图图片(PNG,Pro 密钥可用 SVG),可加标记点、标题、图例、主题和区域标签
  • 以 dryRun 预览区域匹配结果和配色方案,不实际渲染
  • 列出可用的地图目录,支持按关键词搜索
  • 查询单张地图的区域键与名称,每页 200 条,可按键、名称或别名搜索
适用场景
适合在对话中直接得到地图图片的场景,例如按人口给美国各州填色、按货币给欧盟成员国填色,或把几个办公地点标在欧洲地图上。临时需要地理可视化时,不必另建绘图流程。
运行要求
可使用 api.ultimaps.com 的远程端点,或本地 npm 包(需要 Node.js 20 或更高版本)。无需账号;可选 API 密钥,本地通过 ULTIMAPS_API_KEY 提供,远程服务器通过 Authorization 请求头以 Bearer 形式提供。需要能访问 Ultimaps API 的网络。
安装前请注意
渲染请求(含区域数值、标记点、标题和样式)会发送给 Ultimaps 并记录日志,同时记录 IP 地址;请求内容保留 30 天,IP 与 user agent 保留 90 天。API 密钥仅在渲染请求中发送,密钥无效会直接报错而不会退回免密钥模式。渲染计入每小时、每日或每月配额;小型免密钥渲染的可嵌入链接包含完整地图请求,任何拿到链接的人都能读取。渲染出的图片会写入临时目录且不会被删除。

安装

在 SourceWeft 中

  1. 打开 控制台中的 Ultimaps,将其添加到工作区。
  2. 为需要使用其工具的对话启用该服务。

Web executable,通过 Streamable HTTP。 远程服务在工作区中配置后即可从网页运行时运行。

交给智能体安装

把这段提示词粘贴到 Claude Code、Codex、Cursor 等智能体,或 SourceWeft 对话中。智能体会读取该服务器的安装指南,先向你展示发布者、端点和登录方式,经你同意后再把它添加到你的客户端。密钥不会写进任何命令。

阅读 https://sourceweft.com/mcp/com.ultimaps%2Fmcp/install.md,并按其中说明把这个 MCP 服务器接入我的客户端。修改任何配置之前,先告诉我它的发布者、端点和登录方式,等我确认。不要把 API 密钥写进命令或我会提交的文件;问我密钥应从哪里获取。

查看智能体所依据的安装指南

其他 MCP 客户端

把它添加到你客户端的 mcpServers 配置中。

{
  "mcpServers": {
    "ultimaps": {
      "type": "http",
      "url": "https://api.ultimaps.com/mcp"
    }
  }
}

README

@ultimaps/mcp

An MCP server for Ultimaps. Ask Claude, Codex or any MCP client for a map and get the image back in the conversation. It covers choropleths from pasted numbers, category maps and pinned locations, for countries, states, provinces, counties, continents and the world.

"Map US states by population." · "Color the EU members by currency." · "Show France's regions with these unemployment rates: …" · "Pin our five offices on a map of Europe."

No account needed. Without an API key the server uses the keyless tier. Set ULTIMAPS_API_KEY for plan quotas and larger or unbranded output.

Can't run a local command? In ChatGPT (developer mode), claude.ai or any client that connects to remote MCP servers, add the hosted server instead: https://api.ultimaps.com/mcp. In ChatGPT, turn it on in each conversation where you want maps. It has the same three tools and nothing to install. See Hosted server. This package is the local version: requests come from your own IP address with your own key, and every image is saved to a file on your computer.

Tools

ToolWhat it does
render_mapRenders a map as an image (PNG, or SVG with a Pro key), shown inline when it is small enough. Choropleth (numbers), categories (labels) or explicit colors, plus pins, title, a legend with its own heading, theme, region labels (names, values or both) and extra layers. Region names are matched fuzzily, and every correction or miss is reported with suggestions. dryRun: true previews matching and the color plan without rendering.
list_mapsThe map catalog: {id, title, regionType, layers, regionCount, labels}, searchable with query.
get_map_regionsOne map's region keys and titles, 200 per page, searchable by key, title or alias.

All three are read-only. Agents rarely need the discovery tools: render_map accepts region names, codes and aliases directly.

Install

Requires Node.js 20 or newer.

Claude Code

sh
claude mcp add ultimaps -- npx -y @ultimaps/mcp# with a key:claude mcp add ultimaps --env ULTIMAPS_API_KEY=um_live_… -- npx -y @ultimaps/mcp

Codex

sh
codex mcp add ultimaps -- npx -y @ultimaps/mcp# with a key:codex mcp add ultimaps --env ULTIMAPS_API_KEY=um_live_… -- npx -y @ultimaps/mcp

Codex writes TOML, not the JSON below. The equivalent entry in ~/.codex/config.toml (or .codex/config.toml in a trusted project):

toml
[mcp_servers.ultimaps]command = "npx"args = ["-y", "@ultimaps/mcp"]

Claude Desktop

Download ultimaps-<version>.mcpb from the latest release and open it: Claude Desktop installs it in one click and asks for the optional API key. Or add this to claude_desktop_config.json:

json
{  "mcpServers": {    "ultimaps": {      "command": "npx",      "args": ["-y", "@ultimaps/mcp"],      "env": { "ULTIMAPS_API_KEY": "" }    }  }}

Cursor

~/.cursor/mcp.json (or .cursor/mcp.json in a project):

json
{  "mcpServers": {    "ultimaps": { "command": "npx", "args": ["-y", "@ultimaps/mcp"] }  }}

VS Code

.vscode/mcp.json:

json
{  "servers": {    "ultimaps": { "type": "stdio", "command": "npx", "args": ["-y", "@ultimaps/mcp"] }  }}

Hosted server

You don't need this package to use the hosted server. Add the URL to your client:

sh
claude mcp add --transport http ultimaps https://api.ultimaps.com/mcp# with a key:claude mcp add --transport http ultimaps https://api.ultimaps.com/mcp \  --header "Authorization: Bearer um_live_…"

Clients with a config file take the URL alone, for example ~/.cursor/mcp.json:

json
{  "mcpServers": {    "ultimaps": { "url": "https://api.ultimaps.com/mcp" }  }}

The hosted server sends a key as an Authorization header, not as ULTIMAPS_API_KEY. In ChatGPT and claude.ai you can't set headers, so renders there use the anonymous tier: PNG up to 1600 px with attribution, up to 30 per hour per conversation. Every render also comes back as an image link that expires after 30 days. Images too large for the conversation, and all SVGs, come back only as the link. ChatGPT doesn't show images returned by tools, so the link is how you see the map there.

Configuration

VariableDefaultPurpose
ULTIMAPS_API_KEYnone (keyless)API key from Studio → Workspace → API. An invalid key is an error and never falls back to keyless.
ULTIMAPS_API_URLhttps://api.ultimaps.comPoint at a local API during development (http://localhost:3001). Plain http is only accepted for localhost.

Limits

KeylessFree keyPro key
Renders30/hour, 5/minute500/month, 50/day, 10/minute5,000/month, 1,000/day, 30/minute
OutputPNG up to 1600 px, attributionPNG up to 1600 px at scale 2 (a 3200 px raster), attributionPNG up to 4000 px at scale 4, SVG, no attribution

All keys in a workspace share the monthly quota. The daily and per-minute caps are per key, so a free key stops at 50 renders a day long before the month runs out.

Dry runs skip the monthly quota but still count against rate limits. When five or fewer keyless renders remain in the hour, the result says so.

What a render returns

  • The image, inline, when it is small enough (781 KB for PNG, 98 KB for SVG). The default 1200 px width usually fits. Every render is also written to <tmpdir>/ultimaps-mcp/ and the path is in the result, so in a terminal client the file is the thing you can actually open. Nothing is re-rendered or resampled on your behalf.
  • A text report: auto-corrected and unmatched region keys with suggestions, the resolved choropleth plan, warnings (such as layer_unavailable or labels_overlap), a link to open the map in Ultimaps Studio for editing, and the render id for support.
  • An embeddable image URL for keyless PNG renders whose whole spec fits a ~2,000-character URL, so small datasets only. The URL carries the spec, not the image, and renders keyless, so it is not offered when a key is set.
  • structuredContent with the same report as data, described by the tool's outputSchema.

Privacy Policy

This server runs on your machine, has no telemetry of its own and talks only to the Ultimaps API (https://api.ultimaps.com, or the ULTIMAPS_API_URL you set). The full Ultimaps privacy policy is at ultimaps.com/privacy-policy.

What is sent to Ultimaps. Tool calls are ordinary HTTPS requests to the Ultimaps API, so they arrive from your IP address with an ultimaps-mcp/<version> user agent. render_map sends the whole map request: region keys and values, pins, title and styling. If you set ULTIMAPS_API_KEY, it is sent with render requests only.

What Ultimaps keeps. Each render request is logged: the request content, the map and outcome, timing, your IP address and user agent, and for keyed requests which key and workspace made it. This lets support look up a render id, lets the "Open in Studio" link rebuild your map, and counts usage. The request content is kept for 30 days and the IP address and user agent for 90 days. What remains is a usage record, tied to your workspace when a key was used. Ultimaps uses a third-party error-monitoring service that may receive details of a failed request. Ultimaps does not sell this data or use it for advertising.

What stays on your machine. Every rendered image is written to <tmpdir>/ultimaps-mcp/ and this server never deletes it. What your MCP client keeps, including tool results in your conversation, is governed by its own privacy policy.

Shareable links. The embeddable image URL offered for small keyless renders contains the full map request. Anyone with the link can read it.

The hosted server. The server at https://api.ultimaps.com/mcp runs on Ultimaps' servers, not yours, so the section above about your machine doesn't apply to it. The full privacy policy covers it.

Questions or deletion requests: [email protected], quoting the render id.

Development

sh
npm installnpm run typechecknpm test           # unit + in-process protocol testsnpm run build      # → dist/

End-to-end over stdio against a real API (spends render units from your tier):

sh
npm run buildnode scripts/smoke.mjs

src/generated/render-request.schema.json is generated from the Ultimaps API contract; do not edit it by hand. Tool and property descriptions live in src/descriptions.ts. Arguments are never validated locally: the API is additive-only, and its 400 responses carry suggestions.

Issues and pull requests are welcome. Releases are cut by the Ultimaps team, and accepted changes ship with the next release.

The package publishes a bin and nothing else. import '@ultimaps/mcp' is not supported and fails by name, because dist/index.js starts a stdio server when it loads.

License

MIT © Ultimaps. See LICENSE.

来源:README.md,提交 8804579

工具

3

list_maps

List maps

List the maps Ultimaps can render: the world, continents, countries subdivided into states, provinces, counties or departments, and US ZIP code areas. Each row is {id, title, regionType, layers, regionCount, labels}. `id` is the mapId for render_map and get_map_regions; it is the map's slug on ultimaps.com (the last path segment, not the whole URL) and always means the current edition. `regionCount` is how many region keys a complete dataset needs. `labels: false` means the map has no region labels, so `style.labels` does nothing there. `layers` are the ids render_map's `layers` can turn on. Pass `query` to search ids, titles, region types and categories (e.g. "counties", "germany", "africa"). Only call this when you don't know the id: common ids such as `world`, `united-states` and `europe` just work, and an unknown id usually comes back with the closest ids.

输入参数query

get_map_regions

Get map regions

Look up one map: title, regionType, regionCount, labels, layers, and its regions as {key, title}, 200 per page. You rarely need this before rendering. render_map accepts region names, codes and common aliases and auto-corrects typos, reporting what it matched. Use it to build a dataset covering every region of a map, to see how a map names its regions, or to resolve a key render_map could not match. `query` searches keys, titles and aliases, so no hits means the map really has no such region. Use `offset` for further pages.

输入参数mapId必填queryoffset

render_map

Render map

Draws a map of real places as an image: countries, states, counties or ZIP codes colored by data (a choropleth or heat map) or by category, with a legend, a title and pins. Borders come from real geographic data, not from an image model, and region names are matched for you. It draws only real places, never fictional or invented ones. The map is returned as an image in the conversation. Maps cover the world, continents, countries, their states, provinces and counties, and US ZIP code areas. Color regions with ONE of these (choropleth and categories are mutually exclusive): - `choropleth`: a number per region, e.g. {"values": {"California": 39.5, "Texas": 30.5}}. Classes, breaks and palette are picked from the data unless you set them. Say what the numbers are with `kind` (and `midpoint` when they have a meaningful center, `unit` for a short label unit): that is what gets percents, currencies, years and diverging scales right. When the data does not cover every region of the map, add `noData: true` so the legend explains the uncolored ones. - `categories`: a label per region, e.g. {"values": {"France": "Euro", "Poland": "Złoty"}}. Colors are assigned automatically unless you set `colors`. - `regions`: explicit hex colors, e.g. {"Texas": "#1D4ED8"}. Also works on top of either mode as an override. Region keys can be names, ISO/FIPS-style codes or common aliases. Typos are auto-corrected, and every correction or unmatched key is reported with suggestions, so there is no need to call get_map_regions first. Get `mapId` from list_maps if you don't know it. Also available: pins (`locations` with lat/lon), `title`, `legend` (position, `title`, `subtitle`), `style` (theme, borders, region labels; `style.labels.content: "value"` prints each region's value instead of its name and `"name_value"` stacks the name above the value, both needing `choropleth` or `categories`; `style.labels.fit` (default "auto") shortens labels that don't fit or overlap and never hides one; any still

输入参数mapId必填styletitledryRunlayerslegendoutputregionslocationscategorieschoroplethonUnmatched

版本历史

3
  1. v0.2.0Oct 20, 2026
  2. v0.1.1Sep 16, 2026
  3. v0.1.0Sep 16, 2026

评分

已满足适用检查项的 100%

该评分衡量此收录条目的完整程度,依据注册中心条目、端点与公开来源计算得出。它不是对服务器本身的评价,也不表示服务器安全或当前可用:可连通性是带日期的检查结果,评分也不包含安装量或用户评价。

  • 近 30 天内可连通必需25 分
  • 已声明认证方式必需10 分
  • 已列出工具必需15 分
  • 描述必需15 分
  • 图标10 分
  • 文档15 分
  • 许可证10 分