|
/*
* Creato da SharpDevelop.
* Utente: lucabonotto
* Data: 01/03/2008
* Ora: 14.52
*
* To change this template use Tools | Options | Coding | Edit Standard Headers.
*/
using System;
using System.Collections;
using System.IO;
using System.Runtime.Remoting;
using System.Windows.Forms;
using System.Xml;
namespace LBSoft.PluginManager
{
#region Enums
/// <summary>
/// Message type enumerator
/// </summary>
public enum MessageType
{
Normal = 0,
Error,
Warning,
}
#endregion
#region Interfaces
/// <summary>
/// Interface for the plugin provider
/// </summary>
public interface ILBPluginsManager
{
/// <summary>
/// Method to view the processing message
/// </summary>
/// <param name="message">Message body</param>
/// <param name="addEndLine">Flag to add a newline character</param>
void OutputMessage ( string message, bool addEndLine );
/// <summary>
/// Method to view the processing message
/// </summary>
/// <param name="message">Message body</param>
/// <param name="addEndLine">Flag to add a newline character</param>
/// <param name="type">Type of the message</param>
void OutputMessage ( string message, bool addEndLine, MessageType type );
}
/// <summary>
/// Base plugin interface
/// </summary>
public interface ILBPlugin
{
/// <summary>
/// Method to initialize the plugin
/// </summary>
/// <param name="piPath">Plugin path</param>
/// <returns></returns>
bool Initialize ();
/// <summary>
/// Method to release the plugin object
/// </summary>
/// <returns></returns>
bool Release ();
}
#endregion
#region Classes
/// <summary>
/// Class for the plugin definitions. This class is the object with
/// the definition readed from the 'Plugins.xml' definitions file
/// </summary>
public class Plugin
{
#region Field
// Plugin name
private string pluginName = System.String.Empty;
// Relative path from the application path
private string pluginPath = System.String.Empty;
// Assembly of the plugin
private string pluginAssembly = System.String.Empty;
// Plugin version
private string pluginVersion = System.String.Empty;
// Name of the plugin object
private string pluginObject = System.String.Empty;
#endregion
#region Ctors
/// <summary>
/// Ctor of the class
/// </summary>
public Plugin()
{
}
#endregion
#region Properties
/// <summary>
/// Description name of the plugin object
/// </summary>
public string Name
{
get { return this.pluginName; }
set { this.pluginName = value; }
}
/// <summary>
/// Path of the plugin assembly
/// </summary>
public string Path
{
get { return this.pluginPath; }
set { this.pluginPath = value; }
}
/// <summary>
/// Assembly name of the plugin object
/// </summary>
public string Assembly
{
get { return this.pluginAssembly; }
set { this.pluginAssembly = value; }
}
/// <summary>
/// Version of the plugin object
/// </summary>
public string Version
{
get { return this.pluginVersion; }
set { this.pluginVersion = value; }
}
/// <summary>
/// Name of the plugin object in the assembly with the namespace
/// </summary>
public string Object
{
get { return this.pluginObject; }
set { this.pluginObject = value; }
}
#endregion
}
/// <summary>
/// Class for the menagement of the plugins object and definitions
/// </summary>
public class PluginsManager
{
#region Fields
private string definitionsFile = "Plugins.xml";
// List of the plugins definitions
private ArrayList plugins;
// List of the loaded plugins objects
private ArrayList pluginObjs;
// Path of the plugins
private String pluginsPath;
// Last error message
private String lastMessageErr;
// Interface for the plugin manager
private ILBPluginsManager provider = null;
// Flag to show the messages
private bool showMessages = true;
#endregion
#region Ctors
/// <summary>
/// Ctor of the class
/// </summary>
public PluginsManager()
: this ( string.Empty)
{
}
/// <summary>
/// Ctor of the class
/// </summary>
/// <param name="path">Path of the plugins assemblies</param>
public PluginsManager( string path )
{
this.plugins = new ArrayList();
this.pluginObjs = new ArrayList();
this.PluginsPath = path;
}
#endregion
#region Properties
/// <summary>
/// Definitions file path
/// </summary>
public string DefinitionsFile
{
set { this.definitionsFile = value; }
get { return this.definitionsFile; }
}
/// <summary>
/// Provider interface for the manager
/// </summary>
public ILBPluginsManager Provider
{
set { this.provider = value; }
get { return this.provider; }
}
/// <summary>
/// Path of the plugins assemblies
/// </summary>
public string PluginsPath
{
set
{
this.pluginsPath = value;
char sep = Path.DirectorySeparatorChar;
this.pluginsPath = this.pluginsPath.TrimEnd ( sep );
}
get { return this.pluginsPath; }
}
/// <summary>
/// Strig of the last error
/// </summary>
public string LastMessaggeError
{
get { return this.lastMessageErr; }
}
/// <summary>
/// List of the plugins definitions
/// </summary>
public ArrayList Plugins
{
get { return this.plugins; }
}
/// <summary>
/// List of the loaded plugins objects
/// </summary>
public ArrayList PluginsObjects
{
get { return this.pluginObjs; }
}
/// <summary>
/// Enable the messages visibility
/// </summary>
public bool ShowMessages
{
set { this.showMessages = value; }
get { return this.showMessages; }
}
#endregion
#region Public methods
/// <summary>
/// Retrieve the plugin definitions
/// </summary>
/// <param name="name">Name of the plugin definition</param>
/// <returns></returns>
public Plugin GetPlugin( string name )
{
foreach (Plugin plugin in plugins)
{
if ( plugin.Name == name )
return plugin;
}
return null;
}
/// <summary>
/// Load the plugin object
/// </summary>
/// <param name="name">Name of the plugin</param>
/// <returns>Plugin object or null</returns>
public ILBPlugin LoadPlugin ( string name )
{
this.lastMessageErr = "";
// Find plugin definitions
Plugin pi = this.GetPlugin ( name );
if ( pi == null )
{
this.lastMessageErr = "Plugin not found";
return null;
}
// Create the path for the plugin assembly
string str = string.Empty;
if ( this.PluginsPath == string.Empty )
str = ".";
str += this.PluginsPath + System.IO.Path.DirectorySeparatorChar;
if ( pi.Path != null )
{
if ( pi.Path != string.Empty )
str += pi.Path + System.IO.Path.DirectorySeparatorChar;
}
str += pi.Assembly;
// Try to create an object
ILBPlugin piObj = null;
try
{
// Create the plugin instance
ObjectHandle oHandle = Activator.CreateInstanceFrom( str,
pi.Object );
// Set the object
piObj = oHandle.Unwrap() as ILBPlugin;
// Initialization of the plugin
if ( piObj.Initialize() == false )
return null;
// Add to the list
this.pluginObjs.Add ( piObj );
}
catch( Exception e )
{
this.OutputMessage ( e.ToString(), true );
this.lastMessageErr = e.ToString();
}
// Return the plugin object
return piObj;
}
/// <summary>
/// Unload the plugin oblect
/// </summary>
/// <param name="piObj">Plugin object</param>
/// <returns>true if there is no error, otherwise false</returns>
public bool UnloadPlugin( ILBPlugin piObj )
{
if ( piObj != null )
{
// Release the object
if ( piObj.Release() == false )
return false;
// Remove from the list
this.pluginObjs.Remove ( piObj );
}
return true;
}
/// <summary>
/// Load the plugins configuration file
/// </summary>
/// <returns>true if there is no error, otherwise false</returns>
public bool LoadPluginsConfig ()
{
bool ret = true;
try
{
// Message
this.OutputMessage ( "Reading plugins definitions...", false );
// Open definitions file
XmlDocument doc = new XmlDocument();
doc.Load ( this.definitionsFile );
// Find root node
XmlNode pluginsNode = doc.SelectSingleNode ( "Plugins") ;
if ( pluginsNode == null )
throw new XmlException ( "Definitions file is not valid\n" );
// Scan the childs nodes
foreach ( XmlNode node in pluginsNode.ChildNodes )
{
// Find the attributes
XmlAttribute attrName = node.Attributes["Name"];
XmlAttribute attrPath = node.Attributes["Path"];
XmlAttribute attrAssembly = node.Attributes["Assembly"];
XmlAttribute attrVersion = node.Attributes["Version"];
XmlAttribute attrObjectName = node.Attributes["ObjectName"];
// Check attributes
if ( ( attrName.Value == String.Empty ) || ( attrPath.Value == String.Empty ) ||
( attrAssembly.Value == String.Empty ) || ( attrVersion.Value == String.Empty ) ||
( attrObjectName.Value == String.Empty ) )
{
throw new XmlException ( "Node attributes are not valid\n" );
}
// Create a plugin definitions object
Plugin piData = new Plugin();
if ( piData == null )
throw new ApplicationException ( "Unable to create plugin definitions object\n" );
// Set the data
piData.Name = attrName.Value;
piData.Path = attrPath.Value;
piData.Assembly = attrAssembly.Value;
piData.Version = attrVersion.Value;
piData.Object = attrObjectName.Value;
// Add definitions in the list
this.plugins.Add ( piData );
}
// Message all ok
this.OutputMessage ( "Ok", true );
}
catch ( XmlException eXml )
{
// XML exception
this.OutputMessage ( "Failed", true, MessageType.Warning );
this.OutputMessage ( eXml.Message, true, MessageType.Warning );
ret = false;
}
catch( Exception e )
{
// General exception
this.OutputMessage ( "Failed", true, MessageType.Warning );
this.OutputMessage ( e.Message, true, MessageType.Warning );
ret = false;
}
return ret;
}
#endregion
#region Virtual methods
/// <summary>
/// Metodh for viewing the message
/// </summary>
/// <param name="message">Message body</param>
/// <param name="addEndLine">Flag for add a newline character</param>
protected virtual void OutputMessage( string message, bool addEndLine )
{
this.OutputMessage ( message, addEndLine, MessageType.Normal );
}
/// <summary>
/// Metodh for viewing the message
/// </summary>
/// <param name="message">Message body</param>
/// <param name="addEndLine">Flag for add a newline character</param>
/// <param name="type">Type of the message</param>
protected virtual void OutputMessage( string message, bool addEndLine, MessageType type )
{
if ( this.ShowMessages == false )
return;
if ( this.Provider != null )
this.Provider.OutputMessage ( message, addEndLine, type );
else
{
MessageBoxIcon mi = MessageBoxIcon.None;
switch ( type )
{
case MessageType.Error:
mi = MessageBoxIcon.Error;
break;
case MessageType.Warning:
mi = MessageBoxIcon.Warning;
break;
}
MessageBox.Show ( message, this.GetType().Name, MessageBoxButtons.OK, mi );
}
}
#endregion
}
#endregion
}
|
By viewing downloads associated with this article you agree to the Terms of Service and the article's licence.
If a file you wish to view isn't highlighted, and is a text file (not binary), please
let us know and we'll add colourisation support for it.