Revit MCP Python

by revit-mcp

Not rated
GitHub

About

A pyRevit-based MCP server for Autodesk Revit, enabling connection to any MCP-compatible client.

Details

Author
revit-mcp
Categories
Developer Tools, Other, File Management, Automation

Setup

Install Revit MCP Python in your MCP client (Claude Desktop, Cursor, Windsurf, and others).

Repository: https://github.com/revit-mcp/revit-mcp-python

Follow the installation instructions in the repository README, then restart your MCP client.

A pyRevit-oriented implementation of the Model Context Protocol (MCP) for Autodesk Revit

- This minimal implementation leverages the Routes module inside pyRevit to create a bridge between Revit and Large Language Models (LLMs).
- It provides a straightforward template to get started quickly, letting you prototype and iterate tools to give LLMs access to your Revit models.
- These tools are designed to be expanded for your specific use cases. You're very welcome to fork the repo and make your own contributions.
- Note:The pyRevit Routes API is currently in draft form and subject to change. It lacks built-in authentication mechanisms, so you'll need to implement your own security measures for production use.

- Beginners to the Revit API
- Python specialists who aren't versed in C#
- Anyone wanting to prototype and iterate quickly with LLMs and Revit

- A complete Routes implementation for pyRevit
- A minimal MCP server script to connect to any MCP-compatible client
- Several test commands to get you started right away

The system runs astwo separate serversworking together in a chain:

Claude / LLM Client | | MCP Protocol (stdio or HTTP) v main.py (MCP Server) | | HTTP requests (localhost:48884) v pyRevit Routes (REST API running inside Revit) | | Revit API calls v Revit Application

main.pyis the MCP server. It speaks the MCP protocol so that Claude (or any MCP-compatible client) can call tools. When a tool is called,main.pytranslates it into an HTTP request and forwards it to Revit.

pyRevit Routesis a lightweight REST API that runsinsidethe Revit process. It receives those HTTP requests, executes Revit API code (since it has direct access to the running instance), and returns JSON responses.

They never conflict because they serve different roles, speak different protocols, and listen on different ports.

Note:The Launch & Document tools (launch_revit,list_revit_installations) are the exception — they run entirely on the MCP side, usingsubprocessto start Revit and then polling the pyRevit Routes health endpoint until the bridge is ready.

- Built with FastMCP
- Handles HTTP communication with Revit Routes API
- Registers tools from modular tool system
- Provides helper functions for GET/POST/Image requests
- pyRevit Extension (revit-mcp-python.extension/):

- Contains the Routes API that runs inside Revit
- Modular route registration instartup.py
- Individual route modules inrevit_mcp/directory

- Modular tool organization by functionality
- Central registration throughtools/__init__.py
- Each module registers its own tools with the MCP server
- In Revit, navigate to the pyRevit tab
- Open Settings
- Go toRoutes> activateRoutes ServerpyRevit will start listening on porthttp://localhost:48884/
- In Revit, navigate to the pyRevit tab
- Open Extensions
- Select the MCP Server for Revit Python Extension > Install extension
- Select location, default is%APPDATA%\Roaming\pyRevit\Extensions
- Enable and wait for pyRevit to reload. Restart Revit if necessary.

Manual Installation on a custom directory:

- Clone the repo in a custom location:
git clone https://github.com/mcp-servers-for-revit/mcp-server-for-revit-python

Once installed, test that the Routes API is working:

http://localhost:48884/revit_mcp/status/

If successful, you should see a response like:

{"status": "active", "health": "healthy", "revit_available": true, "document_title": "your_revit_filename", "api_name": "revit_mcp"}

The Routes Service will now load automatically whenever you start Revit. To disable it, simply remove the extension path from the pyRevit settings.

The MCP SDK includes a handy inspector tool for debugging:

Then accesshttp://127.0.0.1:6274in your browser to test your MCP server interactively.

The MCP server supports multiple transport modes for different use cases:

Running with combined transport (recommended for HTTP):

uv run --with "mcp[cli]" main.py --combined

This starts the server onhttp://127.0.0.1:8000with both SSE and streamable-HTTP endpoints available.

# Test streamable-http curl -X POST http://localhost:8000/mcp # Test SSE curl http://localhost:8000/sse

The simplest way to install your MCP server in Claude Desktop:
- Open Claude Desktop → Settings → Developer → Edit Config
- Add this to themcpServerssection:

{ "mcpServers": { "Revit Connector": { "command": "uv", "args": [ "run", "--with", "mcp[cli]", "mcp", "run", "/absolute/path/to/main.py" ] } } }

For HTTP transport mode, configure Claude Desktop with:

{ "mcpServers": { "Revit Connector": { "url": "http://localhost:8000/mcp" } } }
claude mcp add -s user "Revit-Connector" -- uv run --with "mcp[cli]" mcp run /absolute/path/to/main.py

The modular architecture of this project makes adding functionalities relatively simple. The provided LLM.txt file also gives your language model the necessary context to get started right away.

Part 1: Create the Route Module in Revit

Create a new Python file within therevit-mcp-python.extension/revit_mcp/directory (e.g.,revit_mcp/your_module.py). This module will contain all the related functions you want to expose.

