views:

34

answers:

2

I have program which loads an assembly using Asssembly.LoadFrom method. Some time later I attempt to use Type.GetType to create a type from that assembly (using AssemblyQualifiedName), but the method returns null. If I set it to throw exception, it tells

Could not load file or assembly '...' or one of its dependencies. The system cannot find the file specified.

But I am sure the exact same assembly is already loaded (it shows in the AppDomain.CurrentDomain.GetAssemblies() list).

Anybody has an idea what could be wrong and/or how to solve this issue?

Thanks for help

+3  A: 

In order to understand why this doesn't work, you need to understand the issue of "load contexts". Type.GetType only looks at the "Load" context. The assembly you loaded into memory was in the "LoadFrom" context.

The only way to really get binds in the load context to see assemblies in the load-from context is to use the AssemblyResolve event and write code to return the correct assembly. The AssemblyResolve event fires right before the bind fails and all other assembly lookup did not succeed.

See the following links for more information about load contexts and issues that arise when using LoadFrom.

MSDN - http://msdn.microsoft.com/en-us/library/dd153782.aspx
AssemblyResolve - http://msdn.microsoft.com/en-us/library/system.appdomain.assemblyresolve.aspx
Suzanne Cook - http://blogs.msdn.com/b/suzcook/archive/2003/05/29/57143.aspx

Josh Einstein
A tried using Assembly.Load(AssemblyName.GetAssemblyName(file)). The assembly loads fine (the rest of the program seems to work), but the exception in the Type.GetType stays the same.
CommanderZ
Now it works (after I added the directory where the assemblies are into app.config). Thanks for an explanation of thw area of .NET I had no clue about.
CommanderZ
Right, the AssemblyName returned by GetAssemblyName will get you the strong name of the assembly but then when that is passed to Assembly.Load, the normal assembly probing rules are followed. So as you've noted, it only works if the runtime can find the assembly which may involve app.config probing hints.
Josh Einstein
+2  A: 

If you can get the assembly using Assembly.LoadFrom then you can get the type by doing:

        Assembly assembly = Assembly.LoadFrom("whatever");
        Type myType = assembly.GetType("typeName")

The assembly.GetType has other overloads which you can find out about here

Steve Ellinger
+1 Good pragmatic solution. He still may run into issues if other code attempts to load other types in the same assembly via the load context without AssemblyResolve though. Unfortunately, LoadFrom just has a while bunch of unexpected side-effects that are hard to work around.
Josh Einstein