简体   繁体   English

NHibernate 3 Linq和IUserType

[英]NHibernate 3 Linq and IUserType

I have a table: 我有一张桌子:

Page (
   Id int,
   Name nvarchar(50),
   TemplateName varchar(50)
   ...
)

and it's mapped to domain model: 并映射到域模型:

public class Page {
   public virtual int Id { get; set; }
   public virtual string Name { get; set; }
   public virtual Template Template { get; set; }
}

Note that in the domain model, "Template" property is not of type "string". 请注意,在域模型中,“模板”属性的类型不是“字符串”。 The Template class is like this: Template类是这样的:

public class Template {
   public string Name { get; set; }
   // other properties...
}

"Templates" are loaded from file system. “模板”是从文件系统加载的。 I have a TemplateManager class: 我有一个TemplateManager类:

public class TemplateManager {
    public static Template LoadTemplate(string templateName) {
        // check if there's a folder named <templateName>
    }
}

I can use IUserType to map the "Template" property. 我可以使用IUserType来映射“ Template”属性。

public class PageMap : ClassMapping<Page> {
    public PageMap() {
        ...
        Property(c => c.Template, m => {
             m.Column("TemplateName");
             m.Type<TemplateUserType>();
        }
    }
}

public class TemplateUserType : IUserType {
    public object NullSafeGet(System.Data.IDataReader rs, string[] names, object owner)
    {
        var templateName = rs[names[0]].AsString();

        if (!String.IsNullOrEmpty(templateName))
        {
            return TemplateManager.LoadTemplate(templateName);
        }

        return null;
    }
}

Okay, so far so good. 好的,到目前为止很好。 But the problem is, how can I use Template property in Linq queries? 但是问题是,如何在Linq查询中使用Template属性? For exmaple: 例如:

var pages = session.Query<Page>().Where(it => it.Template.Name == "MyTemplate");

I think the solution might be to write a class (say TemplatePropertyHqlGenerator) implementing IHqlGeneratorForProperty . 我认为解决方案可能是编写一个实现IHqlGeneratorForProperty的类(例如TemplatePropertyHqlGenerator)。 This is the linq query extension point provided by NHibernate 3. But how to write this TemplatePropertyHqlGenerator class? 这是NHibernate 3提供的linq查询扩展点。 但是如何编写这个TemplatePropertyHqlGenerator类呢?

Thanks in advanced! 提前致谢!

The IUserType interface lets you define a type which is considered atomic. IUserType接口使您可以定义被视为原子的类型。 That is to say, you can then perform direct comparisons between instances of the type and NHibernate will know how to translate them. 也就是说,您可以在类型实例之间进行直接比较,NHibernate将知道如何转换它们。

Eg the following query would evaluate: 例如,以下查询将评估:

var template = new Template();
session.Query<Page>().Where(it => it.Template == template);

If you want to define a type which has component values which you can then manipulate, you need to implement the ICompositeUserType interface. 如果要定义具有可随后处理的组件值的类型,则需要实现ICompositeUserType接口。 This interface requires you define the properties of the type as atomic elements, giving NHibernate the information it needs to understand the specific properties of the type. 该接口要求您将类型的属性定义为原子元素,从而为NHibernate提供了解类型的特定属性所需的信息。

As a result, it's a little more complex than IUserType to implement, but it should facilitate what you want to achieve. 结果,它实现起来比IUserType复杂一点,但是它应该可以简化您想要实现的目标。

Here's an understandable example of implementing the interface for a Money type: http://geekswithblogs.net/opiesblog/archive/2006/08/05/87218.aspx 这是为Money类型实现接口的一个可理解的示例: http : //geekswithblogs.net/opiesblog/archive/2006/08/05/87218.aspx

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM