using System.IO; using UnityEditor; using UnityEngine; using System.Diagnostics; namespace LLM.Editor { public static class DataExtractorMenu { private const string HighLevelScript = "Assets/LLM/source/orchestrators/extract_high_level.py"; private const string MidLevelScript = "Assets/LLM/source/orchestrators/extract_mid_level.py"; private const string LowLevelScript = "Assets/LLM/source/orchestrators/extract_low_level.py"; private const string CreateConfigScript = "Assets/LLM/source/orchestrators/create_config.py"; [MenuItem("Tools/DataExtractor/High Level Export")] private static void ExportHighLevel() { RunExtractor("High Level", HighLevelScript, true); } [MenuItem("Tools/DataExtractor/Mid Level Export")] private static void ExportMidLevel() { RunExtractor("Mid Level", MidLevelScript, true); } [MenuItem("Tools/DataExtractor/Low Level Export")] private static void ExportLowLevel() { RunExtractor("Low Level", LowLevelScript, true); } [MenuItem("Tools/DataExtractor/Create or Update Config File")] private static void CreateOrUpdateConfigFile() { RunExtractor("Create Config", CreateConfigScript, false); } private static void RunExtractor(string level, string scriptPath, bool requireOutputPath) { string outputPath = ""; if (requireOutputPath) { outputPath = EditorUtility.OpenFolderPanel($"Select Output Folder for {level} Export", "", ""); if (string.IsNullOrEmpty(outputPath)) { UnityEngine.Debug.Log($"{level} export cancelled by user."); return; } } var projectRoot = Path.GetFullPath(Path.Combine(Application.dataPath, "..")); var pythonExecutable = Application.platform == RuntimePlatform.WindowsEditor ? Path.Combine(projectRoot, "venv", "Scripts", "python.exe") : Path.Combine(projectRoot, "venv", "bin", "python"); var fullScriptPath = Path.Combine(projectRoot, scriptPath); if (!File.Exists(pythonExecutable)) { UnityEngine.Debug.LogError($"Python executable not found at: {pythonExecutable}"); EditorUtility.DisplayDialog("Export Error", "The Python virtual environment executable was not found. Please ensure the 'venv' directory is set up correctly.", "OK"); return; } if (!File.Exists(fullScriptPath)) { UnityEngine.Debug.LogError($"Extractor script not found at: {fullScriptPath}"); EditorUtility.DisplayDialog("Export Error", $"The Python script for the {level} task was not found.", "OK"); return; } var arguments = requireOutputPath ? $"\"{fullScriptPath}\" --input \"{projectRoot}\" --output \"{outputPath}\"" : $"{fullScriptPath}"; UnityEngine.Debug.Log($"Running command: \"{pythonExecutable}\" {arguments}"); var process = new Process { StartInfo = new ProcessStartInfo { FileName = pythonExecutable, Arguments = arguments, RedirectStandardOutput = true, RedirectStandardError = true, UseShellExecute = false, CreateNoWindow = true, WorkingDirectory = projectRoot } }; EditorUtility.DisplayProgressBar("Data Extractor", $"Running {level} task...", 0.5f); process.OutputDataReceived += (_, e) => { if (e.Data != null) UnityEngine.Debug.Log($"[Extractor] {e.Data}"); }; process.ErrorDataReceived += (_, e) => { if (e.Data != null) UnityEngine.Debug.LogError($"[Extractor ERROR] {e.Data}"); }; process.Start(); process.BeginOutputReadLine(); process.BeginErrorReadLine(); process.WaitForExit(); EditorUtility.ClearProgressBar(); if (process.ExitCode == 0) { EditorUtility.DisplayDialog("Task Complete", $"{level} task finished successfully.", "OK"); } else { EditorUtility.DisplayDialog("Task Failed", $"The {level} task failed. Check the Unity Console for error messages.", "OK"); } } } }