Figma MCP local

Figma MCP local

A local, high-performance replacement for the hosted Figma MCP server that caches Figma files and exposes a local MCP endpoint for Cursor or any MCP client.

Category
访问服务器

README

Design Intelligence Platform (Local MVP)

A local, high-performance replacement for the hosted Figma MCP server. It downloads Figma files once into a SQLite cache, builds a full-text search index over them, and exposes a local MCP endpoint that Cursor (or any MCP client) queries — without touching the Figma API.

Cursor ──► http://localhost:8787/mcp ──► SQLite cache ──► FTS5 search index
                                              ▲
                                              │ only during explicit sync
                                          Figma API

The cache is the source of truth. The Figma API is called in exactly three situations: validating your token on connect, a cheap version check at the start of a sync, and the full file download when the version changed (or --force).

Architecture

Clean architecture with constructor-based dependency injection; src/app.ts is the composition root that wires everything together.

src/
  api/            REST routes (connect, sync, projects, status, logs, health)
  mcp/            MCP server: 8 tools over Streamable HTTP (stateless)
  figma/          Figma REST API client (axios, typed errors, request logging)
  sync/           Parser: Figma document tree -> flattened node rows + search docs
  database/       Drizzle schema, better-sqlite3 client (WAL), idempotent migrations
  search/         FTS5 search repository (safe query building, bm25 ranking, snippets)
  cache/          Cache metadata key/value store (file versions, bookkeeping)
  config/         Zod-validated .env configuration
  services/       AccountService, SyncService (job engine), QueryService, simplifier
  repositories/   Row-level access: accounts, files/pages, nodes, components, styles, variables
  types/          Figma API types + simplified domain types
  utils/          Structured logger (JSON lines + ring buffer for the dashboard)
  shared/         Typed application errors
frontend/         React + Vite + Tailwind dashboard (Connect / Projects / MCP Status)
tests/            Vitest suites incl. end-to-end MCP-over-HTTP tests with a mocked Figma API
scripts/          CLI sync

How data is stored

A Figma file is a single huge JSON tree. Instead of storing one blob (slow to query) or fully normalizing every property (schema churn), each node becomes one row: queryable columns (node_id, parent_id, page_id, type, name, depth, child_index) plus the node's own JSON with children stripped. Subtrees are rebuilt breadth-first at query time down to a depth limit. Search runs over an FTS5 virtual table indexing names and text content.

Simplified node format

get_node defaults to a compact design representation built for code generation: hex colors, auto-layout expressed as flex terms (mode/gap/padding/justify/align), resolved typography, and component instance names. Raw Figma JSON is available with format: "raw".

Installation

Requires Node.js 20+.

npm install
cp .env.example .env   # optional; defaults work out of the box
npm run dev
  • Dashboard (dev): http://localhost:5173 (proxies to the API)
  • API + MCP server: http://localhost:8787

For a production-style run: npm run build && npm start — the built dashboard is then served directly at http://localhost:8787.

Environment variables

Variable Default Description
PORT 8787 REST + MCP server port
DATABASE_URL sqlite.db SQLite database file path
LOG_LEVEL info debug | info | warn | error
FIGMA_MAX_RATE_LIMIT_RETRIES 3 Automatic retries on a Figma 429 (0 disables)

Using it

  1. Connect — open the dashboard, paste a Figma personal access token (Figma → Settings → Security → Personal access tokens). When creating the token, grant these scopes:

    • current_user:read — used once to validate the token
    • file_content:read — required to download files
    • file_metadata:read — recommended; lets re-syncs use the cheap Tier 3 metadata endpoint (the app falls back to a Tier 1 shallow fetch without it)
    • file_variables:read — optional, Enterprise plans only

    The token is validated against /v1/me and stored in the local SQLite database. It is stored in plaintext — this is a single-user local dev tool; treat sqlite.db accordingly.

  2. Sync — paste a file key (the segment after figma.com/design/ in a file URL) and click Sync. The full file is downloaded, flattened into SQLite, and indexed. Re-syncs first do a cheap version check and no-op when nothing changed.

  3. Connect Cursor — add to your Cursor MCP settings:

{
  "mcpServers": {
    "design-intelligence": {
      "type": "http",
      "url": "http://localhost:8787/mcp"
    }
  }
}

Then ask Cursor things like "Generate the Login page", "Find all buttons", "List every page", "Find typography styles" — all answered from the local cache.

CLI sync

npm run sync -- <fileKey>            # sync (version-checked)
npm run sync -- <fileKey> --force    # re-download unconditionally

MCP tools

Tool Purpose
sync_file Explicitly (re)download a file into the cache; chunked for huge files
sync_node Incrementally re-sync one node/frame/page subtree (must already be cached)
get_file_summary One-call overview: counts, page list, top components — orient before drilling in
list_pages Pages of a cached file with their top-level frames
get_node Node subtree — simplified (default) or raw; depth bounds the size
search FTS over pages, frames, components, text and styles; limit/offset
list_components Components / component sets with descriptions; limit/offset + total
get_styles Shared styles and design variables; limit/offset + totals

