在MSBuild(TFS)中使用Nhibernate.Bytecode.Castle出现问题

4
我们有一个Fluent NHibernate映射测试,在我们的本地机器上通过了,但当我们提交到TFS时,构建服务器上的测试失败了。我们正在使用MSTest。我们得到的错误是:
NHibernate.Bytecode.UnableToLoadProxyFactoryFactoryException:在配置代理工厂类期间无法加载类型“NHibernate.ByteCode.Castle.ProxyFactoryFactory,NHibernate.ByteCode.Castle”。 可能的原因是: - NHibernate.Bytecode提供程序程序集未部署。 - 用于初始化session-factory部分的“proxyfactory.factory_class”属性的typeName格式不正确。
解决方案: 确认您的部署文件夹包含以下程序集之一: NHibernate.ByteCode.LinFu.dll NHibernate.ByteCode.Castle.dll ---> System.IO.FileNotFoundException:无法加载文件或程序集“NHibernate.ByteCode.Castle”或其某个依赖项。系统找不到指定的文件。 WRN:已关闭程序集绑定日志记录。 要启用程序集绑定失败日志记录,请将注册表值[HKLM \ Software \ Microsoft \ Fusion!EnableLog](DWORD)设置为1。 注意:与程序集绑定失败日志记录相关联的某些性能损失。 要关闭此功能,请删除注册表值[HKLM \ Software \ Microsoft \ Fusion!EnableLog]。
我们已经检查了删除文件夹,NHibernate.Bytecode.Castle.dll在那里。我们有对Castle.Core,Castle.DynamicProxy2,Iesi.Collections,log4net,NHibernate和NHibernate.ByteCode.Castle的dll和引用。我们已经通过在删除文件夹中的命令提示符下使用MSBuild运行了测试,错误仍然发生。我们的流畅映射如下(NHibernateConfig.MappingConfiguration()调用实际映射,自动映射):
Fluently.Configure() .Database(SQLiteConfiguration.Standard.ShowSql().InMemory()) .Mappings(NHibernateConfig.MappingConfiguration()) .BuildConfiguration();
为什么会这样?

你是否已经添加了对NHibernate.ByteCode.LinFu.dll和NHibernate.ByteCode.Castle.dll的引用? - Burt
我们没有使用LinFu。我已经在帖子中更新了所有的参考资料。 - JontyMC
7个回答

11

如果我记得字节码程序集是如何工作,那么你实际上并没有对它们进行有用的引用。也就是说,在代码中你没有特别使用它们的任何一个类。因此,“智能”引用复制导致这些不被引入。(我可能是在胡说八道,抱歉)。

为了解决这个问题,你可以:a) 将相应的字节码程序集设置为始终复制内容引用(一般)或b)创建一个愚蠢的小类(私有静态),引用实际字节码程序集中的任何一个单一类(一般+1)。

我确信还有另一种方法可以强制执行引用,但这两种应该是最简单的、20秒钟的解决方案。


谢谢,使用静态类起作用了。不过这似乎有点像黑客技巧。我尝试使用testrunconfig来拉取dll,但是我无法让它工作。 - JontyMC
1
很好。混淆是因为VS用于解析引用的MSBuild任务比Team Build更懒惰。就个人而言,我还没有研究过如何调和这两者之间的差异。 - Ryan Cromwell
1
将 NHibernate.Bytecode.Castle 的引用设置为“复制本地”对我有帮助。 - Stelloy

6

我曾经遇到了同样的问题,不得不在执行Fluently.Configure的类中添加引用。

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using NHibernate;
using FluentNHibernate.Cfg;
using FluentNHibernate.Automapping;
using FluentNHibernate.Conventions.Helpers;
using FluentNHibernate.Conventions;
using FluentNHibernate.Conventions.AcceptanceCriteria;
using FluentNHibernate.Conventions.Inspections;
using FluentNHibernate.Conventions.Instances;
using FluentNHibernate.MappingModel;
using FluentNHibernate;
**using NHibernate.ByteCode.Castle;**

namespace CESP_NotifyLib
{
    class SessionFactoryController
    {

        public SessionFactoryController()
        {

        }

        public ISessionFactory GiveFactory()
        {
            return CreateSessionFactory();
        }

        **private static void ReferByteCode(){

            //Just to make sure the ByteCodeCastle is loaded
            ProxyFactory fake = new ProxyFactory();
        }**

        private static ISessionFactory CreateSessionFactory()
        {
            ReferByteCode();

            var cfg = new NotifyFluentNhibernateConfiguration();

            return Fluently.Configure()
              .Database(
               FluentNHibernate.Cfg.Db.MsSqlConfiguration.MsSql2005
                    .ConnectionString("Server=[MYSERVERIPADRESS]\\DBSERVER;Database=NotifyTest;User ID=NHibernateTester;Password=[MYPASSWORD];Trusted_Connection=False;")
              )

              .Mappings(m => {
                  m.AutoMappings
                    .Add(AutoMap.AssemblyOf<SubscriptionManagerRP>(cfg));

              } )

              .BuildSessionFactory();
        }



    }
}

3

一些有用的提示。

您可以在测试类上放置DeploymentItem属性。这将复制所需的DLL。您还需要在项目引用中引用这些DLL。

    [TestClass]
[DeploymentItem("NHibernate.ByteCode.LinFu.dll")]
[DeploymentItem("NHibernate.ByteCode.LinFu.xml")]
public class Accounts

您可以通过比较/[myapp]/bin/debug文件夹和/TestResults/[TestRunDate]文件夹来找到缺失的DLL文件。我使用的是VS 2012,这是针对MSTest的。

2

来自 Fluent NHibernate wiki

在 CreateSessionFactory 中缺少 ProxyFactory 的配置。由于问题 154 不会被修复,需要在数据库配置调用中添加以下一行:

.ProxyFactoryFactory("NHibernate.ByteCode.Castle.ProxyFactoryFactory, NHibernate.ByteCode.Castle"), 我的配置如下:

return Fluently.Configure()
    .Database(SQLiteConfiguration.Standard.UsingFile("firstProject.db")
    .ProxyFactoryFactory("NHibernate.ByteCode.Castle.ProxyFactoryFactory, NHibernate.ByteCode.Castle"))

2
添加对NHibernate.ByteCode.Castle.dll的引用,解决了我的问题。

1

实际上,“ReferByteCode”方法是必需的,仅有引用是不够的。这是一个值得麦克盖文尝试的技巧,但它确实有效。


0
如果你遇到这个问题,我建议你下载另一个Castle的包。在我的情况下,问题是我下载的包中没有实现接口(IProxyFactory或类似的东西),所以我删除了NHibernate.ByteCode.Castle和NHibernate.ByteCode.Search,并安装了NHibarnate.Castle包,解决了我一整天的问题。 我正在使用NuGet包管理器!
还记得Fusion Log是你的好朋友!

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接