我有一个带有简单插件系统的小型asp.net webapi应用程序。 所有插件都位于" / bin / debug / plugins /"夹。 我在应用程序启动时加载插件并从autofac容器中的插件注册组件。
但我有一个nhibernate插件的问题,它包含我的存储库,映射等。插件加载后也加载了nhibernate.dll(使用ProcessExporer检查它:http://postimg.org/image/mm4w56vln/)。然后我尝试创建ISessionFactory ...并接收下一个错误
Could not load file or assembly 'NHibernate, Version=4.0.0.4000, Culture=neutral, PublicKeyToken=aa95f207798dfdb4' or one of its dependencies. The system cannot find the file specified.":"NHibernate, Version=4.0.0.4000, Culture=neutral, PublicKeyToken=aa95f207798dfdb4
我的插件加载程序:
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Reflection;
using Jarres.Plugin.Exceptions;
namespace Jarres.Plugin
{
public class PluginLoader : IPluginLoader
{
private readonly List<Assembly> _cache = new List<Assembly>();
public IDictionary<PluginInfo, IPlugin> Load(IEnumerable<PluginInfo> plugins)
{
if (plugins == null)
{
throw new ArgumentNullException("plugins");
}
InitializeCache();
AppDomain.CurrentDomain.AssemblyResolve += ResolveModuleAssembly;
var result = plugins.ToDictionary(x => x, GetPlugin);
AppDomain.CurrentDomain.AssemblyResolve -= ResolveModuleAssembly;
return result;
}
private IPlugin GetPlugin(PluginInfo plugin)
{
var path = plugin.Path;
var name = plugin.Name;
var version = plugin.Version;
var fileversion = FileVersionInfo.GetVersionInfo(path).ProductVersion;
if (version != fileversion)
{
throw new PluginVersionException(name, version, fileversion);
}
var types = LoadAssembly(path).GetExportedTypes().Where(x => typeof (IPlugin).IsAssignableFrom(x) && !x.IsAbstract).ToArray();
if (types.Length == 0)
{
throw new PluginNotFoundException(name, path);
}
if (types.Length > 1)
{
throw new MultiplePluginsException(name, path);
}
return (IPlugin)Activator.CreateInstance(types[0]);
}
private Assembly LoadAssembly(string path)
{
var assembly = GetFromCacheByPath(path);
if (assembly == null)
{
assembly = Assembly.LoadFile(path);
AddToCache(assembly);
LoadAssemblyReferences(assembly);
}
return assembly;
}
private void LoadAssemblyReferences(Assembly assembly)
{
foreach (var reference in assembly.GetReferencedAssemblies())
{
var directory = Path.GetDirectoryName(assembly.Location);
if (directory != null)
{
var path = Path.Combine(directory, reference.Name + ".dll");
if (File.Exists(path))
{
LoadAssembly(path);
}
}
}
}
private Assembly ResolveModuleAssembly(object sender, ResolveEventArgs args)
{
return GetFromCacheByName(args.Name);
}
#region cache
private void InitializeCache()
{
_cache.AddRange(AppDomain.CurrentDomain.GetAssemblies());
foreach (var assembly in Assembly.GetExecutingAssembly().GetReferencedAssemblies())
{
_cache.Add(Assembly.Load(assembly));
}
}
private void AddToCache(Assembly assembly)
{
if (assembly == null)
{
throw new ArgumentNullException("assembly");
}
_cache.Add(assembly);
}
private Assembly GetFromCacheByPath(string path)
{
var name = Path.GetFileNameWithoutExtension(path);
return _cache.FirstOrDefault(x => x.GetName().Name == Path.GetFileName(name));
}
private Assembly GetFromCacheByName(string name)
{
return _cache.FirstOrDefault(a => a.FullName.StartsWith(name));
}
#endregion
}
}
只有将nhibernate.dll复制到/ bin / debug /文件夹时才能创建ISessionFactory。但我想将此dll存储在插件文件夹中。 例如,我对实体框架插件没有任何问题。
为什么我在加载nhibernate.dll时无法创建ISessionFactory?
答案 0 :(得分:0)
答案 1 :(得分:0)
解决。 所有引用都正确加载,但此引用不在/ bin / {Debug,Release} /文件夹中。 所以,我将目标文件夹的路径添加到我的app.config中。