# In revit-mcp-python.extension/revit_mcp/your_module.py # -- coding: UTF-8 -- """ Your Module for Revit MCP Handles your specific functionality. """ from pyrevit import routes, revit, DB import json import logging # Standard logger setup logger = logging.getLogger(__name__) def register_your_routes(api): """Register all your routes with the API.""" # ---- Example 1: A GET request for reading data ---- @api.route('/your_endpoint/', methods=["GET"]) def get_project_title(doc): """Gets the project title from the Revit model.""" try: value = doc.Title return routes.make_response(data={"status": "success", "data": value}) except Exception as e: logger.error("Get project title failed: {}".format(str(e))) return routes.make_response(data={"error": str(e)}, status=500) # ---- Example 2: A POST request for modifying the model ---- @api.route('/modify_model/', methods=["POST"]) def modify_model(doc, request): """Handles POST requests for modifying the Revit model.""" try: data = json.loads(request.data) if isinstance(request.data, str) else request.data # Use a transaction for all model modifications t = DB.Transaction(doc, "Modify Model via MCP") t.Start() try: element_id = data.get("element_id") new_value = data.get("new_value") element = doc.GetElement(DB.ElementId(int(element_id))) param = element.LookupParameter("Comments") param.Set(new_value) t.Commit() return routes.make_response(data={"status": "success", "result": "Element modified."}) except Exception as tx_error: if t.HasStarted() and not t.HasEnded(): t.RollBack() raise tx_error except Exception as e: logger.error("Modify model failed: {}".format(str(e))) return routes.make_response(data={"error": str(e)}, status=500) logger.info("Your custom routes were registered successfully.")

Create the corresponding tools for the MCP server in thetools/directory (e.g.,tools/your_tools.py). This module will use therevit_getandrevit_posthelpers frommain.py.

# In tools/your_tools.py # -- coding: utf-8 -- """Your tools for the MCP server.""" from mcp.server.fastmcp import Context from .utils import format_response def register_your_tools(mcp, revit_get, revit_post, revit_image=None): """Register your tools with the MCP server.""" # ---- Tool for the GET request ---- @mcp.tool() async def get_revit_project_title(ctx: Context) -> str: """ Retrieves the title of the currently open Revit project. """ response = await revit_get("/your_endpoint/", ctx) return format_response(response) # ---- Tool for the POST request ---- @mcp.tool() async def modify_revit_element_comment( element_id: int, new_value: str, ctx: Context = None ) -> str: """ Modifies the 'Comments' parameter of a specific element. Args: element_id: The ID of the element to modify. new_value: The new comment to apply to the element. """ payload = {"element_id": element_id, "new_value": new_value} response = await revit_post("/modify_model/", payload, ctx) return format_response(response)

Openrevit-mcp-python.extension/startup.pyand add your new route registration function.

# In revit-mcp-python.extension/startup.py # ... (other imports) # Import the registration function from your new module from revit_mcp.your_module import register_your_routes def register_routes(): """Register all MCP route modules""" api = routes.API('revit_mcp') try: # ... (existing route registrations) # Register your new routes (this registers all functions inside) register_your_routes(api) logger.info("All MCP routes registered successfully") except Exception as e: logger.error("Failed to register MCP routes: {}".format(str(e))) raise

Opentools/__init__.pyand add your new tool registration function.

# In tools/__init__.py # ... (other tool imports) # Import the registration function from your new tool module from .your_tools import register_your_tools def register_tools(mcp_server, revit_get_func, revit_post_func, revit_image_func): """Register all tools with the MCP server""" # ... (existing tool registrations) # Register your new tools (this registers all tools inside) register_your_tools(mcp_server, revit_get_func, revit_post_func, revit_image_func) return mcp_server

This is a work in progress and more of a demonstration than a fully-featured product. Future improvements could include:

- Creating a Client inside Revit
- Implementing compatibilities with other language Models
- Authentication and security enhancements
- More advanced Revit tools and capabilities
- Better error handling and debugging features
- Benchmarking with local models
- Documentation and examples for common use cases
- ...

Contributions are welcome! Feel free to submit pull requests or open issues for any bugs or feature requests. Feel free to reach out to me if you have any questions, ideas

This is a web browser that enables your coding agent, such as Claude Code, to visit websites on your behalf and assist you in identifying bugs or creating UI test cases.

Inline review comments for markdown specs and design docs. Agents request human review mid-task via MCP and pause until you send feedback.

Local-first PDF engine for AI agents. Zero-dep TypeScript, PDF/A, signatures, 800+ pages/sec.

Dynamically manage AI personas from markdown files for AI assistants like Claude.

Local-first MCP tools for AI-assisted work receipts, source intake, workspace maps, routing ledgers, action receipts, and MATCH / DRIFT / UNVERIFIABLE verification.

An MCP server for managing and serving prompts from markdown files with YAML frontmatter support.

Logs file edits, decisions, and commands so agents stay in sync, avoid conflicts, and pick up where others left off.

An MCP server for viewing, editing, and creating text files, based on the Claude built-in text editor tool.

A file mover tool that stages and executes file moves safely. Works as both a CLI tool and an MCP server for AI agents.

Filesystem MCP server for secure file operations inside configured directories, including reading, writing, listing, and project navigation.

Provides file system operations, analysis, and manipulation capabilities through a standardized tool interface.

No reviews yet — be the first

Sign in to leave a review

Use Google, GitHub, or an email account so ratings stay tied to real people.

Email sign in

No reviews posted yet.