diff --git a/src/Artemis.Core/Events/PluginEventArgs.cs b/src/Artemis.Core/Events/PluginEventArgs.cs index 5d3311f93..cc874c699 100644 --- a/src/Artemis.Core/Events/PluginEventArgs.cs +++ b/src/Artemis.Core/Events/PluginEventArgs.cs @@ -1,5 +1,5 @@ using System; -using Artemis.Plugins.Interfaces; +using Artemis.Plugins.Models; namespace Artemis.Core.Events { @@ -9,11 +9,11 @@ namespace Artemis.Core.Events { } - public PluginEventArgs(IPlugin plugin) + public PluginEventArgs(PluginInfo pluginInfo) { - Plugin = plugin; + PluginInfo = pluginInfo; } - public IPlugin Plugin { get; } + public PluginInfo PluginInfo { get; } } } \ No newline at end of file diff --git a/src/Artemis.Core/Services/PluginService.cs b/src/Artemis.Core/Services/PluginService.cs index 50ff1e9e6..d4e21e79b 100644 --- a/src/Artemis.Core/Services/PluginService.cs +++ b/src/Artemis.Core/Services/PluginService.cs @@ -39,7 +39,7 @@ namespace Artemis.Core.Services // Empty the list of plugins foreach (var pluginInfo in _plugins) - pluginInfo.Dispose(); + pluginInfo.UnloadPlugin(); _plugins.Clear(); // Iterate all plugin folders and load each plugin @@ -52,17 +52,24 @@ namespace Artemis.Core.Services /// public async Task ReloadPlugin(PluginInfo pluginInfo) { - throw new NotImplementedException(); + pluginInfo.UnloadPlugin(); + await pluginInfo.CompilePlugin(_kernel); + + OnPluginReloaded(new PluginEventArgs(pluginInfo)); } /// public async Task GetModuleViewModel(PluginInfo pluginInfo) { - return pluginInfo.GetModuleViewModel(_kernel); + return await Task.Run(() => pluginInfo.GetModuleViewModel(_kernel)); } public void Dispose() { + // Empty the list of plugins + foreach (var pluginInfo in _plugins) + pluginInfo.UnloadPlugin(); + _plugins.Clear(); } #region Events diff --git a/src/Artemis.Plugins/Models/PluginInfo.cs b/src/Artemis.Plugins/Models/PluginInfo.cs index 000ac8263..e59d67600 100644 --- a/src/Artemis.Plugins/Models/PluginInfo.cs +++ b/src/Artemis.Plugins/Models/PluginInfo.cs @@ -1,5 +1,4 @@ -using System; -using System.IO; +using System.IO; using System.Linq; using System.Reflection; using System.Threading.Tasks; @@ -11,7 +10,7 @@ using Ninject; namespace Artemis.Plugins.Models { - public class PluginInfo : IDisposable + public class PluginInfo { private static Assembly _assembly; @@ -42,9 +41,13 @@ namespace Artemis.Plugins.Models [JsonIgnore] public string Folder { get; set; } - public void Dispose() + /// + /// Unloads the plugin and clears the plugin info's internal data + /// + public void UnloadPlugin() { Plugin.UnloadPlugin(); + _assembly = null; } /// @@ -67,19 +70,28 @@ namespace Artemis.Plugins.Models var pluginInfo = JsonConvert.DeserializeObject(File.ReadAllText(folder + "plugin.json")); pluginInfo.Folder = folder; + await pluginInfo.CompilePlugin(kernel); + return pluginInfo; + } + + /// + /// Compiles the plugin's main CS file and any of it's includes and instantiates it. + /// + /// The Ninject kernel to use for DI + public async Task CompilePlugin(IKernel kernel) + { // Load the main script and get the type - _assembly = await CSScript.Evaluator.CompileCodeAsync(File.ReadAllText(folder + pluginInfo.Main)); + _assembly = await CSScript.Evaluator.CompileCodeAsync(File.ReadAllText(Folder + Main)); + var pluginType = _assembly.GetTypes().Where(t => typeof(IPlugin).IsAssignableFrom(t)).ToList(); if (!pluginType.Any()) - throw new ArtemisPluginException(pluginInfo, "Failed to load plugin, no type found that implements IPlugin"); + throw new ArtemisPluginException(this, "Failed to load plugin, no type found that implements IPlugin"); if (pluginType.Count > 1) - throw new ArtemisPluginException(pluginInfo, "Failed to load plugin, more than one type found that implements IPlugin"); + throw new ArtemisPluginException(this, "Failed to load plugin, more than one type found that implements IPlugin"); // Instantiate the plugin with Ninject - pluginInfo.Plugin = (IPlugin) kernel.Get(pluginType.First()); - pluginInfo.Plugin.LoadPlugin(); - - return pluginInfo; + Plugin = (IPlugin) kernel.Get(pluginType.First()); + Plugin.LoadPlugin(); } ///