AppDomain doesn't make shadow files

亡梦爱人 提交于 2020-01-03 02:01:22

问题


I understand loaded assembly can not be unloaded directly so I created temporary domain and loaded assembly but I got error in creating shadow files.

The code I wrote is as follows:

[LoaderOptimization(LoaderOptimization.MultiDomainHost)]
[STAThread]
static void Main(string[] args)
{
    string startupPath = @"D:\Temp\MyLib\bin\Debug";
    string cachePath = Path.Combine(startupPath, "__cache");
    string assembly = Path.Combine(startupPath, "MyLib.dll");

    AppDomainSetup setup = new AppDomainSetup();
    setup.ApplicationName = "MyLIb";
    setup.ShadowCopyFiles = "true";
    setup.CachePath = cachePath;

    AppDomain domain = AppDomain.CreateDomain("MyLIb", AppDomain.CurrentDomain.Evidence, setup);

    var np = FindFileInPath("MyLib.dll", cachePath);
    var ass = Assembly.LoadFile(np);
    var types = ass.GetTypes();
    AppDomain.Unload(domain);
    }

I got error in finding file in path "could not find a part of the path 'D:\Temp\MyLib\bin\Debug__cache'."

public static string FindFileInPath(string filename, string path)
{
   filename = filename.ToLower();

   foreach (var fullFile in Directory.GetFiles(path))
   {
       var file = Path.GetFileName(fullFile).ToLower();
       if (file == filename)
           return fullFile;

   }
   foreach (var dir in Directory.GetDirectories(path))
   {
       var file = FindFileInPath(filename, dir);
       if (!string.IsNullOrEmpty(file))
                return file;
        }

        return null;
    }
  }

Could someone help me out of this trouble.

Thanks in advance. Joon


回答1:


To start a new appdomain you need to set the ApplicationBase property of your AppDomainSetup. This is the path of the dll's you want to load. Also, you need to set the ShadowCopyDirectories property of your AppDomainSetup object. This will make a shadow copy of all the dll's that are in the given directories.The CachePath determines where the shadowfolders will be created.

For more information see: AppDomainSetup met property ShadowCopyDirectories

AppDomainSetup setup = new AppDomainSetup();
setup.ApplicationName = "MyLIb";
setup.ApplicationBase = dllsDir;
setup.ShadowCopyFiles = "true";
setup.CachePath = cachePath; 
setup.ShadowCopyDirectories = dllsDir; 
AppDomain = AppDomain.CreateDomain("MyAppDomain", null, setup);

You first need to invoke the CreateInstanceAndUnwrap method of the new appdomain. Then you can begin loading dll's in the new Appdomain.

var proxy = AppDomain.CreateInstanceAndUnwrap(GetType().Assembly.GetName().ToString(), typeof(Proxy).FullName);
var assembly = proxy.GetAssembly(fullPathToDllInDllsDir);

This is the "Proxy" class you can create. Note that the most important part of this class is the MarshalByRefObject

 public class Proxy : MarshalByRefObject
 {
        public Assembly GetAssembly(string assemblyPath)
        {
            try
            {
                return Assembly.Load(AssemblyName.GetAssemblyName(assemblyPath));
            }
            catch (Exception)
            {
                return null;
            }
        }   
} 

This will create a shadowfolder for that dll and load it in the appdomain (If ShadowCopyFiles is set to true)

Extra: Try to use the Assembly.Load() or Assembly.LoadFrom() methods and try to avoid the use of Assembly.LoadFile(). This is only needed in very specific cases. See this explanation

For assemblies that are loaded without context, the problem can be caused by using the Assembly.LoadFile method to load the same assembly from different paths. The runtime considers two assemblies that are loaded from different paths to be different assemblies, even if their identities are the same.

Note that you can use the Assembly.LoadFrom method to load these assemblies. Because they are now in the probing path, they will be loaded into the default load context instead of the load-from context. However, we recommend that you switch to the Assembly.Load method and supply full assembly display names to ensure that correct versions are always used.



来源:https://stackoverflow.com/questions/46067782/appdomain-doesnt-make-shadow-files

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!