Frage Erstellen Sie benutzerdefinierte Anwendungsdomäne, und fügen Sie ihr Baugruppen hinzu


Wie kann ich eine App-Domain erstellen, ihr Assemblys hinzufügen und diese App-Domain dann zerstören? Das habe ich ausprobiert:

    static void Main(string[] args)
    {           
        string pathToExe = @"A:\Users\Tono\Desktop\ConsoleApplication1.exe";

        AppDomain myDomain = AppDomain.CreateDomain("MyDomain");

        Assembly a = Assembly.Load(System.IO.File.ReadAllBytes(pathToExe));

        myDomain.Load(a.FullName); // Crashes here!            
    }

Ich habe es auch versucht:

myDomain.Load(File.ReadAllBytes(pathToExe)); 

Wie kann ich der appdomain eine Assembly hinzufügen? Sobald ich das getan habe, kann ich die Methode über Reflektion ausfindig machen und dann die Appdomain zerstören

Die Ausnahme, die ich bekomme, ist:

Konnte Datei oder Assembly nicht laden 'ConsoleApplication1, Version = 1.0.0.0,   Culture = neutral, PublicKeyToken = null 'oder eine seiner Abhängigkeiten. Das   System kann die angegebene Datei nicht finden.


7
2018-06-20 23:04


Ursprung


Antworten:


Zwei schnelle Punkte:

  1. AppDomain.Load lädt eine Assembly in der aktuellen AppDomain und nicht auf myDomain (komisch, ich weiß).
  2. AppDomain.Load lädt eine Baugruppe in die Load Kontext, der Assemblies aus dem Basis-Verzeichnis der Apps, den privaten Bin-Pfaden und dem GAC löst. Wahrscheinlich befindet sich die Assembly, die Sie laden möchten, nicht an einer dieser Stellen, was die Ausnahmebedingungsnachricht erklärt.

Für mehr Informationen sehen Sie sich das an Antworten.

Eine Möglichkeit zum Laden von Assemblys in eine Anwendungsdomäne ist das Erstellen eines von MarshalByRef abgeleiteten Ladeprogramms. Sie benötigen so etwas, um zu verhindern, dass Typen (und Assemblys) in Ihre Hauptanwendungsdomäne gelangen. Hier ist ein einfacher:

public class SimpleAssemblyLoader : MarshalByRefObject
{
    public void Load(string path)
    {
        ValidatePath(path);

        Assembly.Load(path);
    }

    public void LoadFrom(string path)
    {
        ValidatePath(path);

        Assembly.LoadFrom(path);
    }

    private void ValidatePath(string path)
    {
        if (path == null) throw new ArgumentNullException("path");
        if (!System.IO.File.Exists(path))
            throw new ArgumentException(String.Format("path \"{0}\" does not exist", path));
    }
}

Und benutze es so:

//Create the loader (a proxy).
var assemblyLoader =  (SimpleAssemblyLoader)myDomain.CreateInstanceAndUnwrap(typeof(SimpleAssemblyLoader).Assembly.FullName, typeof(SimpleAssemblyLoader).FullName);
//Load an assembly in the LoadFrom context. Note that the Load context will
//not work unless you correctly set the AppDomain base-dir and private-bin-paths.
assemblyLoader.LoadFrom(pathToExe);

//Do whatever you want to do.

//Finally unload the AppDomain.
AppDomain.Unload(myDomain);

11
2018-06-26 15:19