An MCP server for generating and managing Grasshopper Python components
Project description
Sand Martin
Sand Martin is an MCP (Model Context Protocol) server that enables real-time orchestration of the Grasshopper canvas within Rhino. It allows Large Language Models (like Claude) to create components, inject Python code, and wire nodes together directly in a live Grasshopper session.
Demo
1. Authenticate with the Agent
2. Update Slider Values
3. Inject and Run Code
Architecture
Sand Martin uses a Client-Server model:
- SandMartin.Host (C#): A Grasshopper plugin (
.gha) that runs an internal HTTP server inside the Rhino process. It has direct access to theGrasshopper.KernelAPI. - Sand Martin Bridge (Python): A lightweight MCP server that translates LLM requests into commands for the Host server.
Getting Started
1. Requirements
- Rhino 8 (macOS/Windows)
- .NET SDK 6.0+ (for building the Host)
- Python 3.10+
2. Install the Python Bridge
You can install the Sand Martin bridge directly from PyPI:
pip install sand-martin
3. Install the Rhino/Grasshopper Plugin
Option A: Download from Food4Rhino (Recommended)
- Download the latest release from Food4Rhino.
- In Grasshopper, go to File > Special Folders > Components Folder.
- Place the downloaded
.ghafile (and any accompanying.dllfiles) into that folder. - Restart Rhino.
Option B: Build from Source
From the root directory, open sand-martin.sln in your IDE (Visual Studio or Rider) and build the SandMartin.Host project. Copy the resulting .gha file to your Grasshopper components folder.
Configuration for Claude Desktop
Add the following to your claude_desktop_config.json:
{
"mcpServers": {
"sand-martin": {
"command": "python",
"args": ["/PATH/TO/YOUR/sand-martin/src/sand_martin/server.py"]
}
}
}
Note: Replace /PATH/TO/YOUR/ with the actual absolute path to this repository.
Usage
- Start Rhino and open Grasshopper.
- Start the Server: Drag the "Sand Martin Server" component onto the canvas and set the Run toggle to
True. - Authenticate the Agent:
- Auto-Discovery (Default): The Python bridge automatically reads the security token from your system's temporary directory. No manual setup is usually required!
- Manual Fallback: If auto-discovery fails, a unique token is printed to the Rhino Command Line.
- Agent Behavior: If the agent cannot find the token, it will explicitly ask you to copy it from the Rhino Command History (look for "SAND MARTIN SECURITY TOKEN"). You can then paste it directly into the chat.
- Orchestrate: You can now ask Claude to:
- "Create a Python component that calculates a Fibonacci sequence."
- "Connect a Slider to the input of my component."
- "Show me the current state of my canvas."
Security
Sand Martin includes built-in security features to protect your environment:
- Auth Token: A unique token is generated every time the server starts. You must set this in your environment as
SAND_MARTIN_TOKEN. - Code Gating: You can disable code injection at any time by setting
AllowCodeInjectiontoFalseon the Grasshopper component. - Localhost Only: The server only accepts connections from
127.0.0.1.
See SECURITY.md for more details.
⚠️ Warning: Always set the
Runtoggle toFalseon the Sand Martin component when not in use.
Project Structure
src/SandMartin.Host/: C# source for the Grasshopper plugin.src/sand_martin/: Python source for the MCP server.sand-martin.sln: Visual Studio Solution file.pyproject.toml: Python project configuration.
License
This project is licensed under the Apache License 2.0.
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file sand_martin-0.5.0.tar.gz.
File metadata
- Download URL: sand_martin-0.5.0.tar.gz
- Upload date:
- Size: 2.2 MB
- Tags: Source
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
1df2f80135bb4ade539b29e376a2b2ada0e83e36304afc7cc65fe9cf1a0bd0d2
|
|
| MD5 |
c94b4f9d7cdaef22ec265a4b6d828a01
|
|
| BLAKE2b-256 |
6953f3283457f5817f91659ceadd69f68b55e4870896f17fdaa88c6d49d2b818
|
Provenance
The following attestation bundles were made for sand_martin-0.5.0.tar.gz:
Publisher:
pypi-publish.yml on LeoYuanjieLi/sand-martin
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
sand_martin-0.5.0.tar.gz -
Subject digest:
1df2f80135bb4ade539b29e376a2b2ada0e83e36304afc7cc65fe9cf1a0bd0d2 - Sigstore transparency entry: 1962992624
- Sigstore integration time:
-
Permalink:
LeoYuanjieLi/sand-martin@8ad9dc7ceeff7d13ebb8437def5d3867ed5ac8c5 -
Branch / Tag:
refs/tags/v0.5.0 - Owner: https://github.com/LeoYuanjieLi
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
pypi-publish.yml@8ad9dc7ceeff7d13ebb8437def5d3867ed5ac8c5 -
Trigger Event:
push
-
Statement type:
File details
Details for the file sand_martin-0.5.0-py3-none-any.whl.
File metadata
- Download URL: sand_martin-0.5.0-py3-none-any.whl
- Upload date:
- Size: 14.9 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
fc500b9c4348e1db3e00244333afe31b1cf75e6588474fa45449aae994b6d80b
|
|
| MD5 |
70187fdde4c95bbc777e59f7c2a059c3
|
|
| BLAKE2b-256 |
5e8913eb86e27d927f058b74715953a24dd3b40df02a3c9b06f809a544c408c1
|
Provenance
The following attestation bundles were made for sand_martin-0.5.0-py3-none-any.whl:
Publisher:
pypi-publish.yml on LeoYuanjieLi/sand-martin
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
sand_martin-0.5.0-py3-none-any.whl -
Subject digest:
fc500b9c4348e1db3e00244333afe31b1cf75e6588474fa45449aae994b6d80b - Sigstore transparency entry: 1962992742
- Sigstore integration time:
-
Permalink:
LeoYuanjieLi/sand-martin@8ad9dc7ceeff7d13ebb8437def5d3867ed5ac8c5 -
Branch / Tag:
refs/tags/v0.5.0 - Owner: https://github.com/LeoYuanjieLi
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
pypi-publish.yml@8ad9dc7ceeff7d13ebb8437def5d3867ed5ac8c5 -
Trigger Event:
push
-
Statement type: