NHibernate не может разрешить классы в динамически загруженной сборке, загруженной из подкаталога - PullRequest
0 голосов
/ 26 июня 2018

// Форматирование выполнено неправильно.

Используя плагины nopcommerce, написанные на ядре nhibernate и .net, каждый плагин содержит свой собственный каталог сущностей, но при сбое конфигурации NHibernate

var cfg = new Configuration();
cfg.Configure(CommonHelper.MapPath("~/App_Data/db/defauls.config"));
// error here
cfg.AddAssembly("plugins assembly name");

FileNotFoundException: не удалось загрузить файл или сборку ' имя сборки плагинов ' или одну из ее зависимостей. Система не может найти указанный файл.

System.Reflection.RuntimeAssembly. MappingException: постоянный класс " имя сборки плагинов .Entities.class name, имя сборки плагинов не найдено

NHibernate.Cfg.XmlHbmBinding.Binder.ClassForFullNameChecked (строка fullName, строка errorMessage) MappingException: Не удалось скомпилировать документ сопоставления: имя сборки плагинов .Entities.class name.hbm.xml

NHibernate.Cfg.Configuration.LogAndThrow(Exception exception)

1 Ответ

0 голосов
/ 26 июня 2018

Предположим, что Plugin.Shop.dll находится в корневой папке плагина Plugin.Shop.Entities. Из свойства выберите тип контента в качестве встроенного ресурса и дайте ссылку на эту DLL и из свойства установите его False для копирования папки.

Это файл EmbeddedAssembly.cs

using System;
using System.Collections.Generic;
using System.IO;
using System.Reflection;
using System.Security.Cryptography;

namespace Plugin.Shop.Entities
{
    public class EmbeddedAssembly
    {
        // Version 1.0

        static Dictionary<string, Assembly> dic = null;

        public static void Load(string embeddedResource, string fileName)
        {
            if (dic == null)
                dic = new Dictionary<string, Assembly>();

            byte[] ba = null;
            Assembly asm = null;
            Assembly curAsm = Assembly.GetExecutingAssembly();

            using (Stream stm = curAsm.GetManifestResourceStream(embeddedResource))
            {
                // Either the file is not existed or it is not mark as embedded resource
                if (stm == null)
                    throw new Exception(embeddedResource + " is not found in Embedded Resources.");

                // Get byte[] from the file from embedded resource
                ba = new byte[(int)stm.Length];
                stm.Read(ba, 0, (int)stm.Length);
                try
                {
                    asm = Assembly.Load(ba);

                    // Add the assembly/dll into dictionary
                    dic.Add(asm.FullName, asm);
                    return;
                }
                catch
                {
                    // Purposely do nothing
                    // Unmanaged dll or assembly cannot be loaded directly from byte[]
                    // Let the process fall through for next part
                }
            }

            bool fileOk = false;
            string tempFile = "";

            using (SHA1CryptoServiceProvider sha1 = new SHA1CryptoServiceProvider())
            {
                string fileHash = BitConverter.ToString(sha1.ComputeHash(ba)).Replace("-", string.Empty); ;

                tempFile = Path.GetTempPath() + fileName;

                if (File.Exists(tempFile))
                {
                    byte[] bb = File.ReadAllBytes(tempFile);
                    string fileHash2 = BitConverter.ToString(sha1.ComputeHash(bb)).Replace("-", string.Empty);

                    if (fileHash == fileHash2)
                    {
                        fileOk = true;
                    }
                    else
                    {
                        fileOk = false;
                    }
                }
                else
                {
                    fileOk = false;
                }
            }

            if (!fileOk)
            {
                System.IO.File.WriteAllBytes(tempFile, ba);
            }

            asm = Assembly.LoadFile(tempFile);

            dic.Add(asm.FullName, asm);
        }

        public static Assembly Get(string assemblyFullName)
        {
            if (dic == null || dic.Count == 0)
                return null;

            if (dic.ContainsKey(assemblyFullName))
                return dic[assemblyFullName];

            return null;
        }
    }
}

Это файл регистра зависимостей

using Autofac;
using Autofac.Core;
using Nop.Core.Configuration;
using Nop.Core.Data;
using Nop.Core.Infrastructure;
using Nop.Core.Infrastructure.DependencyManagement;
using Nop.Data;
using Nop.Web.Framework.Mvc;
using System;
using System.Reflection;

namespace Plugin.Shop.Entities.Infrastructure
{
    /// <summary>
    /// Dependency registrar
    /// </summary>
    public class DependencyRegistrar : IDependencyRegistrar
    {       
        public virtual void Register(ContainerBuilder builder, ITypeFinder typeFinder, NopConfig config)
        {
            builder.RegisterType<NameService>().As<INameService>().InstancePerLifetimeScope();

            string codeDll = "Plugin.Shop.Entities.Plugin.Shop.dll";
            EmbeddedAssembly.Load(codeDll, "Plugin.Shop.dll");

            AppDomain.CurrentDomain.AssemblyResolve += CurrentDomain_AssemblyResolve;
        }

        private Assembly CurrentDomain_AssemblyResolve(object sender, ResolveEventArgs args)
        {
            return EmbeddedAssembly.Get(args.Name);
        }

        public int Order
        {
            get { return 1; }
        }
    }
}
...