Skip to content

Instantly share code, notes, and snippets.

@Fhernd
Created June 3, 2014 01:49
Show Gist options
  • Save Fhernd/d85f5d45fe17face9b3f to your computer and use it in GitHub Desktop.
Save Fhernd/d85f5d45fe17face9b3f to your computer and use it in GitHub Desktop.
Demostración de la creación y uso de una clase controladora de carga de assemblies e instanciación de tipos.
using System;
using System.IO;
using System.Reflection;
using System.Threading;
using System.Collections;
using System.Collections.Generic;
using System.Collections.Specialized;
namespace Recetas.Cap03
{
///<summary>
/// Interfaz con contrato estándar para plugins.
///</summary>
public interface IPlugin
{
///<summary>
/// Inicia la ejecución/carga del plugin.
///</summary>
void Iniciar();
///<summary>
/// Detiene la ejecución/carga del plugin.
///</summary>
void Detener();
}
///<summary>
/// Implementación de una clase que representa un
/// plugin abstracto (ejemplo demostrativo).
///</summary>
public class PluginBasico : IPlugin
{
public void Iniciar()
{
Console.WriteLine("El dominio {0} ha iniciado su carga...",
AppDomain.CurrentDomain.FriendlyName.ToString());
}
public void Detener()
{
Console.WriteLine("El dominio {0} ha iniciado su descarga...",
AppDomain.CurrentDomain.FriendlyName.ToString());
}
}
///<summary>
/// Esta es la clase encargad de la gestión de plugins.
/// Facilita la carga de los plugins en un dominio de
/// aplicación específico.
///</summary>
public class GestorPlugins : MarshalByRefObject
{
// Estructura de datos (diccionario) que mantiene
// referencias de a los plugins que gestionará.
private Dictionary<string, IPlugin> plugins = new Dictionary<string, IPlugin>();
public GestorPlugins()
{
}
///<summary>
/// Constructor de `GestorPlugins` que carga
/// una serie (diccionario) de plugins en su
/// momento de instanciación
///</summary>
public GestorPlugins(NameValueCollection listaPlugins)
{
// Carga la lista de plugins en `listaPlugins`:
foreach (string plugin in listaPlugins.Keys)
{
CargarPlugin(listaPlugins[plugin], plugin);
}
}
///<summary>
/// Método que se encarga de la carga de un assembly, y la
/// instanciación de un plugin del assembly en cuestión.
///<summary>
public bool CargarPlugin(string nombreAssembly, string nombrePlugin)
{
try
{
// Carga el assembly:
Assembly assembly = Assembly.Load(nombreAssembly);
// Creación de una instancia de la implementación del plugin:
IPlugin plugin = assembly.CreateInstance(nombrePlugin, true) as IPlugin;
if (plugin != null)
{
// Se agrega el plugin al diccionario:
plugins[nombrePlugin] = plugin;
// Carga satisfactoria:
return true;
}
else
{
return false;
}
}
catch
{
return false;
}
}
///<summary>
/// Inicia el plugin:
///</summary>
public void IniciarPlugin(string plugin)
{
try
{
plugins[plugin].Iniciar();
}
catch
{
// En caso de que la inicialización del
// plugin genere errores, se crea un
// registro de la actividad.
}
}
///<summary>
/// Detiene la ejecución del plugin.
///</summary>
public void DetenerPlugin(string plugin)
{
try
{
plugins[plugin].Detener();
}
catch
{
// En caso de que el detenimiento del
// plugin genere errores, se crea un
// registro de la actividad.
}
}
///<summary>
/// Carga un listo de listado completo de plugins.
///</summary>
public ArrayList ListaPlugins()
{
return new ArrayList(plugins.Keys);
}
public class Aplicacion
{
public static void Main()
{
Console.WriteLine();
// Demostración del uso del constructor de `GestorPlugins`
// con un cero-argumentos:
// Creación de un dominio de aplicación:
AppDomain nuevoDominio1 = AppDomain.CreateDomain("NuevoDominio1");
// Creamos una instancia de `GestorPlugins` con el constructor
// por defecto (cero-argumentos):
GestorPlugins gestor1 = (GestorPlugins) nuevoDominio1.CreateInstanceAndUnwrap(
"GestorPlugins", "Recetas.Cap03.GestorPlugins"
);
// Carga de un plugin básico sobre el gestor de plugins:
gestor1.CargarPlugin("GestorPlugins", "Recetas.Cap03.PluginBasico");
// Operaciones de inicio y detentención del plugin en el
// dominio de aplicación `nuevoDominio1`
// (Especificación de nombre de clase completamente calificado):
gestor1.IniciarPlugin("Recetas.Cap03.PluginBasico");
Thread.Sleep(1000);
gestor1.DetenerPlugin("Recetas.Cap03.PluginBasico");
Console.WriteLine();
Thread.Sleep(2000);
// Demostración del uso del constructor de `GestorPlugins`
// con un argumento:
// Creación otro dominio de aplicación:
AppDomain nuevoDominio2 = AppDomain.CreateDomain("NuevoDominio2");
// Creación de un conjunto de plugins:
NameValueCollection listaPlugins = new NameValueCollection();
// `Aplicacion.exe` es el assembly actual:
listaPlugins["Recetas.Cap03.PluginBasico"] = "GestorPlugins";
// Creamos otra instancia de `GestorPlugins`:
GestorPlugins gestor2 = (GestorPlugins) nuevoDominio2.CreateInstanceAndUnwrap(
"GestorPlugins", "Recetas.Cap03.GestorPlugins", true, 0, null,
new object[] { listaPlugins }, null, null
);
// Despliegue de los plugins cargados en el dominio de
// aplicación `nuevoDominio2`:
Console.WriteLine("\n\nPlugis cargados en `nuevoDominio2`:");
foreach (string s in gestor2.ListaPlugins())
{
Console.WriteLine("\t{0}", s);
}
Console.WriteLine();
}
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment