Merge upstream/main: CoplayDev rebrand with bridge stability improvements
This merge combines upstream's organizational rebrand and updates with our comprehensive bridge stability improvements: **From Upstream:** - CoplayDev organizational rebrand (README, LICENSE, documentation) - Updated logo and deployment scripts - Python version pinning (.python-version file) **From Our Branch (Preserved):** - Comprehensive bridge stability improvements (threading, heartbeat, retries) - Enhanced debugging and diagnostic features - Embedded server installation approach (more reliable than git-based) - Broader Python compatibility (>=3.10 vs >=3.12) - Advanced port management with per-project persistence - Auto-setup and connection reliability features - Robust error handling and recovery mechanisms **Key Technical Decisions:** - Used our comprehensive UnityMcpBridge.cs (625 lines vs 473) with all stability features - Maintained embedded server approach over upstream's git-based installer - Preserved broader Python compatibility (>=3.10) for better accessibility - Used our optimized connection settings and retry logic - Kept our user-centric server installation approach (on-demand vs automatic) 🤖 Generated with [Claude Code](https://claude.ai/code) Co-Authored-By: Claude <noreply@anthropic.com>main
parent
f24e124c15
commit
c0de38e1e7
2
LICENSE
2
LICENSE
|
|
@ -1,6 +1,6 @@
|
|||
MIT License
|
||||
|
||||
Copyright (c) 2025 Justin P Barnett
|
||||
Copyright (c) 2025 CoplayDev
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
|
|
|
|||
|
|
@ -48,7 +48,7 @@ Restores original files from backup.
|
|||
|
||||
Unity package cache is typically located at:
|
||||
```
|
||||
X:\UnityProject\Library\PackageCache\com.justinpbarnett.unity-mcp@1.0.0
|
||||
X:\UnityProject\Library\PackageCache\com.coplaydev.unity-mcp@1.0.0
|
||||
```
|
||||
|
||||
To find it:
|
||||
|
|
|
|||
85
README.md
85
README.md
|
|
@ -1,11 +1,15 @@
|
|||
# Unity MCP ✨
|
||||
|
||||
#### Proudly sponsored and maintained by [Coplay](https://www.coplay.dev/?ref=unity-mcp), the AI assistant for Unity. [Read the backstory here.](https://www.coplay.dev/blog/coplay-and-open-source-unity-mcp-join-forces)
|
||||
|
||||
[](https://discord.gg/y4p8KfzrN4)
|
||||
[](https://unity.com/releases/editor/archive)
|
||||
[](https://www.python.org)
|
||||
[](https://modelcontextprotocol.io/introduction)
|
||||

|
||||

|
||||

|
||||

|
||||
[](https://opensource.org/licenses/MIT)
|
||||
[](https://www.coplay.dev/?ref=unity-mcp)
|
||||
|
||||
**Create your Unity apps with LLMs!**
|
||||
|
||||
|
|
@ -13,14 +17,12 @@ Unity MCP acts as a bridge, allowing AI assistants (like Claude, Cursor) to inte
|
|||
|
||||
## 💬 Join Our Community
|
||||
|
||||
### [Discord](https://discord.gg/vhTUxXaqYr)
|
||||
### [Discord](https://discord.gg/y4p8KfzrN4)
|
||||
|
||||
**Get help, share ideas, and collaborate with other Unity MCP developers!**
|
||||
|
||||
|
||||
---
|
||||
|
||||
|
||||
## Key Features 🚀
|
||||
|
||||
* **🗣️ Natural Language Control:** Instruct your LLM to perform Unity tasks.
|
||||
|
|
@ -35,7 +37,7 @@ Unity MCP acts as a bridge, allowing AI assistants (like Claude, Cursor) to inte
|
|||
|
||||
* `read_console`: Gets messages from or clears the console.
|
||||
* `manage_script`: Manages C# scripts (create, read, update, delete).
|
||||
* `manage_editor`: Controls and queries the editor's state and settings.
|
||||
* `manage_editor`: Controls and queries the editor\'s state and settings.
|
||||
* `manage_scene`: Manages scenes (load, save, create, get hierarchy, etc.).
|
||||
* `manage_asset`: Performs asset operations (import, create, modify, delete, etc.).
|
||||
* `manage_shader`: Performs shader CRUD operations (create, read, modify, delete).
|
||||
|
|
@ -62,7 +64,6 @@ Unity MCP connects your tools using two components:
|
|||
|
||||
### Prerequisites
|
||||
|
||||
|
||||
* **Git CLI:** For cloning the server code. [Download Git](https://git-scm.com/downloads)
|
||||
* **Python:** Version 3.12 or newer. [Download Python](https://www.python.org/downloads/)
|
||||
* **Unity Hub & Editor:** Version 2020.3 LTS or newer. [Download Unity](https://unity.com/download)
|
||||
|
|
@ -76,6 +77,7 @@ Unity MCP connects your tools using two components:
|
|||
* [Claude Code](https://github.com/anthropics/claude-code)
|
||||
* [Cursor](https://www.cursor.com/en/downloads)
|
||||
* [Visual Studio Code Copilot](https://code.visualstudio.com/docs/copilot/overview)
|
||||
* [Windsurf](https://windsurf.com)
|
||||
* *(Others may work with manual config)*
|
||||
* <details> <summary><strong>[Optional] Roslyn for Advanced Script Validation</strong></summary>
|
||||
|
||||
|
|
@ -98,7 +100,6 @@ Unity MCP connects your tools using two components:
|
|||
|
||||
**Note:** Without Roslyn, script validation falls back to basic structural checks. Roslyn enables full C# compiler diagnostics with precise error reporting.</details>
|
||||
|
||||
|
||||
### Step 1: Install the Unity Package (Bridge)
|
||||
|
||||
1. Open your Unity project.
|
||||
|
|
@ -106,11 +107,13 @@ Unity MCP connects your tools using two components:
|
|||
3. Click `+` -> `Add package from git URL...`.
|
||||
4. Enter:
|
||||
```
|
||||
https://github.com/justinpbarnett/unity-mcp.git?path=/UnityMcpBridge
|
||||
https://github.com/CoplayDev/unity-mcp.git?path=/UnityMcpBridge
|
||||
```
|
||||
5. Click `Add`.
|
||||
6. The MCP Server should automatically be installed onto your machine as a result of this process.
|
||||
|
||||
**Note:** If you installed the MCP Server before Coplay's maintenance, you will need to uninstall the old package before re-installing the new one.
|
||||
|
||||
### Step 2: Configure Your MCP Client
|
||||
|
||||
Connect your MCP Client (Claude, Cursor, etc.) to the Python server you installed in Step 1.
|
||||
|
|
@ -121,13 +124,13 @@ Connect your MCP Client (Claude, Cursor, etc.) to the Python server you installe
|
|||
|
||||
1. In Unity, go to `Window > Unity MCP`.
|
||||
2. Click `Auto Configure` on the IDE you uses.
|
||||
3. Look for a green status indicator 🟢 and "Connected". *(This attempts to modify the MCP Client's config file automatically)*.
|
||||
3. Look for a green status indicator 🟢 and "Connected". *(This attempts to modify the MCP Client\'s config file automatically)*.
|
||||
|
||||
**Option B: Manual Configuration**
|
||||
|
||||
If Auto-Configure fails or you use a different client:
|
||||
|
||||
1. **Find your MCP Client's configuration file.** (Check client documentation).
|
||||
1. **Find your MCP Client\'s configuration file.** (Check client documentation).
|
||||
* *Claude Example (macOS):* `~/Library/Application Support/Claude/claude_desktop_config.json`
|
||||
* *Claude Example (Windows):* `%APPDATA%\Claude\claude_desktop_config.json`
|
||||
2. **Edit the file** to add/update the `mcpServers` section, using the *exact* paths from Step 1.
|
||||
|
|
@ -174,6 +177,7 @@ If Auto-Configure fails or you use a different client:
|
|||
}
|
||||
}
|
||||
```
|
||||
|
||||
(Replace YOUR_USERNAME if using ~/bin)
|
||||
|
||||
**Linux:**
|
||||
|
|
@ -197,18 +201,18 @@ If Auto-Configure fails or you use a different client:
|
|||
|
||||
(Replace YOUR_USERNAME)
|
||||
|
||||
|
||||
|
||||
**For Claude Code**
|
||||
|
||||
If you're using Claude Code, you can register the MCP server using these commands:
|
||||
If you\'re using Claude Code, you can register the MCP server using these commands:
|
||||
|
||||
**macOS:**
|
||||
|
||||
```bash
|
||||
claude mcp add UnityMCP -- uv --directory /[PATH_TO]/UnityMCP/UnityMcpServer/src run server.py
|
||||
```
|
||||
|
||||
**Windows:**
|
||||
|
||||
```bash
|
||||
claude mcp add UnityMCP -- "C:/Users/USERNAME/AppData/Roaming/Python/Python313/Scripts/uv.exe" --directory "C:/Users/USERNAME/AppData/Local/Programs/UnityMCP/UnityMcpServer/src" run server.py
|
||||
```
|
||||
|
|
@ -231,6 +235,7 @@ claude mcp add UnityMCP -- "C:/Users/USERNAME/AppData/Roaming/Python/Python313/S
|
|||
## Future Dev Plans (Besides PR) 📝
|
||||
|
||||
### 🔴 High Priority
|
||||
|
||||
- [ ] **Asset Generation Improvements** - Enhanced server request handling and asset pipeline optimization
|
||||
- [ ] **Code Generation Enhancements** - Improved generated code quality and error handling
|
||||
- [ ] **Robust Error Handling** - Comprehensive error messages, recovery mechanisms, and graceful degradation
|
||||
|
|
@ -238,10 +243,12 @@ claude mcp add UnityMCP -- "C:/Users/USERNAME/AppData/Roaming/Python/Python313/S
|
|||
- [ ] **Documentation Expansion** - Complete tutorials for custom tool creation and API reference
|
||||
|
||||
### 🟡 Medium Priority
|
||||
|
||||
- [ ] **Custom Tool Creation GUI** - Visual interface for users to create and configure their own MCP tools
|
||||
- [ ] **Advanced Logging System** - Logging with filtering, export, and debugging capabilities
|
||||
|
||||
### 🟢 Low Priority
|
||||
|
||||
- [ ] **Mobile Platform Support** - Extended toolset for mobile development workflows and platform-specific features
|
||||
- [ ] **Easier Tool Setup**
|
||||
- [ ] **Plugin Marketplace** - Community-driven tool sharing and distribution platform
|
||||
|
|
@ -254,6 +261,7 @@ claude mcp add UnityMCP -- "C:/Users/USERNAME/AppData/Roaming/Python/Python313/S
|
|||
</details>
|
||||
|
||||
### 🔬 Research & Exploration
|
||||
|
||||
- [ ] **AI-Powered Asset Generation** - Integration with AI tools for automatic 3D models, textures, and animations
|
||||
- [ ] **Real-time Collaboration** - Live editing sessions between multiple developers *(Currently in progress)*
|
||||
- [ ] **Analytics Dashboard** - Usage analytics, project insights, and performance metrics
|
||||
|
|
@ -266,7 +274,7 @@ claude mcp add UnityMCP -- "C:/Users/USERNAME/AppData/Roaming/Python/Python313/S
|
|||
|
||||
### Development Tools
|
||||
|
||||
If you're contributing to Unity MCP or want to test core changes, we have development tools to streamline your workflow:
|
||||
If you\'re contributing to Unity MCP or want to test core changes, we have development tools to streamline your workflow:
|
||||
|
||||
- **Development Deployment Scripts**: Quickly deploy and test your changes to Unity MCP Bridge and Python Server
|
||||
- **Automatic Backup System**: Safe testing with easy rollback capabilities
|
||||
|
|
@ -289,8 +297,7 @@ Help make Unity MCP better!
|
|||
|
||||
5. **Push** your branch.
|
||||
|
||||
6. **Open a Pull Request** against the master branch.
|
||||
|
||||
6. **Open a Pull Request** against the main branch.
|
||||
|
||||
---
|
||||
|
||||
|
|
@ -300,53 +307,37 @@ Help make Unity MCP better!
|
|||
<summary><strong>Click to view common issues and fixes...</strong></summary>
|
||||
|
||||
- **Unity Bridge Not Running/Connecting:**
|
||||
|
||||
- Ensure Unity Editor is open.
|
||||
|
||||
- Check the status window: Window > Unity MCP.
|
||||
|
||||
- Restart Unity.
|
||||
|
||||
- **MCP Client Not Connecting / Server Not Starting:**
|
||||
|
||||
- **Verify Server Path:** Double-check the --directory path in your MCP Client's JSON config. It must exactly match the location where you cloned the UnityMCP repository in Installation Step 1 (e.g., .../Programs/UnityMCP/UnityMcpServer/src).
|
||||
|
||||
- **Verify uv:** Make sure uv is installed and working (pip show uv).
|
||||
|
||||
- **Verify Server Path:** Double-check the --directory path in your MCP Client\'s JSON config. It must exactly match the location where you cloned the UnityMCP repository in Installation Step 1 (e.g., .../Programs/UnityMCP/UnityMcpServer/src).
|
||||
- **Verify uv:** Make sure `uv` is installed and working (pip show uv).
|
||||
- **Run Manually:** Try running the server directly from the terminal to see errors: `# Navigate to the src directory first! cd /path/to/your/UnityMCP/UnityMcpServer/src uv run server.py`
|
||||
|
||||
- **Permissions (macOS/Linux):** If you installed the server in a system location like /usr/local/bin, ensure the user running the MCP client has permission to execute uv and access files there. Installing in ~/bin might be easier.
|
||||
|
||||
- **Auto-Configure Failed:**
|
||||
|
||||
- Use the Manual Configuration steps. Auto-configure might lack permissions to write to the MCP client's config file.
|
||||
|
||||
- Use the Manual Configuration steps. Auto-configure might lack permissions to write to the MCP client\'s config file.
|
||||
|
||||
</details>
|
||||
|
||||
Still stuck? [Open an Issue](https://www.google.com/url?sa=E&q=https%3A%2F%2Fgithub.com%2Fjustinpbarnett%2Funity-mcp%2Fissues) or [Join the Discord](https://discord.gg/vhTUxXaqYr)!
|
||||
|
||||
---
|
||||
|
||||
## Contact 👋
|
||||
|
||||
- **justinpbarnett:** [X/Twitter](https://www.google.com/url?sa=E&q=https%3A%2F%2Fx.com%2Fjustinpbarnett)
|
||||
- **scriptwonder**: [Email](mailto:swu85@ur.rochester.edu), [LinkedIn](https://www.linkedin.com/in/shutong-wu-214043172/)
|
||||
|
||||
Still stuck? [Open an Issue](https://github.com/CoplayDev/unity-mcp/issues) or [Join the Discord](https://discord.gg/y4p8KfzrN4)!
|
||||
|
||||
---
|
||||
|
||||
## License 📜
|
||||
|
||||
MIT License. See [LICENSE](https://www.google.com/url?sa=E&q=https%3A%2F%2Fgithub.com%2Fjustinpbarnett%2Funity-mcp%2Fblob%2Fmaster%2FLICENSE) file.
|
||||
MIT License. See [LICENSE](LICENSE) file.
|
||||
|
||||
---
|
||||
|
||||
## Acknowledgments 🙏
|
||||
|
||||
Thanks to the contributors and the Unity team.
|
||||
|
||||
|
||||
## Star History
|
||||
|
||||
[](https://www.star-history.com/#justinpbarnett/unity-mcp&Date)
|
||||
[](https://www.star-history.com/#CoplayDev/unity-mcp&Date)
|
||||
|
||||
## Sponsor
|
||||
|
||||
<p align="center">
|
||||
<a href="https://www.coplay.dev/?ref=unity-mcp" target="_blank" rel="noopener noreferrer">
|
||||
<img src="logo.png" alt="Coplay Logo" width="100%">
|
||||
</a>
|
||||
</p>
|
||||
|
|
|
|||
|
|
@ -25,18 +25,18 @@ namespace UnityMcpBridge.Editor.Helpers
|
|||
{
|
||||
try
|
||||
{
|
||||
Debug.Log("Unity MCP: Installing Python server...");
|
||||
Debug.Log("<b><color=#2EA3FF>UNITY-MCP</color></b>: Installing Python server...");
|
||||
ServerInstaller.EnsureServerInstalled();
|
||||
|
||||
// Mark as installed
|
||||
EditorPrefs.SetBool(InstallationFlagKey, true);
|
||||
|
||||
Debug.Log("Unity MCP: Python server installation completed successfully.");
|
||||
Debug.Log("<b><color=#2EA3FF>UNITY-MCP</color></b>: Python server installation completed successfully.");
|
||||
}
|
||||
catch (System.Exception ex)
|
||||
{
|
||||
Debug.LogError($"Unity MCP: Failed to install Python server: {ex.Message}");
|
||||
Debug.LogWarning("Unity MCP: You may need to manually install the Python server. Check the Unity MCP Editor Window for instructions.");
|
||||
Debug.LogError($"<b><color=#2EA3FF>UNITY-MCP</color></b>: Failed to install Python server: {ex.Message}");
|
||||
Debug.LogWarning("<b><color=#2EA3FF>UNITY-MCP</color></b>: You may need to manually install the Python server. Check the Unity MCP Editor Window for instructions.");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,5 +1,6 @@
|
|||
using System;
|
||||
using System.IO;
|
||||
using UnityEditor;
|
||||
using System.Net;
|
||||
using System.Net.Sockets;
|
||||
using System.Security.Cryptography;
|
||||
|
|
@ -15,6 +16,12 @@ namespace UnityMcpBridge.Editor.Helpers
|
|||
/// </summary>
|
||||
public static class PortManager
|
||||
{
|
||||
private static bool IsDebugEnabled()
|
||||
{
|
||||
try { return EditorPrefs.GetBool("UnityMCP.DebugLogs", false); }
|
||||
catch { return false; }
|
||||
}
|
||||
|
||||
private const int DefaultPort = 6400;
|
||||
private const int MaxPortAttempts = 100;
|
||||
private const string RegistryFileName = "unity-mcp-port.json";
|
||||
|
|
@ -41,7 +48,7 @@ namespace UnityMcpBridge.Editor.Helpers
|
|||
string.Equals(storedConfig.project_path ?? string.Empty, Application.dataPath ?? string.Empty, StringComparison.OrdinalIgnoreCase) &&
|
||||
IsPortAvailable(storedConfig.unity_port))
|
||||
{
|
||||
Debug.Log($"Using stored port {storedConfig.unity_port} for current project");
|
||||
if (IsDebugEnabled()) Debug.Log($"<b><color=#2EA3FF>UNITY-MCP</color></b>: Using stored port {storedConfig.unity_port} for current project");
|
||||
return storedConfig.unity_port;
|
||||
}
|
||||
|
||||
|
|
@ -50,7 +57,7 @@ namespace UnityMcpBridge.Editor.Helpers
|
|||
{
|
||||
if (WaitForPortRelease(storedConfig.unity_port, 1500))
|
||||
{
|
||||
Debug.Log($"Stored port {storedConfig.unity_port} became available after short wait");
|
||||
if (IsDebugEnabled()) Debug.Log($"<b><color=#2EA3FF>UNITY-MCP</color></b>: Stored port {storedConfig.unity_port} became available after short wait");
|
||||
return storedConfig.unity_port;
|
||||
}
|
||||
// Prefer sticking to the same port; let the caller handle bind retries/fallbacks
|
||||
|
|
@ -71,7 +78,7 @@ namespace UnityMcpBridge.Editor.Helpers
|
|||
{
|
||||
int newPort = FindAvailablePort();
|
||||
SavePort(newPort);
|
||||
Debug.Log($"Discovered and saved new port: {newPort}");
|
||||
if (IsDebugEnabled()) Debug.Log($"<b><color=#2EA3FF>UNITY-MCP</color></b>: Discovered and saved new port: {newPort}");
|
||||
return newPort;
|
||||
}
|
||||
|
||||
|
|
@ -84,18 +91,18 @@ namespace UnityMcpBridge.Editor.Helpers
|
|||
// Always try default port first
|
||||
if (IsPortAvailable(DefaultPort))
|
||||
{
|
||||
Debug.Log($"Using default port {DefaultPort}");
|
||||
if (IsDebugEnabled()) Debug.Log($"<b><color=#2EA3FF>UNITY-MCP</color></b>: Using default port {DefaultPort}");
|
||||
return DefaultPort;
|
||||
}
|
||||
|
||||
Debug.Log($"Default port {DefaultPort} is in use, searching for alternative...");
|
||||
if (IsDebugEnabled()) Debug.Log($"<b><color=#2EA3FF>UNITY-MCP</color></b>: Default port {DefaultPort} is in use, searching for alternative...");
|
||||
|
||||
// Search for alternatives
|
||||
for (int port = DefaultPort + 1; port < DefaultPort + MaxPortAttempts; port++)
|
||||
{
|
||||
if (IsPortAvailable(port))
|
||||
{
|
||||
Debug.Log($"Found available port {port}");
|
||||
if (IsDebugEnabled()) Debug.Log($"<b><color=#2EA3FF>UNITY-MCP</color></b>: Found available port {port}");
|
||||
return port;
|
||||
}
|
||||
}
|
||||
|
|
@ -204,7 +211,7 @@ namespace UnityMcpBridge.Editor.Helpers
|
|||
string legacy = Path.Combine(GetRegistryDirectory(), RegistryFileName);
|
||||
File.WriteAllText(legacy, json);
|
||||
|
||||
Debug.Log($"Saved port {port} to storage");
|
||||
if (IsDebugEnabled()) Debug.Log($"<b><color=#2EA3FF>UNITY-MCP</color></b>: Saved port {port} to storage");
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -281,7 +281,7 @@ namespace UnityMcpBridge.Editor.Helpers
|
|||
return false;
|
||||
}
|
||||
|
||||
Debug.Log("Unity MCP: Python environment repaired successfully.");
|
||||
Debug.Log("<b><color=#2EA3FF>UNITY-MCP</color></b>: Python environment repaired successfully.");
|
||||
return true;
|
||||
}
|
||||
catch (Exception ex)
|
||||
|
|
@ -305,7 +305,32 @@ namespace UnityMcpBridge.Editor.Helpers
|
|||
catch { }
|
||||
|
||||
string home = Environment.GetFolderPath(Environment.SpecialFolder.UserProfile) ?? string.Empty;
|
||||
string[] candidates =
|
||||
|
||||
// Platform-specific candidate lists
|
||||
string[] candidates;
|
||||
if (RuntimeInformation.IsOSPlatform(OSPlatform.Windows))
|
||||
{
|
||||
candidates = new[]
|
||||
{
|
||||
// Common per-user installs
|
||||
Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData) ?? string.Empty, @"Programs\Python\Python313\Scripts\uv.exe"),
|
||||
Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData) ?? string.Empty, @"Programs\Python\Python312\Scripts\uv.exe"),
|
||||
Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData) ?? string.Empty, @"Programs\Python\Python311\Scripts\uv.exe"),
|
||||
Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData) ?? string.Empty, @"Programs\Python\Python310\Scripts\uv.exe"),
|
||||
Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData) ?? string.Empty, @"Python\Python313\Scripts\uv.exe"),
|
||||
Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData) ?? string.Empty, @"Python\Python312\Scripts\uv.exe"),
|
||||
Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData) ?? string.Empty, @"Python\Python311\Scripts\uv.exe"),
|
||||
Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData) ?? string.Empty, @"Python\Python310\Scripts\uv.exe"),
|
||||
// Program Files style installs (if a native installer was used)
|
||||
Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.ProgramFiles) ?? string.Empty, @"uv\uv.exe"),
|
||||
// Try simple name resolution later via PATH
|
||||
"uv.exe",
|
||||
"uv"
|
||||
};
|
||||
}
|
||||
else
|
||||
{
|
||||
candidates = new[]
|
||||
{
|
||||
"/opt/homebrew/bin/uv",
|
||||
"/usr/local/bin/uv",
|
||||
|
|
@ -319,17 +344,44 @@ namespace UnityMcpBridge.Editor.Helpers
|
|||
// Fallback to PATH resolution by name
|
||||
"uv"
|
||||
};
|
||||
}
|
||||
|
||||
foreach (string c in candidates)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (ValidateUvBinary(c)) return c;
|
||||
if (File.Exists(c) && ValidateUvBinary(c)) return c;
|
||||
}
|
||||
catch { /* ignore */ }
|
||||
}
|
||||
|
||||
// Try which uv (explicit path)
|
||||
// Use platform-appropriate which/where to resolve from PATH
|
||||
try
|
||||
{
|
||||
if (RuntimeInformation.IsOSPlatform(OSPlatform.Windows))
|
||||
{
|
||||
var wherePsi = new System.Diagnostics.ProcessStartInfo
|
||||
{
|
||||
FileName = "where",
|
||||
Arguments = "uv.exe",
|
||||
UseShellExecute = false,
|
||||
RedirectStandardOutput = true,
|
||||
RedirectStandardError = true,
|
||||
CreateNoWindow = true
|
||||
};
|
||||
using var wp = System.Diagnostics.Process.Start(wherePsi);
|
||||
string output = wp.StandardOutput.ReadToEnd().Trim();
|
||||
wp.WaitForExit(3000);
|
||||
if (wp.ExitCode == 0 && !string.IsNullOrEmpty(output))
|
||||
{
|
||||
foreach (var line in output.Split(new[] { '\r', '\n' }, StringSplitOptions.RemoveEmptyEntries))
|
||||
{
|
||||
string path = line.Trim();
|
||||
if (File.Exists(path) && ValidateUvBinary(path)) return path;
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
var whichPsi = new System.Diagnostics.ProcessStartInfo
|
||||
{
|
||||
|
|
@ -348,6 +400,7 @@ namespace UnityMcpBridge.Editor.Helpers
|
|||
if (ValidateUvBinary(output)) return output;
|
||||
}
|
||||
}
|
||||
}
|
||||
catch { }
|
||||
|
||||
// Manual PATH scan
|
||||
|
|
@ -359,8 +412,11 @@ namespace UnityMcpBridge.Editor.Helpers
|
|||
{
|
||||
try
|
||||
{
|
||||
string candidate = Path.Combine(part, "uv");
|
||||
if (File.Exists(candidate) && ValidateUvBinary(candidate)) return candidate;
|
||||
// Check both uv and uv.exe
|
||||
string candidateUv = Path.Combine(part, "uv");
|
||||
string candidateUvExe = Path.Combine(part, "uv.exe");
|
||||
if (File.Exists(candidateUv) && ValidateUvBinary(candidateUv)) return candidateUv;
|
||||
if (File.Exists(candidateUvExe) && ValidateUvBinary(candidateUvExe)) return candidateUvExe;
|
||||
}
|
||||
catch { }
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1990,7 +1990,60 @@ namespace UnityMcpBridge.Editor.Windows
|
|||
{
|
||||
try
|
||||
{
|
||||
// Common absolute paths
|
||||
// Windows-specific Python detection
|
||||
if (Application.platform == RuntimePlatform.WindowsEditor)
|
||||
{
|
||||
// Common Windows Python installation paths
|
||||
string[] windowsCandidates =
|
||||
{
|
||||
@"C:\Python313\python.exe",
|
||||
@"C:\Python312\python.exe",
|
||||
@"C:\Python311\python.exe",
|
||||
@"C:\Python310\python.exe",
|
||||
@"C:\Python39\python.exe",
|
||||
Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData), @"Programs\Python\Python313\python.exe"),
|
||||
Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData), @"Programs\Python\Python312\python.exe"),
|
||||
Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData), @"Programs\Python\Python311\python.exe"),
|
||||
Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData), @"Programs\Python\Python310\python.exe"),
|
||||
Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData), @"Programs\Python\Python39\python.exe"),
|
||||
Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.ProgramFiles), @"Python313\python.exe"),
|
||||
Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.ProgramFiles), @"Python312\python.exe"),
|
||||
Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.ProgramFiles), @"Python311\python.exe"),
|
||||
Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.ProgramFiles), @"Python310\python.exe"),
|
||||
Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.ProgramFiles), @"Python39\python.exe"),
|
||||
};
|
||||
|
||||
foreach (string c in windowsCandidates)
|
||||
{
|
||||
if (File.Exists(c)) return true;
|
||||
}
|
||||
|
||||
// Try 'where python' command (Windows equivalent of 'which')
|
||||
var psi = new ProcessStartInfo
|
||||
{
|
||||
FileName = "where",
|
||||
Arguments = "python",
|
||||
UseShellExecute = false,
|
||||
RedirectStandardOutput = true,
|
||||
RedirectStandardError = true,
|
||||
CreateNoWindow = true
|
||||
};
|
||||
using var p = Process.Start(psi);
|
||||
string outp = p.StandardOutput.ReadToEnd().Trim();
|
||||
p.WaitForExit(2000);
|
||||
if (p.ExitCode == 0 && !string.IsNullOrEmpty(outp))
|
||||
{
|
||||
string[] lines = outp.Split('\n');
|
||||
foreach (string line in lines)
|
||||
{
|
||||
string trimmed = line.Trim();
|
||||
if (File.Exists(trimmed)) return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// macOS/Linux detection (existing code)
|
||||
string home = Environment.GetFolderPath(Environment.SpecialFolder.UserProfile) ?? string.Empty;
|
||||
string[] candidates =
|
||||
{
|
||||
|
|
@ -2022,6 +2075,7 @@ namespace UnityMcpBridge.Editor.Windows
|
|||
p.WaitForExit(2000);
|
||||
if (p.ExitCode == 0 && !string.IsNullOrEmpty(outp) && File.Exists(outp)) return true;
|
||||
}
|
||||
}
|
||||
catch { }
|
||||
return false;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,4 +1,5 @@
|
|||
{
|
||||
<<<<<<< HEAD
|
||||
"name": "com.justinpbarnett.unity-mcp",
|
||||
"version": "2.0.0",
|
||||
"displayName": "Unity MCP Bridge",
|
||||
|
|
@ -6,5 +7,30 @@
|
|||
"unity": "2020.3",
|
||||
"dependencies": {
|
||||
"com.unity.nuget.newtonsoft-json": "3.0.2"
|
||||
=======
|
||||
"name": "com.coplaydev.unity-mcp",
|
||||
"version": "1.0.0",
|
||||
"displayName": "Unity MCP Bridge",
|
||||
"description": "A bridge that manages and communicates with the sister application, Unity MCP Server, which allows for communications with MCP Clients like Claude Desktop or Cursor.",
|
||||
"unity": "2020.3",
|
||||
"documentationUrl": "https://github.com/CoplayDev/unity-mcp",
|
||||
"licensesUrl": "https://github.com/CoplayDev/unity-mcp/blob/main/LICENSE",
|
||||
"dependencies": {
|
||||
"com.unity.nuget.newtonsoft-json": "3.0.2"
|
||||
},
|
||||
"keywords": [
|
||||
"unity",
|
||||
"ai",
|
||||
"llm",
|
||||
"mcp",
|
||||
"model-context-protocol",
|
||||
"mcp-server",
|
||||
"mcp-client"
|
||||
],
|
||||
"author": {
|
||||
"name": "CoplayDev",
|
||||
"email": "support@coplay.dev",
|
||||
"url": "https://coplay.dev"
|
||||
>>>>>>> upstream/main
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -0,0 +1 @@
|
|||
3.12
|
||||
|
|
@ -19,7 +19,7 @@ echo.
|
|||
|
||||
:: Package cache location
|
||||
echo Unity Package Cache Location:
|
||||
echo Example: X:\UnityProject\Library\PackageCache\com.justinpbarnett.unity-mcp@1.0.0
|
||||
echo Example: X:\UnityProject\Library\PackageCache\com.coplaydev.unity-mcp@1.0.0
|
||||
set /p "PACKAGE_CACHE_PATH=Enter Unity package cache path: "
|
||||
|
||||
if "%PACKAGE_CACHE_PATH%"=="" (
|
||||
|
|
|
|||
|
|
@ -16,7 +16,7 @@ echo.
|
|||
|
||||
:: Package cache location
|
||||
echo Unity Package Cache Location:
|
||||
echo Example: X:\UnityProject\Library\PackageCache\com.justinpbarnett.unity-mcp@1.0.0
|
||||
echo Example: X:\UnityProject\Library\PackageCache\com.coplaydev.unity-mcp@1.0.0
|
||||
set /p "PACKAGE_CACHE_PATH=Enter Unity package cache path: "
|
||||
|
||||
if "%PACKAGE_CACHE_PATH%"=="" (
|
||||
|
|
|
|||
Loading…
Reference in New Issue