DynamoVisualProgramming.DynamoServices by Autodesk

<PackageReference Include="DynamoVisualProgramming.DynamoServices" Version="2.14.0-beta4253" />

 PythonEngineManager

public sealed class PythonEngineManager
Singleton class that other class can access and use for query loaded Python Engine info.
using System; using System.Collections.Generic; using System.Collections.ObjectModel; using System.Linq; using System.Reflection; namespace Dynamo.PythonServices { public sealed class PythonEngineManager { internal static readonly Lazy<PythonEngineManager> lazy = new Lazy<PythonEngineManager>(() => new PythonEngineManager()); public ObservableCollection<PythonEngine> AvailableEngines; internal static readonly string CPython3EngineName = "CPython3"; internal static readonly string IronPython2EngineName = "IronPython2"; internal static string PythonEvaluatorSingletonInstance = "Instance"; internal static string IronPythonEvaluatorClass = "IronPythonEvaluator"; internal static string IronPythonEvaluationMethod = "EvaluateIronPythonScript"; internal static string CPythonEvaluatorClass = "CPythonEvaluator"; internal static string CPythonEvaluationMethod = "EvaluatePythonScript"; internal static string IronPythonAssemblyName = "DSIronPython"; internal static string CPythonAssemblyName = "DSCPython"; internal static string IronPythonTypeName = IronPythonAssemblyName + "." + IronPythonEvaluatorClass; internal static string CPythonTypeName = CPythonAssemblyName + "." + CPythonEvaluatorClass; internal static string PythonInputMarshalerProperty = "InputMarshaler"; internal static string PythonOutputMarshalerProperty = "OutputMarshaler"; internal static string DummyEvaluatorClass = "DummyPythonEvaluator"; internal static string DummyEvaluatorMethod = "Evaluate"; public static PythonEngineManager Instance => lazy.Value; private PythonEngineManager() { AvailableEngines = new ObservableCollection<PythonEngine>(); LoadPythonEngine(AppDomain.CurrentDomain.GetAssemblies().FirstOrDefault(delegate(Assembly a) { if (a != (Assembly)null) return a.GetName().Name == CPythonAssemblyName; return false; })); AppDomain.CurrentDomain.AssemblyLoad += delegate(object sender, AssemblyLoadEventArgs args) { if (args.LoadedAssembly != (Assembly)null && args.LoadedAssembly.GetName().Name == CPythonAssemblyName) Instance.LoadPythonEngine(args.LoadedAssembly); }; } private PythonEngine GetEngine(string version) { return AvailableEngines.FirstOrDefault((PythonEngine x) => x.Name == version); } internal void LoadPythonEngine(IEnumerable<Assembly> assemblies) { foreach (Assembly assembly in assemblies) { LoadPythonEngine(assembly); } } private void LoadPythonEngine(Assembly assembly) { if (!(assembly == (Assembly)null)) try { PythonEngine pythonEngine = (PythonEngine)(assembly.GetTypes().FirstOrDefault(delegate(Type x) { if (typeof(PythonEngine).IsAssignableFrom(x) && !x.IsInterface) return !x.IsAbstract; return false; })?.GetProperty(PythonEvaluatorSingletonInstance, BindingFlags.Static | BindingFlags.NonPublic)?.GetValue(null)); if (pythonEngine != null && GetEngine(pythonEngine.Name) == null) AvailableEngines.Add(pythonEngine); } catch { } } } }