我有一个预先存在的表,使用一种开放的模式。我有一个Item表,各种实体被归类为Items,然后将属性存储在Item属性表中。单个实体类型可以具有存储在多个表中的字段。我们使用视图公开实体。因此,大多数实体对应一个视图,然后当我们插入/更新时,我们必须系统地更新表或使用存储过程。
我正在尝试确定NHibernate是否会通过我们定制的存储库(遵循工厂模式)获得任何东西。现在,我发现让NHibernate处理这种数据库模式非常困难。我看待它的方式,我们要么必须完全重构我们的数据库以遵循NHibernate的约定,要么以某种方式完全重构或实体。
我没有在文档中看到有关如何执行此操作的内容,除了涉及数据库的最简单的示例,这些示例或多或少遵循NHibernate的约定。
这是一个有代表性的数据库图表。我们将Episode作为一个实体,从Item,IP_Episode,IP_EpisodeBroadcastInfo,IP_Show等中提取信息,以构建所需的所有字段。
答案 0 :(得分:1)
你提到了约定。这是一个流畅的NHibernate概念,是的,你所做的并不完全符合Fluent NHibernate的现有惯例。但是,它完全符合NHibernate的功能。 NHibernate擅长映射到各种不同的数据库模式。不要被Fluent NHibernate希望你去的方式所束缚。我不是说不要使用Fluent NHibernate。如果数据库模式中的一致且合理,则可以编写自己的约定来匹配。
为了说明NHibernate的灵活性,让我们假设我们有一个类似于此的表结构:
create table Episode (
Id int not null primary key,
NumberInSeries int null
);
create table Show (
Episode_id int not null primary key,
Title nvarchar(100) not null,
foreign key (Episode_id) references Episode (Id)
);
create table Broadcast (
Episode_id int not null primary key,
InitialAirDate datetime not null,
foreign key (Episode_id) references Episode (Id)
);
Episode
中的一行对应Show
中的零行或一行以及Broadcast
中的零行或一行。您可以在.NET中以几种不同的方式为这种类型的关系建模。以下是NHibernate提供的各种选项:
public class Episode
{
public virtual int Id { get; set; }
public virtual int? NumberInSeries { get; set; }
}
public class Show : Episode
{
public virtual string Title { get; set; }
}
public class Broadcast : Episode
{
public virtual DateTime InitialAirDate { get; set; }
}
如果要为不会更改的关系建模,请使用此选项。如果剧集是一个节目,它总是一个节目。此外,这种建模意味着剧集不能同时是节目和广播。我不相信这是你想要的,但你可能会发现它在你的模型的其他地方很有用。
有关详细信息,请参阅...
one-to-one
public class Episode
{
public virtual int Id { get; set; }
public virtual int? NumberInSeries { get; set; }
public virtual Show Show { get; set; }
public virtual Broadcast Broadcast { get; set; }
}
public class Show
{
public virtual Episode Episode { get; set; }
public virtual string Title { get; set; }
}
public class Broadcast
{
public virtual Episode Episode { get; set; }
public virtual DateTime InitialAirDate { get; set; }
}
这使您可以更好地控制哪些表实际包含与给定剧集关联的行,因为您可以设置episode.Broadcast = null
。对于给定的剧集,同时显示和播放信息也很好。
有关详细信息,请参阅...
join
public class Episode
{
// These properties come from the Episode table...
public virtual int Id { get; set; }
public virtual int? NumberInSeries { get; set; }
// This one comes from the Show table.
public virtual string Title { get; set; }
// This one comes from the Broadcast table.
public virtual DateTime InitialAirDate { get; set; }
}
这是一种表示数据的简单方法,但您无法控制是否将行插入到Show和Broadcast表中。
有关详细信息,请参阅...
既然你说过“单个实体类型可能在多个表中存储了字段”,我觉得join
应该能够处理你当前建模的方式。