stevo
stevo

Reputation: 2284

How to load assemblies in ASP.NET Core 1.0 RC2

I am migrating my web app from ASP.NET Core RC1 to RC2. I'm trying to load my referenced class libraries.

This code snippet doesn't work with RC2 any more:

public class Startup
{  
    public void Configure(IApplicationBuilder app, IHostingEnvironment env, ILoggerFactory loggerFactory)
    {
        // libraryManager is null .... 
        ILibraryManager libraryManager = app.GetService<ILibraryManager>();

        List<Assembly> result = new List<Assembly>();

        IEnumerable<Library> libraries = libraryManager.GetLibraries();

        IEnumerable<AssemblyName> assemblyNames = libraries.SelectMany(e => e.Assemblies).Distinct();
        assemblyNames = Enumerable.Where(assemblyNames, e => e.Name.StartsWith("projectNamespace"));

        foreach (AssemblyName assemblyName in assemblyNames)
        {
            Assembly assembly = Assembly.Load(assemblyName);
            .
            .
            .
        }
    }
}

Upvotes: 5

Views: 3142

Answers (2)

Maxim
Maxim

Reputation: 13458

I think stevo has made 2 wrong assumptions:

1) that project namespace should be part of compilation library name.
2) that compilation library name is the same as binary name.

First one is wrong when you change it in project settings. Second one is wrong when you specify it in buildOptions in project.json.

So your idea is correct but implementation is wrong. To fix that we need to forget about resolving by namespace until assembly is loaded.
I guess since all assemblies will be loaded in any case we will not get big performance lag.

But it is not panacea... assembly can have multiple root namespaces inside! So maybe better way will be to define some attribute on assembly level and check it instead of namespace.

In any case if you want to limit your search by assembly name it should be made like this:

IEnumerable<AssemblyName> names = DependencyContext.Default.GetDefaultAssemblyNames();

foreach (AssemblyName name in names)
{
    if (name.Name.StartsWith("MyRoot") == true)
    {
        Assembly assembly = Assembly.Load(name);

        // Process assembly here...
        // I will check attribute for each loaded assembly found in MyRoot.
    }
}

Upvotes: 3

stevo
stevo

Reputation: 2284

I found a solution. I'm using now DependencyContext instead of ILibraryManager

var loadableAssemblies = new List<Assembly>();

var deps = DependencyContext.Default;            
foreach (var compilationLibrary in deps.CompileLibraries)
{
    if (compilationLibrary.Name.Contains(projectNamespace))
    {
        var assembly = Assembly.Load(new AssemblyName(compilationLibrary.Name));
        loadableAssemblies.Add(assembly);
    }
}

Upvotes: 12

Related Questions