29 using System.Collections.Generic;
31 using System.Reflection;
35 namespace OpenSim.Framework
53 string Message {
get; }
54 bool Apply(
string extpoint);
69 public class PluginLoader <T> : IDisposable where T :
IPlugin
71 private const int max_loadable_plugins = 10000;
73 private List<T> loaded =
new List<T>();
74 private List<string> extpoints =
new List<string>();
77 private Dictionary<string,IPluginConstraint> constraints
78 =
new Dictionary<string,IPluginConstraint>();
80 private Dictionary<string,IPluginFilter> filters
81 =
new Dictionary<string,IPluginFilter>();
83 private static readonly ILog log
84 = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
88 set { initialiser = value; }
89 get {
return initialiser; }
92 public List<T> Plugins
94 get {
return loaded; }
99 get {
return (loaded.Count == 1)? loaded [0] :
default (T); }
105 initialise_plugin_dir_(
".");
111 initialise_plugin_dir_(
".");
117 initialise_plugin_dir_(dir);
120 public void Add(
string extpoint)
122 if (extpoints.Contains(extpoint))
125 extpoints.Add(extpoint);
131 AddConstraint(extpoint, cons);
137 AddFilter(extpoint, filter);
142 constraints.Add(extpoint, cons);
147 filters.Add(extpoint, filter);
150 public void Load(
string extpoint)
158 foreach (
string ext
in extpoints)
160 log.Info(
"[PLUGINS]: Loading extension point " + ext);
162 if (constraints.ContainsKey(ext))
166 log.Error(
"[PLUGINS]: " + ext +
" failed constraint: " + cons.
Message);
171 if (filters.ContainsKey(ext))
172 filter = filters[ext];
174 List<T> loadedPlugins =
new List<T>();
177 log.Info(
"[PLUGINS]: Trying plugin " + node.Path);
179 if ((filter != null) && (filter.Apply(node) ==
false))
183 loadedPlugins.Add(plugin);
189 foreach (T plugin
in loadedPlugins)
191 Initialiser.Initialise(plugin);
204 AddinManager.AddinLoadError -= on_addinloaderror_;
205 AddinManager.AddinLoaded -= on_addinloaded_;
208 private void initialise_plugin_dir_(
string dir)
210 if (AddinManager.IsInitialized ==
true)
213 log.Info(
"[PLUGINS]: Initializing addin manager");
215 AddinManager.AddinLoadError += on_addinloaderror_;
216 AddinManager.AddinLoaded += on_addinloaded_;
221 AddinManager.Initialize(dir);
222 AddinManager.Registry.Update(null);
226 private void on_addinloaded_(
object sender, AddinEventArgs args)
228 log.Info (
"[PLUGINS]: Plugin Loaded: " + args.AddinId);
231 private void on_addinloaderror_(
object sender, AddinErrorEventArgs args)
233 if (args.Exception == null)
234 log.Error (
"[PLUGINS]: Plugin Error: "
237 log.Error (
"[PLUGINS]: Plugin Error: "
238 + args.Exception.Message +
"\n"
239 + args.Exception.StackTrace);
242 private void clear_registry_(
string dir)
248 string customDir = Environment.GetEnvironmentVariable (
"MONO_ADDINS_REGISTRY");
249 string v0 =
"addin-db-000";
250 string v1 =
"addin-db-001";
251 if (customDir != null && customDir !=
String.Empty)
253 v0 = Path.Combine(customDir, v0);
254 v1 = Path.Combine(customDir, v1);
258 if (Directory.Exists(v0))
259 Directory.Delete(v0,
true);
261 if (Directory.Exists(v1))
262 Directory.Delete(v1,
true);
277 private static TextWriter prev_console_;
282 prev_console_ = System.Console.Out;
283 System.Console.SetOut(
new StreamWriter(Stream.Null));
287 if (prev_console_ != null)
288 System.Console.SetOut(prev_console_);
299 string provider =
"";
306 public string ID {
get {
return id; } }
307 public string Provider {
get {
return provider; } }
308 public string TypeName {
get {
return type; } }
310 public Type TypeObject
317 if (type.Length == 0)
318 throw new InvalidOperationException(
"Type name not specified.");
320 return typeobj = Addin.GetType(type,
true);
326 return Activator.CreateInstance(TypeObject);
350 public string Message
354 return "The number of plugins is constrained to the interval ["
355 + min +
", " + max +
"]";
361 int count = AddinManager.GetExtensionNodes(extpoint).Count;
363 if ((count < min) || (count > max))
376 private string[] m_filters;
386 m_filters = p.Split(
',');
388 for (
int i = 0; i < m_filters.Length; i++)
390 m_filters[i] = m_filters[i].Trim();
401 for (
int i = 0; i < m_filters.Length; i++)
403 if (m_filters[i] == plugin.
Provider)
418 private string[] m_filters;
428 m_filters = p.Split(
',');
430 for (
int i = 0; i < m_filters.Length; i++)
432 m_filters[i] = m_filters[i].Trim();
443 for (
int i = 0; i < m_filters.Length; i++)
445 if (m_filters[i] == plugin.
ID)
Any plugins which need to pass parameters to their initialisers must inherit this class and use it to...
PluginLoader(PluginInitialiserBase init)
void Add(string extpoint, IPluginFilter filter)
Classes wishing to impose constraints on plugin loading must implement this class and pass it to Plug...
void Add(string extpoint, IPluginConstraint cons)
PluginCountConstraint(int exact)
void suppress_console_output_(bool save)
PluginConstraintViolatedException(string msg)
PluginProviderFilter(string p)
Constructor.
Exception thrown if an incorrect number of plugins are loaded
bool Apply(string extpoint)
This interface, describes a generic plugin
bool Apply(string extpoint)
void AddFilter(string extpoint, IPluginFilter filter)
bool Apply(PluginExtensionNode plugin)
Apply this filter to the given plugin.
PluginConstraintViolatedException(string msg, Exception e)
Filters out which plugin to load based on the plugin name or names given. Plugin names are contained ...
Classes wishing to select specific plugins from a range of possible options must implement this class...
PluginLoader(PluginInitialiserBase init, string dir)
void Add(string extpoint)
PluginIdFilter(string p)
Constructor.
bool Apply(PluginExtensionNode plugin)
Apply this filter to plugin .
PluginCountConstraint(int minimum, int maximum)
void Load(string extpoint)
Filters plugins according to their ID. Plugin IDs are contained in their addin.xml ...
PluginConstraintViolatedException()
void Dispose()
Unregisters Mono.Addins event handlers, allowing temporary Mono.Addins data to be garbage collected...
Constraint that bounds the number of plugins to be loaded.
void AddConstraint(string extpoint, IPluginConstraint cons)