我正在爲我正在開發的一個項目創建兩個解決方案,一個用於主服務器,它將在不需要更新的情況下持續運行。次要解決方案是DLL,程序員將不斷更改和更新代碼。服務器解決方案是一個Windows應用程序和程序員的解決方案(一個不斷變化的,AKA JupiterCode.dll)是一個類庫。動態更新加載的DLL
我通過telnet訪問代碼,這是必需的,並將在那裏輸入命令。然後輸入的字符串將通過DLL文件上的反射來執行(「用戶輸入'smile',是否有命令叫做'smile'?是的,我們來執行這個代碼吧。」)。我已經完成了所有這些工作,並且正在順利進行,但是當我想要實際更新DLL時,我遇到了一些問題,以便用戶可以輸入更多命令。當我重建類庫時,服務器尚未反映新的更改。服務器只在我重建服務器時反映新的更改。
我想這樣當用戶進入UPDATE到telnet服務器擁有它,它會更新新的DLL加載的DLL,但是當我嘗試做這樣的事情......
string originalDllPath = "C:\\Users\\*****\\Documents\\PseudoGameClient\\bin\\Debug\\JupiterCode.dll";
string newDllPath = "C:\\Users\\*****\\Documents\\PseudoServerStub\\bin\\Debug\\.dll";
string newDllBakPath = "C:\\Users\\*****\\Documents\\PseudoServerStub\\bin\\Debug\\JupiterCodeNewBak.dll";
string oldDllPath = "C:\\Users\\*****\\Documents\\PseudoServerStub\\bin\\Debug\\JupiterCode.dll";
string oldDllBakPath = "C:\\Users\\*****\\Documents\\PseudoServerStub\\bin\\Debug\\JupiterCodeBak.dll";
try
{
File.Copy(originalDllPath, newDllPath, true);
AppDomain.Unload(updatedCodeDomain);
AppDomain sandbox = AppDomain.CreateDomain("Sandbox");
Assembly assembly = sandbox.Load(oldDllBakPath);
upToDateCode = assembly;
File.Copy(oldDllPath, newDllBakPath, true);
File.Copy(newDllPath, oldDllPath, true);
AppDomain.Unload(sandbox);
AppDomain newCodeDomain = AppDomain.CreateDomain("NewCode");
assembly = newCodeDomain.Load(oldDllPath);
upToDateCode = assembly;
File.Copy(newDllBakPath, oldDllBakPath, true);
File.Delete(newDllPath);
File.Delete(newDllBakPath);
updatedCodeDomain = newCodeDomain;
}
catch (Exception ex)
{
}
在這種方法中,一旦它到達
Assembly assembly = sandbox.Load(oldDllBakPath);
這讓我異常:
「無法加載文件或程序集」C:\\ Users \\ aderbedrosia \\ Documents \\ PseudoServerStub \\ bin \\ Debug \\ JupiterCodeBak.dll「或其某個依賴項。給定的程序集名稱或代碼庫無效。 (Exception from HRESULT:0x80131047)「:」C:\\ Users \\ aderbedrosia \\ Documents \\ PseudoServerStub \\ bin \\ Debug \\ JupiterCodeBak.dll「} System.Exception {System.IO.FileLoadException
(注意:Uptodatecode保留爲一個類字段,因爲我後面指的是它執行的命令,它再次,工作完好,除了無法更新。)
我也嘗試過:
File.Copy(originalDllPath, newDllPath, true);
Assembly assembly = Assembly.LoadFrom(oldDllBakPath);
AppDomain.Unload(updatedCodeDomain);
AppDomain sandbox = AppDomain.CreateDomain("sandbox");
sandbox.Load(assembly.GetName());
upToDateCode = null;
upToDateCode = assembly;
File.Copy(oldDllPath, newDllBakPath, true);
File.Copy(newDllPath, oldDllPath, true);
assembly = Assembly.LoadFrom(oldDllPath);
AppDomain.Unload(sandbox);
AppDomain sandbox2 = AppDomain.CreateDomain("secondarySandbox");
sandbox2.Load(assembly.GetName());
upToDateCode = assembly;
File.Copy(newDllBakPath, oldDllBakPath, true);
File.Delete(newDllPath);
File.Delete(newDllBakPath);
updatedCodeDomain = sandbox2;
,並在
錯誤出sandbox.Load(assembly.GetName());
與
「無法加載文件或程序集 'JupiterCode,版本= 1.0.0.0, 文化=中性公鑰= 9a98a67e4d0b3db8' 或它 的一個依賴。系統無法找到文件指定 「:」 JupiterCode,版本= 1.0.0.0,文化=中立, 公鑰= 9a98a67e4d0b3db8"
再次重申,我能夠在運行時動態加載程序集,但用一個更新的DLL替換一個更新的DLL(在運行時,不需要重新編譯)是很困難的。