105 lines
3.8 KiB
C#
105 lines
3.8 KiB
C#
using System;
|
|
using UnityEditor;
|
|
using MCPForUnity.Editor.Constants;
|
|
using MCPForUnity.Editor.Helpers;
|
|
using MCPForUnity.Editor.Services.Transport;
|
|
using MCPForUnity.Editor.Services.Transport.Transports;
|
|
|
|
namespace MCPForUnity.Editor.Services
|
|
{
|
|
/// <summary>
|
|
/// Ensures the legacy stdio bridge resumes after domain reloads, mirroring the HTTP handler.
|
|
/// </summary>
|
|
[InitializeOnLoad]
|
|
internal static class StdioBridgeReloadHandler
|
|
{
|
|
static StdioBridgeReloadHandler()
|
|
{
|
|
AssemblyReloadEvents.beforeAssemblyReload += OnBeforeAssemblyReload;
|
|
AssemblyReloadEvents.afterAssemblyReload += OnAfterAssemblyReload;
|
|
}
|
|
|
|
private static void OnBeforeAssemblyReload()
|
|
{
|
|
try
|
|
{
|
|
// Only persist resume intent when stdio is the active transport and the bridge is running.
|
|
bool useHttp = EditorPrefs.GetBool(EditorPrefKeys.UseHttpTransport, true);
|
|
bool isRunning = MCPServiceLocator.TransportManager.IsRunning(TransportMode.Stdio);
|
|
bool shouldResume = !useHttp && isRunning;
|
|
|
|
if (shouldResume)
|
|
{
|
|
EditorPrefs.SetBool(EditorPrefKeys.ResumeStdioAfterReload, true);
|
|
|
|
// Stop only the stdio bridge; leave HTTP untouched if it is running concurrently.
|
|
var stopTask = MCPServiceLocator.TransportManager.StopAsync(TransportMode.Stdio);
|
|
stopTask.ContinueWith(t =>
|
|
{
|
|
if (t.IsFaulted && t.Exception != null)
|
|
{
|
|
McpLog.Warn($"Error stopping stdio bridge before reload: {t.Exception.GetBaseException()?.Message}");
|
|
}
|
|
}, System.Threading.Tasks.TaskScheduler.Default);
|
|
}
|
|
else
|
|
{
|
|
EditorPrefs.DeleteKey(EditorPrefKeys.ResumeStdioAfterReload);
|
|
}
|
|
}
|
|
catch (Exception ex)
|
|
{
|
|
McpLog.Warn($"Failed to persist stdio reload flag: {ex.Message}");
|
|
}
|
|
}
|
|
|
|
private static void OnAfterAssemblyReload()
|
|
{
|
|
bool resume = false;
|
|
try
|
|
{
|
|
resume = EditorPrefs.GetBool(EditorPrefKeys.ResumeStdioAfterReload, false);
|
|
bool useHttp = EditorPrefs.GetBool(EditorPrefKeys.UseHttpTransport, true);
|
|
resume = resume && !useHttp;
|
|
if (resume)
|
|
{
|
|
EditorPrefs.DeleteKey(EditorPrefKeys.ResumeStdioAfterReload);
|
|
}
|
|
}
|
|
catch (Exception ex)
|
|
{
|
|
McpLog.Warn($"Failed to read stdio reload flag: {ex.Message}");
|
|
}
|
|
|
|
if (!resume)
|
|
{
|
|
return;
|
|
}
|
|
|
|
// Restart via TransportManager so state stays in sync; if it fails (port busy), rely on UI to retry.
|
|
TryStartBridgeImmediate();
|
|
}
|
|
|
|
private static void TryStartBridgeImmediate()
|
|
{
|
|
var startTask = MCPServiceLocator.TransportManager.StartAsync(TransportMode.Stdio);
|
|
startTask.ContinueWith(t =>
|
|
{
|
|
if (t.IsFaulted)
|
|
{
|
|
var baseEx = t.Exception?.GetBaseException();
|
|
McpLog.Warn($"Failed to resume stdio bridge after reload: {baseEx?.Message}");
|
|
return;
|
|
}
|
|
if (!t.Result)
|
|
{
|
|
McpLog.Warn("Failed to resume stdio bridge after domain reload");
|
|
return;
|
|
}
|
|
|
|
MCPForUnity.Editor.Windows.MCPForUnityEditorWindow.RequestHealthVerification();
|
|
}, System.Threading.Tasks.TaskScheduler.Default);
|
|
}
|
|
}
|
|
}
|