首先设计一个插件,让插件从MarshalByRefObject继承,以方便跨域传递,类型可以任意取名,代码如下:
namespace SomeLib
{
public class Worker:MarshalByRefObject
{
public void DoWork()
{
for (int i = 0; i < 100; i++)
{
Console.WriteLine($"{i + 1}次 {AppDomain.CurrentDomain.FriendlyName}");
Thread.Sleep(TimeSpan.FromSeconds(1));
}
}
}
}
把生成的dll放到主程序目录下,主程序代码如下:
namespace SomeHost
{
class Program
{
static void Main(string[] args)
{
var addinDll = Path.Combine(Environment.CurrentDirectory, @"SomeLib.dll");
var addinAssembly = Assembly.LoadFrom(addinDll);
var addinType = addinAssembly.ExportedTypes.Where<Type>(t => t.IsClass && t.IsSubclassOf(typeof(MarshalByRefObject))).First<Type>();
var ad = AppDomain.CreateDomain("MyDomain");
dynamic obj = ad.CreateInstanceAndUnwrap(addinType.Assembly.FullName, addinType.FullName);
obj.DoWork();
Console.WriteLine($"obj是代理吗? {RemotingServices.IsTransparentProxy(ad)}");
AppDomain.Unload(ad);
Console.WriteLine($"外接类型所在程序集:{addinType.Assembly.FullName} 完全限定名:{addinType.FullName}");
Console.WriteLine("finished");
Console.ReadKey();
}
}
}
dll在新建的程序域中,运行良好,插件如果有什么问题,不会影响到主体程序,卸载插件也非常方便。我使用了dynamic类型,这样只要知道dll中的方法签名,就可以直接调用,非常方便。遗憾的是插件只能放在主程序目录下,不能单独放另一个目录里,提示找不到文件,也不知道问题出在哪里?使用dotnet4.52。