¿Diferencia entre LoadFile y LoadFrom con .NET Assemblies?

Estaba mirando la documentación de msdn y todavía estoy un poco confundido sobre cuál es exactamente la diferencia entre usar LoadFile y LoadFrom al cargar un ensamblaje. ¿Puede alguien proporcionar un ejemplo o una analogía para describirlo mejor? La documentación de MSDN me confundió más. Además, es ReflectionOnlyLoadFrom lo mismo que LoadFrom excepto que carga el ensamblaje solo en modo de reflexión.

Como mi experiencia .NET no es la mejor, aquí hay algunas preguntas sobre la documentación de MSDN que utiliza LoadFile:

1) ¿Qué significa que LoadFile examina ensamblajes que tienen la misma identidad pero que están ubicados en diferentes rutas? ¿Cuál es la identidad (ejemplo)?

2) Indica que LoadFile no carga archivos en el ‘Contexto LoadFrom’ y no resuelve dependencias utilizando la ruta de carga. ¿Qué significa esto? ¿Alguien puede dar un ejemplo?

3) Por último, indica que LoadFile es útil en este escenario limitado porque LoadFrom no puede cargar ensamblajes que tienen las mismas identidades pero diferentes rutas; solo cargará la primera de esas asambleas, lo que nuevamente me lleva a la misma pregunta, ¿cuál es la identidad de las asambleas?

¿Esto lo aclara?

 // path1 and path2 point to different copies of the same assembly on disk: Assembly assembly1 = Assembly.LoadFrom(path1); Assembly assembly2 = Assembly.LoadFrom(path2); // These both point to the assembly from path1, so this is true Console.WriteLine(assembly1.CodeBase == assembly2.CodeBase); assembly1 = Assembly.LoadFile(path1); assembly2 = Assembly.LoadFile(path2); // These point to different assemblies now, so this is false Console.WriteLine(assembly1.CodeBase == assembly2.CodeBase); 

Editar : para responder a las preguntas que planteaste en tu pregunta revisada, definitivamente debes leer a Suzanne Cook en Assembly Identity .

Hay muchas reglas que rigen cómo se cargan los ensamblajes, y algunas tienen que ver con la forma en que resuelven las dependencias: si su AssemblyA depende de AssemblyB, ¿dónde debería buscar .NET para encontrar AssemblyB? En Global Assembly Cache, el mismo directorio que encontró AssemblyA, o en otro lugar completamente? Además, si encuentra copias múltiples de ese ensamblaje, ¿cómo debería elegir cuál usar?

LoadFrom tiene un conjunto de reglas, mientras que LoadFile tiene otro conjunto de reglas. Es difícil imaginar muchas razones para usar LoadFile , pero si necesita usar la reflexión en diferentes copias del mismo ensamblaje, está ahí para usted.

Del blog de Suzanne Cook :

LoadFile vs. LoadFrom

Ten cuidado, estas no son lo mismo.

LoadFrom () pasa por Fusion y puede redirigirse a otro ensamblado en una ruta diferente pero con la misma identidad si ya se ha cargado uno en el contexto LoadFrom.

LoadFile () no se vincula a través de Fusion: el cargador simplemente sigue adelante y carga exactamente * lo que solicitó la persona que llamó. No utiliza el contexto Load o LoadFrom.

Por lo tanto, LoadFrom () generalmente le brinda lo que usted solicitó, pero no necesariamente. LoadFile () es para aquellos que realmente quieren realmente lo que se solicita. (* Sin embargo, a partir de v2, la política se aplicará tanto a LoadFrom () como a LoadFile (), por lo que LoadFile () no será necesariamente lo que se solicitó. Además, a partir de v2, si un ensamblado con su identidad está en En su lugar, se usará el GAC, la copia GAC. Use ReflectionOnlyLoadFrom () para cargar exactamente lo que desea, pero tenga en cuenta que los ensamblados cargados de esa manera no se pueden ejecutar.

LoadFile () tiene una trampa. Como no usa un contexto vinculante, sus dependencias no se encuentran automáticamente en su directorio. Si no están disponibles en el contexto Cargar, tendrá que suscribirse al evento AssemblyResolve para enlazarlos.

Mira aquí .

Consulte también Elegir un artículo de contexto vinculante en el mismo blog.

Después de muchos arañazos en la cabeza, esta tarde descubrí una diferencia.

Quería cargar una DLL en tiempo de ejecución, y la DLL vivía en otro directorio. Esa DLL tenía sus propias dependencias (DLL) que también vivían en ese mismo directorio.

LoadFile (): cargó el DLL específico, pero no las dependencias. Entonces, cuando se hizo la primera llamada desde el DLL a uno de esos otros DLL lanzó una excepción FileNotFoundException.

LoadFrom (): cargué la DLL que especifiqué y también todas las dependencias que vivían en ese directorio.

una diferencia que noté es:

Assembly.LoadFile – Carga el ensamblaje en diferentes AppDomain con derechos de usuario limitados (diffrence principel). operaciones como serilización / deserilización no pudieron realizarse.

Assembly.LoadFrom : carga el ensamblado en el mismo dominio de aplicación con los mismos derechos de usuario (mismo principio).

Nota: Si un ensamblaje se carga usando una ruta 8.3, y luego desde una ruta que no sea 8.3, se verán como ensamblajes diferentes, aunque sean la misma DLL física.

.NET tiene un contexto de carga diferente. Suzanne Cook escribió sobre ellos aquí: http://blogs.msdn.com/suzcook/archive/2003/05/29/57143.aspx

Esta es la forma en que .Net pone en cuarentena las referencias que no están mezcladas.

En mi caso, simplemente tuve que eliminar el caché de la aplicación ASP que se encuentra @C C:\Windows\Microsoft.NET\Framework\[asp version]\Temporary ASP.NET Files . Se reconstruye cuando el sitio se ejecuta por primera vez. Asegúrese de detener IIS primero.

Espero que esto ayude a alguien como lo hizo por mí.

De acuerdo con la documentación:

LoadFile (String): carga el contenido de un archivo de ensamblado dado una ruta de archivo.

LoadFrom (String): carga un ensamblado dado su nombre o ruta de archivo.