diff --git a/TestProjects/UnityMCPTests/Assets/Tests/EditMode/Tools/CommandRegistryTests.cs b/TestProjects/UnityMCPTests/Assets/Tests/EditMode/Tools/CommandRegistryTests.cs index c12d1fd19..2bbe4616f 100644 --- a/TestProjects/UnityMCPTests/Assets/Tests/EditMode/Tools/CommandRegistryTests.cs +++ b/TestProjects/UnityMCPTests/Assets/Tests/EditMode/Tools/CommandRegistryTests.cs @@ -8,18 +8,29 @@ namespace MCPForUnityTests.Editor.Tools public class CommandRegistryTests { [Test] - public void GetHandler_ReturnsNull_ForUnknownCommand() + public void GetHandler_ThrowException_ForUnknownCommand() { var unknown = "HandleDoesNotExist"; - var handler = CommandRegistry.GetHandler(unknown); - Assert.IsNull(handler, "Expected null handler for unknown command name."); + try + { + var handler = CommandRegistry.GetHandler(unknown); + Assert.Fail("Should throw InvalidOperation for unknown handler."); + } + catch (InvalidOperationException) + { + + } + catch + { + Assert.Fail("Should throw InvalidOperation for unknown handler."); + } } [Test] public void GetHandler_ReturnsManageGameObjectHandler() { - var handler = CommandRegistry.GetHandler("HandleManageGameObject"); - Assert.IsNotNull(handler, "Expected a handler for HandleManageGameObject."); + var handler = CommandRegistry.GetHandler("manage_gameobject"); + Assert.IsNotNull(handler, "Expected a handler for manage_gameobject."); var methodInfo = handler.Method; Assert.AreEqual("HandleCommand", methodInfo.Name, "Handler method name should be HandleCommand."); diff --git a/UnityMcpBridge/Editor/MCPForUnityBridge.cs b/UnityMcpBridge/Editor/MCPForUnityBridge.cs index 88b30deb7..8ad1f8faf 100644 --- a/UnityMcpBridge/Editor/MCPForUnityBridge.cs +++ b/UnityMcpBridge/Editor/MCPForUnityBridge.cs @@ -63,7 +63,7 @@ private static bool IsDebugEnabled() { try { return EditorPrefs.GetBool("MCPForUnity.DebugLogs", false); } catch { return false; } } - + private static void LogBreadcrumb(string stage) { if (IsDebugEnabled()) @@ -82,7 +82,7 @@ private static void LogBreadcrumb(string stage) public static void StartAutoConnect() { Stop(); // Stop current connection - + try { // Prefer stored project port and start using the robust Start() path (with retries/options) @@ -314,7 +314,7 @@ public static void Start() const int maxImmediateRetries = 3; const int retrySleepMs = 75; int attempt = 0; - for (;;) + for (; ; ) { try { @@ -755,7 +755,7 @@ private static async System.Threading.Tasks.Task ReadFrameAsUtf8Async(Ne { byte[] header = await ReadExactAsync(stream, 8, timeoutMs, cancel).ConfigureAwait(false); ulong payloadLen = ReadUInt64BigEndian(header); - if (payloadLen > MaxFrameBytes) + if (payloadLen > MaxFrameBytes) { throw new System.IO.IOException($"Invalid framed length: {payloadLen}"); } @@ -1040,25 +1040,7 @@ private static string ExecuteCommand(Command command) // Use JObject for parameters as the new handlers likely expect this JObject paramsObject = command.@params ?? new JObject(); - // Route command based on the new tool structure from the refactor plan - object result = command.type switch - { - // Maps the command type (tool name) to the corresponding handler's static HandleCommand method - // Assumes each handler class has a static method named 'HandleCommand' that takes JObject parameters - "manage_script" => ManageScript.HandleCommand(paramsObject), - // Run scene operations on the main thread to avoid deadlocks/hangs (with diagnostics under debug flag) - "manage_scene" => HandleManageScene(paramsObject) - ?? throw new TimeoutException($"manage_scene timed out after {FrameIOTimeoutMs} ms on main thread"), - "manage_editor" => ManageEditor.HandleCommand(paramsObject), - "manage_gameobject" => ManageGameObject.HandleCommand(paramsObject), - "manage_asset" => ManageAsset.HandleCommand(paramsObject), - "manage_shader" => ManageShader.HandleCommand(paramsObject), - "read_console" => ReadConsole.HandleCommand(paramsObject), - "manage_menu_item" => ManageMenuItem.HandleCommand(paramsObject), - _ => throw new ArgumentException( - $"Unknown or unsupported command type: {command.type}" - ), - }; + object result = CommandRegistry.GetHandler(command.type)(paramsObject); // Standard success response format var response = new { status = "success", result }; diff --git a/UnityMcpBridge/Editor/Tools/CommandRegistry.cs b/UnityMcpBridge/Editor/Tools/CommandRegistry.cs index 912ddf595..c53642c02 100644 --- a/UnityMcpBridge/Editor/Tools/CommandRegistry.cs +++ b/UnityMcpBridge/Editor/Tools/CommandRegistry.cs @@ -14,14 +14,14 @@ public static class CommandRegistry // to the corresponding static HandleCommand method in the appropriate tool class. private static readonly Dictionary> _handlers = new() { - { "HandleManageScript", ManageScript.HandleCommand }, - { "HandleManageScene", ManageScene.HandleCommand }, - { "HandleManageEditor", ManageEditor.HandleCommand }, - { "HandleManageGameObject", ManageGameObject.HandleCommand }, - { "HandleManageAsset", ManageAsset.HandleCommand }, - { "HandleReadConsole", ReadConsole.HandleCommand }, - { "HandleManageMenuItem", ManageMenuItem.HandleCommand }, - { "HandleManageShader", ManageShader.HandleCommand}, + { "manage_script", ManageScript.HandleCommand }, + { "manage_scene", ManageScene.HandleCommand }, + { "manage_editor", ManageEditor.HandleCommand }, + { "manage_gameobject", ManageGameObject.HandleCommand }, + { "manage_asset", ManageAsset.HandleCommand }, + { "read_console", ReadConsole.HandleCommand }, + { "manage_menu_item", ManageMenuItem.HandleCommand }, + { "manage_shader", ManageShader.HandleCommand}, }; /// @@ -31,17 +31,18 @@ public static class CommandRegistry /// The command handler function if found, null otherwise. public static Func GetHandler(string commandName) { - // Use case-insensitive comparison for flexibility, although Python side should be consistent - return _handlers.TryGetValue(commandName, out var handler) ? handler : null; - // Consider adding logging here if a handler is not found - /* - if (_handlers.TryGetValue(commandName, out var handler)) { - return handler; - } else { - UnityEngine.Debug.LogError($\"[CommandRegistry] No handler found for command: {commandName}\"); - return null; + if (!_handlers.TryGetValue(commandName, out var handler)) + { + throw new InvalidOperationException( + $"Unknown or unsupported command type: {commandName}"); } - */ + + return handler; + } + + public static void Add(string commandName, Func handler) + { + _handlers.Add(commandName, handler); } } }