Skip to content

Instantly share code, notes, and snippets.

@squadwuschel
Last active October 24, 2017 18:05
Show Gist options
  • Save squadwuschel/2a98704003499712c1125e74405721e8 to your computer and use it in GitHub Desktop.
Save squadwuschel/2a98704003499712c1125e74405721e8 to your computer and use it in GitHub Desktop.
Laden von Assemblies und Manuelles nachladen der Abhängigkeiten.
class Program
{
static void Main(string[] args)
{
//Handler registrieren, für den die
AppDomain.CurrentDomain.ReflectionOnlyAssemblyResolve += CurrentDomain_ReflectionOnlyAssemblyResolve;
var alleAssemblies = LoadAssemblies(@"C:\Test\DemoPageProxyGenerator");
}
public static List<Assembly> LoadAssemblies(string fullpathToProjectdir)
{
var allAssemblies = new List<Assembly>();
foreach (string dll in Directory.GetFiles(fullpathToProjectdir, "*.dll", SearchOption.AllDirectories))
{
try
{
//Aufpassen das wir nicht eine Assembly doppelt laden, die evtl. in unterschiedlichen Verzeichnissen liegt.
if (allAssemblies.Any(p => Path.GetFileName(p.Location) == Path.GetFileName(dll)))
{
continue;
}
//Wir nutzen kein Assembly.Load(dll) mehr, da wir auch 64 Bit DLLs laden wollen in einem 32 Bit Prozess. Denn die T4 Template Exe ist eine 32Bit Datei.
//Daher müssen wir Assembly.ReflectionOnlyLoadFrom(dll) verwenden. ACHTUNG damit kann man kein "GetCustomAttributes" mehr verwenden, sondern muss
//"GetCustomAttributesData" verwenden um z.B. die passenden Attribute zu laden.
allAssemblies.Add(Assembly.ReflectionOnlyLoadFrom(dll));
}
catch (Exception e)
{
}
}
//Erst wenn man auf die Typen der Assembly zugreift, werden die Abhängkeiten geladen,
//vorher wird der "CurrentDomain_ReflectionOnlyAssemblyResolve" nicht aufgerufen.
allAssemblies.ForEach(entry =>
{
entry.GetTypes();
});
return allAssemblies;
}
/// <summary>
/// Dependency Resolver für die Assemblies die geladen werden sollen.
/// Da wir auch 64Bit Assemblies laden wollen in einem 32 Bit Prozess,
/// müssen wir die Verweise "Manuell" auflösen.
/// </summary>
public static Assembly CurrentDomain_ReflectionOnlyAssemblyResolve(object sender, ResolveEventArgs args)
{
//Der Name der Assembly die wir nachladen müssen
var assemblyToLoad = new AssemblyName(args.Name);
//Wir ermitteln das aktuelle Arbeitsverzeichnis der anfragenden
//Assembly im besten Fall handelt es sich um das "bin" Directory der Anwendung.
var currentDir = Path.GetDirectoryName(args.RequestingAssembly.Location);
if (currentDir != null)
{
//wir bauen den Pfad zur Assembly zusammen die wir auflösen sollen.
//und prüfen ob die Datei evtl. im aktuellen "bin" verzeichnis bereits existiert, dann wird diese
//Datei als Abhängigkeit zurückgegeben und wir ignorieren damit die Assembly Redirects in der App.Config/Web.Config
var pathWithDll = Path.Combine(currentDir, $"{assemblyToLoad.Name}.dll");
if (File.Exists(pathWithDll))
{
return Assembly.ReflectionOnlyLoadFrom(pathWithDll);
}
}
//Wenn es sich um eine Assembly Handelt, die wir nicht im lokalen "bin" Verzeichnis finden konnten
//dann soll die Datei im GAC gesucht werden.
var name = System.AppDomain.CurrentDomain.ApplyPolicy(args.Name);
return Assembly.ReflectionOnlyLoad(name);
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment