首页 文章

帮助流畅的NHibernate映射通用类

提问于
浏览
2

我希望有人可以帮我解决这个问题,我正在尝试为一个被子类化为泛型类的类编写映射类 . 它更容易用代码描述,所以这是我的模型......

public abstract class TagBase
{
    public virtual int Id { get; private set; }
    public virtual TagTypeEnum TagType { get; set; }
    public virtual string Value { get; set; }
    public virtual bool IsSystemTag { get; private set; }
    public virtual bool isDeleted { get; set; }

    public TagBase()
    {
    }

    public TagBase(TagTypeEnum tagType)
    {
        this.TagType = tagType;
    }

    public override string ToString()
    {
        return Value;
    }
}

public class Tag<TLinkedItem> : TagBase where TLinkedItem : ITagged<TLinkedItem>
{
    public virtual List<TLinkedItem> LinkedItems { get; set; }
}

如您所见 Tag 是通用的,但仅限于那些实现 ITagged<T> 的类

这个想法是一个实体有标签,反过来一个标签有一个强类型的LinkedItem列表 .

标签不能在不同类型的实体之间共享

我的模型中只有两个支持标记的实体,因为它们是 DisplayAsset

我试图用以下Fluent NHibernate代码映射它;

public class TagBaseMap : ClassMap<TagBase>
{
    public TagBaseMap()
    {
        Table("Tag");
        Id(tag => tag.Id);
        Map(tag => tag.Value).Not.Nullable().Length(50);
        Map(tag => tag.IsSystemTag).Not.Nullable();
        Map(tag => tag.isDeleted).Not.Nullable();
        Map(tag => tag.TagType).CustomType<Int32>().Not.Nullable();
    }
}

public class DisplayTagMap : SubclassMap<Tag<Display>>
{
    public DisplayTagMap()
    {
        HasManyToMany(displayTag => displayTag.LinkedItems).Inverse().Table("DisplayTagLink");
    }
}

public class AssetTagMap : SubclassMap<Tag<Asset>>
{
    public AssetTagMap()
    {
        HasManyToMany(assetTag => assetTag.LinkedItems).Inverse().Table("AssetTagLink");
    }
}

当我尝试构建数据库时,我收到此错误 "Incorrect syntax near '`'."

我是否正确思考.Net的泛型类命名,即

'{[ Model.Tag'1 [[Model.Asset,Model,Version = 1.0.0.0,Culture = neutral,PublicKeyToken = null]] . LinkedItems,NHibernate.Mapping.Bag( Model.Tag'1 [[Model.Asset,Saturn.ConnectVision.Model,Version] = 1.0.0.0,Culture = neutral,PublicKeyToken = null]] . LinkedItems)]}'

我在这里做些蠢事吗?

有没有解决这个问题的方法?

提前感谢任何建议 .

1 回答

  • 1

    好吧,我好像现在已经解决了这个问题 .

    以下是Tag的通用版本的映射,其中T:ITagged

    public class DisplayTagMap : SubclassMap<Tag<Display>>
    {
        public DisplayTagMap()
        {
           HasManyToMany(displayTag => displayTag.LinkedItems).Inverse().Table("DisplayTagLink").ParentKeyColumn("display_id").ChildKeyColumn("tag_id");
        }
    }
    
    public class AssetTagMap : SubclassMap<Tag<Asset>>
    {
        public AssetTagMap()
        {
            HasManyToMany(assetTag => assetTag.LinkedItems).Inverse().Table("AssetTagLink").ParentKeyColumn("asset_id").ChildKeyColumn("tag_id");
        }
    }
    

    所以我重写了导致非法Sql语法的生成列名,当然还有需要考虑的反向映射 .

    public class DisplayMap : ClassMap<Display>
    {
        public DisplayMap()
        {
            Id(display => display.Id);
            Map(display => display.Name).Not.Nullable();
            Map(display => display.DisplayGUID).Not.Nullable();
            Map(display => display.Description);
            HasManyToMany(display => display.Tags).Cascade.All().Table("DisplayTagLink").ParentKeyColumn("display_id").ChildKeyColumn("tag_id");
        }
    }
    

    我现在唯一的问题是,如果我输入 DiscriminateSubclassesOnColumn("TagType") ,我会遇到相同的语法问题 .

    如果我错过了这个声明,我最终得到两个额外的表,Tag_Asset和Tag_Display只包含一个返回Tag的外键 . 现在这不是什么大问题 .

    我已经避免 DiscriminateSubClassOnColumn("TagType").SubClass<Tag<Display>>(..... 因为这将导致我必须为我添加的每个子类修改此声明 .

相关问题