我正在尝试重用现有的映射并以各种方式扩展它们。
假设你有这张表:
create table entity (
id int identity(1,1) not null,
a varchar(max) not null,
b int not null,
c int not null
constraint pk_entity primary key clustered (id asc))
这些实体:
public class Entity
{
public virtual int ID { get; set; }
public virtual string A { get; set; }
public override string ToString()
{
return string.Format("{{{0} {1}: {2}}}", GetType().Name, ID, A);
}
}
public class EntityExt1 : Entity
{
public virtual int B { get; set; }
public override string ToString()
{
return string.Format("{{{0} {1}: {2} {3}}}", GetType().Name, ID, A, B);
}
}
public class EntityExt2 : Entity
{
public virtual int C { get; set; }
public override string ToString()
{
return string.Format("{{{0} {1}: {2} {3}}}", GetType().Name, ID, A, C);
}
}
这是映射:
<hibernate-mapping xmlns="urn:nhibernate-mapping-2.2"
assembly="FunWithNHibernateSubclassMappings"
namespace="FunWithNHibernateSubclassMappings">
<class name="Entity" table="entity">
<id name="ID" column="id">
<generator class="identity" />
</id>
<property name="A" column="a" type="string" />
</class>
</hibernate-mapping>
这是进行测试的程序:
using System;
using System.Linq;
using System.Reflection;
using NHibernate.ByteCode.LinFu; // NuGet console: install-package NHibernate.LinFu
using NHibernate.Cfg;
using NHibernate.Cfg.Loquacious;
using NHibernate.Dialect;
using NHibernate.Linq;
using NHibernate;
namespace FunWithNHibernateSubclassMappings
{
public class Program
{
static string CONNSTRING = "Data Source=127.0.0.1;Initial Catalog=testdb;User Id=developer;Password=secret";
static ISession OpenSession(string connectionString)
{
Configuration config = (new Configuration())
.DataBaseIntegration(x =>
{
x.Dialect<MsSql2008Dialect>();
x.ConnectionString = connectionString;
x.LogFormatedSql = true;
x.LogSqlInConsole = true;
})
.Proxy(x =>
{
x.ProxyFactoryFactory<ProxyFactoryFactory>();
})
.AddAssembly(Assembly.GetExecutingAssembly());
ISessionFactory sessionFactory = config.BuildSessionFactory();
return sessionFactory.OpenSession();
}
static void Main(string[] args)
{
ISession session = OpenSession(CONNSTRING);
Console.WriteLine("Query 1:");
session.Query<Entity>()
.Where(j => j.A == "Albatross")
.ToList()
.ForEach(Console.WriteLine);
Console.WriteLine("Query 2:");
session.Query<EntityExt>()
.Where(j => j.A == "Albatross")
.ToList()
.ForEach(Console.WriteLine);
Console.WriteLine();
Console.WriteLine("That's all, folks!");
Console.ReadLine();
}
}
}
然后,实体的映射可以包含各种有用的知识,例如如何映射到其他表。 EntityExt1和EntityExt2实体和映射将受益于能够使用该知识,因为它们不需要重复什么是主键,什么是基本属性以及与其他实体的关系。
让每个开发人员只更改Entity的现有映射并不好,因为向另一个实体添加关系可能会改变现有代码的行为,从而增加测试人员的负担。
有没有办法用NHibernate做到这一点?