NHibernate SQL创建会导致错误

时间:2009-05-07 06:32:46

标签: c# nhibernate

我有2个名为Order和Orderrow的类。我使用NHibernate来加入它。

当运行NUnit来测试查询时,我得到了一个ADOException:

Logica.NHibernate.Tests.NHibernateTest.SelectAllOrdersFromSupplierNamedKnorrTest:
NHibernate.ADOException : could not execute query
[ SELECT this_.OrderId as OrderId1_1_, this_.CreatedAt as CreatedAt1_1_, this_.ShippedAt as ShippedAt1_1_, this_.ContactId as ContactId1_1_, customer2_.ContactId as ContactId0_0_, customer2_.LastName as LastName0_0_, customer2_.Initials as Initials0_0_, customer2_.Address as Address0_0_, customer2_.City as City0_0_, customer2_.Country as Country0_0_ FROM Order this_ inner join Contact customer2_ on this_.ContactId=customer2_.ContactId ]
[SQL: SELECT this_.OrderId as OrderId1_1_, this_.CreatedAt as CreatedAt1_1_, this_.ShippedAt as ShippedAt1_1_, this_.ContactId as ContactId1_1_, customer2_.ContactId as ContactId0_0_, customer2_.LastName as LastName0_0_, customer2_.Initials as Initials0_0_, customer2_.Address as Address0_0_, customer2_.City as City0_0_, customer2_.Country as Country0_0_ FROM Order this_ inner join Contact customer2_ on this_.ContactId=customer2_.ContactId]
  ----> System.Data.SqlClient.SqlException : Incorrect syntax near the keyword 'Order'.

在分析由NHibernate创建的SQL时,我注意到Order类正在破坏SQL语句,因为ORDER BY是SQL中的内部关键字。

这是NHibernate中创建的SQL:

SELECT this_.OrderId as OrderId1_1_, this_.CreatedAt as CreatedAt1_1_, this_.ShippedAt as ShippedAt1_1_, this_.ContactId as ContactId1_1_, customer2_.ContactId as ContactId0_0_, customer2_.LastName as LastName0_0_, customer2_.Initials as Initials0_0_, customer2_.Address as Address0_0_, customer2_.City as City0_0_, customer2_.Country as Country0_0_ FROM Order this_ inner join Contact customer2_ on this_.ContactId=customer2_.ContactId

我在SQL Server 2008管理工作室中对此进行了更改,如下所示:

SELECT this_.OrderId as OrderId1_1_, this_.CreatedAt as CreatedAt1_1_, this_.ShippedAt as ShippedAt1_1_, this_.ContactId as ContactId1_1_, customer2_.ContactId as ContactId0_0_, customer2_.LastName as LastName0_0_, customer2_.Initials as Initials0_0_, customer2_.Address as Address0_0_, customer2_.City as City0_0_, customer2_.Country as Country0_0_ FROM [Order] this_ inner join Contact customer2_ on this_.ContactId=customer2_.ContactId`

我在表名称Order中加了括号(就像这样:[Order])并且它是固定的。

但是如何在NHibernate中修复此问题呢?是否有映射XML文件指令才能完成此操作?

(使用VS2008 SP1,SQL Server 2008 SP1,NHibernate 2.0.1 GA)

4 个答案:

答案 0 :(得分:6)

参见this,“5.3.SQL引用标识符”部分。你基本上需要这个:

<class name="Order" table="`Order`">

答案 1 :(得分:6)

我认为如果你在映射文件中放置引号(“[”和“]”在SQL Server中,或者你的数据库支持的任何引号),hibernate会在生成查询时引用对象名称。

(也许发布您的地图文件,我们可以看看)

答案 2 :(得分:5)

在Fluent NHibernate中,添加

.Column("`Order`");

到您的映射以修复此错误。

答案 3 :(得分:0)

使用约定时,您可以添加以下内容:

public class TableNameConvention
    : IClassConvention, IClassConventionAcceptance
{
    public void Accept(IAcceptanceCriteria<IClassInspector> criteria)
    {
        criteria.Expect(x => Check(x));
    }

    private bool Check(IClassInspector x)
    {
        return String.IsNullOrWhiteSpace(x.TableName) || x.TableName.Equals("`{0}`".Args(x.EntityType.Name));
    }

    public void Apply(IClassInstance instance)
    {
        instance.Table("`" + instance.EntityType.Name + "`");
    }
}

要修复保留表名称和保留列名称(例如“From”)的问题,可以使用以下内容:

public class ColumnNameConvention : IPropertyConvention, IPropertyConventionAcceptance
{
    public void Apply(IPropertyInstance instance)
    {
        instance.Column("`" + instance.Property.Name + "`");
    }

    public void Accept(IAcceptanceCriteria<IPropertyInspector> criteria)
    {
        criteria.Expect(c => Check(c));
    }

    private bool Check(IPropertyInspector inspector)
    {
        //walkaround:
        //this convention causes problems with Components - creates columns like Issue`Id` so we apply it only to entities

        var type = inspector.EntityType;
        if (!(type.IsSubclassOf(typeof (Entity)) || type.IsSubclassOf(typeof (GlossaryEntity))))
        {
            return false;
        }

        return true;
    }
}
相关问题