how to load all assemblies from within your /bin directory
Asked Answered
M

4

45

In a web application, I want to load all assemblies in the /bin directory.

Since this can be installed anywhere in the file system, I can't gaurantee a specific path where it is stored.

I want a List<> of Assembly assembly objects.

Mayda answered 17/8, 2009 at 14:33 Comment(0)
G
63

Well, you can hack this together yourself with the following methods, initially use something like:

string path = Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location);

to get the path to your current assembly. Next, iterate over all DLL's in the path using the Directory.GetFiles method with a suitable filter. Your final code should look like:

List<Assembly> allAssemblies = new List<Assembly>();
string path = Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location);

foreach (string dll in Directory.GetFiles(path, "*.dll"))
    allAssemblies.Add(Assembly.LoadFile(dll));

Please note that I haven't tested this so you may need to check that dll actually contains the full path (and concatenate path if it doesn't)

Giglio answered 17/8, 2009 at 15:2 Comment(4)
You'll probably also want to add a check to ensure you don't add the Assembly that you're actually running as well :)Giglio
The path variable contains the directory filename, it needs to be shortened with Path.GetDirectoryName(path)Commonplace
For my ASP.NET application it seems like CodeBase contains the correct path. Use Uri.LocalPath to remove the file://-part.Trangtranquada
Don't forget to check for "*.exe" too, since executable files can also be assemblies. By the way, there is a better method to enumerate files in .NET 4+. Take a look to this question #163662Shelves
B
54

To get the bin directory, string path = Assembly.GetExecutingAssembly().Location; does NOT always work (especially when the executing assembly has been placed in an ASP.NET temporary directory).

Instead, you should use string binPath = System.IO.Path.Combine(System.AppDomain.CurrentDomain.BaseDirectory, "bin");

Further, you should probably take the FileLoadException and BadImageFormatException into consideration.

Here is my working function:

public static void LoadAllBinDirectoryAssemblies()
{
    string binPath = System.IO.Path.Combine(System.AppDomain.CurrentDomain.BaseDirectory, "bin"); // note: don't use CurrentEntryAssembly or anything like that.

    foreach (string dll in Directory.GetFiles(binPath, "*.dll", SearchOption.AllDirectories))
    {
    try
    {                    
        Assembly loadedAssembly = Assembly.LoadFile(dll);
    }
    catch (FileLoadException loadEx)
    { } // The Assembly has already been loaded.
    catch (BadImageFormatException imgEx)
    { } // If a BadImageFormatException exception is thrown, the file is not an assembly.

    } // foreach dll
}
Bernadette answered 8/4, 2011 at 18:56 Comment(3)
The "bin" directory won't necessarily exist in a deployed .NET Application. You should note that your solution only works for ASP.NET.Drawer
The location of the "bin" directory is located in the AppDomain.SetupInfomation object. Usage as such: var assembliesDir = setup.PrivateBinPathProbe != null ? setup.PrivateBinPath : setup.ApplicationBase;Ide
Be carefull about using the Assembly.LoadFile, because it can cause multiple versions of the same assembly to be loaded (see the docs for reference). Actually I bumped into this problem by myself. The Assembly.Load method is more safe, you can use it like this: Assembly.Load(Path.GetFileNameWithoutExtension(dll)).Aztec
P
6

You can do it like this, but you should probably not load everything into the current appdomain like this, since assemblies might contain harmful code.

public IEnumerable<Assembly> LoadAssemblies()
{
    DirectoryInfo directory = new DirectoryInfo(@"c:\mybinfolder");
    FileInfo[] files = directory.GetFiles("*.dll", SearchOption.TopDirectoryOnly);

    foreach (FileInfo file in files)
    {
        // Load the file into the application domain.
        AssemblyName assemblyName = AssemblyName.GetAssemblyName(file.FullName);
        Assembly assembly = AppDomain.CurrentDomain.Load(assemblyName);
        yield return assembly;
    } 

    yield break;
}

EDIT: I have not tested the code (no access to Visual Studio at this computer), but I hope that you get the idea.

Proceleusmatic answered 17/8, 2009 at 15:0 Comment(0)
B
-3

I know this is a old question but...

System.AppDomain.CurrentDomain.GetAssemblies()

Birthmark answered 20/10, 2012 at 10:22 Comment(1)
I believe this only returns the assemblies that are referenced by the calling assembly (all assemblies the current assembly depends on). This does not necessarily equate to all assemblies present in the executing directory. msdn.microsoft.com/en-us/library/…Microcosm

© 2022 - 2024 — McMap. All rights reserved.