1
我正在嘗試構建一個可熱插拔的插件系統,用戶可以在其中動態加載和卸載dll。核心應用程序儘可能少地重新啓動是非常必要的,所以我將相當多的功能轉移到外部庫。從我已經發現的研究中,我需要創建第二個AppDomain並將該DLL加載到該中,然後傳遞參數等來運行它。目前,我相信我的大部分程序都能正常工作,但是在從CreateInstance對象上調用AppDomain.Unwrap()函數時遇到錯誤。錯誤如下:C#AppDomain無法加載DLL
System.InvalidCastException: Unable to cast transparent proxy to type 'Program1.Loader'.
下面是加載代碼:
try {
unload(dom,out loader,true);
dom=null;
AppDomainSetup dms = new AppDomainSetup();
dms.ConfigurationFile=Environment.CurrentDirectory+Path.DirectorySeparatorChar+"Program1.exe.config";
dms.ApplicationBase=Environment.CurrentDirectory+Path.DirectorySeparatorChar+"Plugins";
Evidence ev = AppDomain.CurrentDomain.Evidence;
dom=AppDomain.CreateDomain("PluginManager",ev,dms);
AssemblyName an = AssemblyName.GetAssemblyName(Environment.CurrentDirectory+"\\Plugins\\PluginManager.dll");
ObjectHandle obj = dom.CreateInstance(an.FullName,"PluginManager.PluginManager");
loader = (Loader)obj.Unwrap();
loader.LoadAssembly(@"PluginManager.dll");
if(!suppressOutput)
Console.WriteLine("Reload successful.");
}
catch(Exception e) {
unload(dom,out loader,true);
loader=null;
Console.WriteLine("PluginManager failed loading. Enter \"reload\" to try again.\n");
Console.Write(e+"\n\n");
}
此行是其中拋出的錯誤:
loader = (Loader)obj.Unwrap();
外部DLL在幾乎沒有任何代碼它,因爲這是一個概念證明。它如下:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace PluginManager {
public class PluginManager:MarshalByRefObject {
public void run(string comm) {
Console.WriteLine(comm);
}
}
}
編輯:這是加載器類的代碼。
class Loader:MarshalByRefObject {
private Assembly _assembly;
public override object InitializeLifetimeService() {
return null;
}
public void LoadAssembly(string path) {
_assembly=Assembly.Load(AssemblyName.GetAssemblyName(path));
}
public object ExecuteStaticMethod(string typeName,string methodName,params object[] parameters) {
Type type = _assembly.GetType(typeName);
MethodInfo method = type.GetMethod(methodName,BindingFlags.Static|BindingFlags.Public);
return method.Invoke(null,parameters);
}
}
我已經更新了代碼,包括裝載機演員。你能用一些代碼解釋你的答案嗎?我不確定你想要我做什麼。 – Bioniclegenius
感謝您的編輯!但Loader在主程序中。當它嘗試從dll加載它時,CreateInstance不會失敗嗎? – Bioniclegenius
但是你不會嘗試加載Loader,你嘗試加載PluginManager。那就是問題所在。這就是你傳遞給AppDomain.CreateInstance的內容。 –