Ich muss eine benutzerdefinierte Anwendungsdomäne erstellen, um einen Fehler in der .NET-Laufzeitumgebung default behavior zu umgehen. Keiner der Beispielcodes, die ich online gesehen habe, ist hilfreich, da ich nicht weiß, wo ich ihn platzieren soll oder was er innerhalb meiner Main()
Methode ersetzen muss.Wie erstelle ich eine Anwendungsdomäne und führe meine Anwendung darin aus?
Antwort
Es soll wahrscheinlich, dass AppDomains Schaffung nur um etwas zu bekommen, zu beachten, dass mit einer konstanten Zeichenfolge festgelegt werden kann, ist wahrscheinlich der falsche Weg, es zu tun . Wenn Sie versuchen, das gleiche wie der Link zu tun, bemerkt man, könnte man einfach tun:
var configFile = Assembly.GetExecutingAssembly().Location + ".config";
if (!File.Exists(configFile))
throw new Exception("do your worst!");
rekursive Einspeisepunkt: o)
static void Main(string[] args)
{
if (AppDomain.CurrentDomain.IsDefaultAppDomain())
{
Console.WriteLine(AppDomain.CurrentDomain.FriendlyName);
var currentAssembly = Assembly.GetExecutingAssembly();
var otherDomain = AppDomain.CreateDomain("other domain");
var ret = otherDomain.ExecuteAssemblyByName(currentAssembly.FullName, args);
Environment.ExitCode = ret;
return;
}
Console.WriteLine(AppDomain.CurrentDomain.FriendlyName);
Console.WriteLine("Hello");
}
Schnell Probe eine nicht-statische Sekundär mit Einspeisepunkt und MarshalByRefObject ...
class Program
{
static AppDomain otherDomain;
static void Main(string[] args)
{
otherDomain = AppDomain.CreateDomain("other domain");
var otherType = typeof(OtherProgram);
var obj = otherDomain.CreateInstanceAndUnwrap(
otherType.Assembly.FullName,
otherType.FullName) as OtherProgram;
args = new[] { "hello", "world" };
Console.WriteLine(AppDomain.CurrentDomain.FriendlyName);
obj.Main(args);
}
}
public class OtherProgram : MarshalByRefObject
{
public void Main(string[] args)
{
Console.WriteLine(AppDomain.CurrentDomain.FriendlyName);
foreach (var item in args)
Console.WriteLine(item);
}
}
Sie müssen:
1) eine Instanz von AppDomainSetup Objekt erstellen und füllen Sie es mit den Setup-Informationen, die Sie für Ihre Domain unter Verwendung AppDomain.CreateDoman Methode
2) Erstellen Sie Ihre neue Domain mögen. Die AppDomainSetup-Instanz mit Konfigurationsparametern wird an die CreateDomain-Methode übergeben.
3) Erstellen Sie eine Instanz Ihres Objekts in der neuen Domäne, indem Sie die CreateInstanceAndUnwrap-Methode für das Domänenobjekt verwenden. Diese Methode übernimmt den Typnamen des zu erstellenden Objekts und gibt einen Remoting-Proxy zurück, den Sie in Ihrer Hauptdomäne verwenden können, um mit dem in der neuen Domäne erstellten Objekt zu kommunizieren
Sobald Sie mit diesen 3 Schritten fertig sind, können Sie Methoden aufrufen die andere Domäne über den Proxy. Sie können die Domäne auch entfernen, nachdem Sie fertig sind, und sie erneut laden.
Diese topic in MSDN Hilfe hat ziemlich ausführliches Beispiel, was Sie brauchen
, die mehr oder weniger ist, was ich in den Beispielen gesehen, die ich an anderer Stelle gesehen haben, aber liefert keine der Informationen, die mir noch fehlen. Soll ich gerade Application.Run (neue MyForm) aufrufen? Zerschneide ich den gesamten Startup-Code von meiner Main-Methode, lasse ihn in eine neue Methode fallen und rufe ihn an, um meine App zu starten? Keine der oben genannten, weil ich noch mehr verwirrt bin als ich denke, dass ich bin? –
Das Objekt, das Sie versuchen, den Proxy von zu bekommen, muss 'MarshalByRefObject' sein, oder es wird nur versucht, eine Kopie in die ursprüngliche AppDomain zu serialisieren. –
@Matthew Whited - Sie haben Recht, ich habe vergessen zu erwähnen, dass – mfeingold
Danke. Gibt es einen Grund, einen Ansatz dem anderen vorzuziehen? –
Die erste wäre wahrscheinlich sauberer. Dadurch können Sie einen Standard-Einstiegspunkt verwenden, anstatt ein Objekt erstellen zu müssen, das über die App-Domänen gemarshallt werden müsste. Der zweite Ansatz ist typischer.Normalerweise wird es jedoch für Plug-Ins verwendet und nicht als Haupteinstiegspunkt der App. –
Es gibt auch eine '.ExecuteAssembly (...)' -Methode für das 'AppDomain'-Objekt, mit der Sie den Pfad zu einer anderen Assembly angeben können, die einen Einstiegspunkt enthält. Dies könnte ein etwas saubereres Design ermöglichen, würde jedoch mindestens zwei Baugruppen erfordern. –