fileKey is optional on read tools when exactly one file is cached. Read tools are marked readOnlyHint so clients like Cursor can auto-run them safely.

REST API

POST /api/connect · POST /api/sync · POST /api/sync-node · GET /api/projects · GET /api/status · GET /api/logs · GET /api/health · GET /api/connection

How sync works

  1. GET /v1/files/:key/meta — compare version against the cached one; stop if unchanged. This is a Tier 3 endpoint (large rate budget). Without the file_metadata:read scope it falls back to GET /v1/files/:key?depth=1 (Tier 1).
  2. GET /v1/files/:key — full download (no vector geometry). Tier 1 — the scarcest rate-limit class (per Figma's rate limits, roughly 10–20 requests/min on Dev/Full seats since Nov 2025), which is exactly why this platform caches instead of proxying.
  3. Parse: flatten the document tree into node rows and search documents.
  4. Single SQLite transaction: replace file, pages, nodes, components, styles.
  5. Variables via GET /v1/files/:key/variables/localEnterprise-plan only; a 403 is expected on personal/pro plans and logged as a warning, not an error.
  6. Rebuild the FTS5 index for the file.

Sync runs as a background job; poll GET /api/status or watch the dashboard. Nothing else ever calls the Figma API.

For very large files, pass chunked: true (the sync_file tool / POST /api/sync) to download page-by-page — a shallow ?depth=1 fetch for the page list, then one ?ids=<pageId> request per page — instead of one giant whole-file response. It bounds peak payload/memory at the cost of more Tier-1 requests (the 429 retry above absorbs transient limits).

Incremental sync

Iterating on one screen shouldn't re-download the whole file. sync_node (MCP) / POST /api/sync-node fetches a single node via GET /v1/files/:key/nodes?ids=, re-roots the returned subtree from the cached node's position, and atomically replaces just that branch — node rows and their search index — while upserting any component/style metadata the response carries. The node must already be cached from a prior full sync; a full sync_file remains the way to reconcile structural changes such as added or deleted pages.

Scripts

npm run dev · npm run build · npm start · npm test · npm run lint · npm run format · npm run sync -- <fileKey>

Error handling

Typed errors with stable codes surface everywhere: INVALID_TOKEN, NOT_CONNECTED, FILE_NOT_FOUND, CACHE_MISS, CACHE_EMPTY, RATE_LIMITED, SYNC_IN_PROGRESS, VALIDATION_ERROR, FIGMA_API_ERROR. MCP tools return them as tool errors instead of crashing the transport.

Future roadmap (designed for, not implemented)

Multiple accounts (the API client is already token-stateless), semantic/vector search (sits next to the FTS table), AI code generation (consumes the simplified node format), background sync, component dependency graphs, and Electron packaging.

推荐服务器

Baidu Map

Baidu Map

百度地图核心API现已全面兼容MCP协议,是国内首家兼容MCP协议的地图服务商。

官方
精选
JavaScript
Playwright MCP Server

Playwright MCP Server

一个模型上下文协议服务器,它使大型语言模型能够通过结构化的可访问性快照与网页进行交互,而无需视觉模型或屏幕截图。

官方
精选
TypeScript
Magic Component Platform (MCP)

Magic Component Platform (MCP)

一个由人工智能驱动的工具,可以从自然语言描述生成现代化的用户界面组件,并与流行的集成开发环境(IDE)集成,从而简化用户界面开发流程。

官方
精选
本地
TypeScript
Audiense Insights MCP Server

Audiense Insights MCP Server

通过模型上下文协议启用与 Audiense Insights 账户的交互,从而促进营销洞察和受众数据的提取和分析,包括人口统计信息、行为和影响者互动。

官方
精选
本地
TypeScript
VeyraX

VeyraX

一个单一的 MCP 工具,连接你所有喜爱的工具:Gmail、日历以及其他 40 多个工具。

官方
精选
本地
graphlit-mcp-server

graphlit-mcp-server

模型上下文协议 (MCP) 服务器实现了 MCP 客户端与 Graphlit 服务之间的集成。 除了网络爬取之外,还可以将任何内容(从 Slack 到 Gmail 再到播客订阅源)导入到 Graphlit 项目中,然后从 MCP 客户端检索相关内容。

官方
精选
TypeScript
Kagi MCP Server

Kagi MCP Server

一个 MCP 服务器,集成了 Kagi 搜索功能和 Claude AI,使 Claude 能够在回答需要最新信息的问题时执行实时网络搜索。

官方
精选
Python
e2b-mcp-server

e2b-mcp-server

使用 MCP 通过 e2b 运行代码。

官方
精选
Neon MCP Server

Neon MCP Server

用于与 Neon 管理 API 和数据库交互的 MCP 服务器

官方
精选
Exa MCP Server

Exa MCP Server

模型上下文协议(MCP)服务器允许像 Claude 这样的 AI 助手使用 Exa AI 搜索 API 进行网络搜索。这种设置允许 AI 模型以安全和受控的方式获取实时的网络信息。

官方
精选