NHibernate 3.2 自带了代码映射机制, 作为 xml 映射之外的一种映射方式, 由于推出的时间比较晚, 所以资料相对比较少, 而且与社区版的 Fluent Mapping 和 Attribute Mapping 不同, 有其独特的设计风格。
下面就通过一个实例来说明怎么使用 NHibernate 自带的代码映射。
要映射的类关系图如下:
上图中有三个实体类, 他们之间的关系说明如下:
Product
与 Store
之间是多对多关系;Store
与 Employee
之间是一对多关系;Employee
与 Store
之间是多对一关系;使用 xml 做实体类映射时, 推荐一个实体类对应一个 xml 文件, 用代码映射时也推荐这样, 一个实体类对应一个映射类, 一个映射类一个文件。
映射类继承自 ClassMapping<T>
, T
标识要映射的实体类, 如下所示:
public class ProductMapping : ClassMapping<Product> {
public ProductMapping() {
// 此处添加映射代码
}
}
使用 Table
函数将类映射到制定的数据表:
Table("product");
使用 Id
函数映射标识, NHibernate 提供了内置的工具类来简化代码:
Id(
m => m.Id,
map => {
map.Column("id");
map.Type(NHibernateUtil.Int32);
map.Generator(Generators.Identity);
}
);
使用 Property
函数映射属性, NHibernate 提供了内置的工具类来简化代码:
Property(
m => m.Name,
map => {
map.Column("name");
map.Type(NHibernateUtil.String);
map.Length(20);
}
);
使用 ManyToOne
函数来映射多对一属性, 比如 Employee
的 Store
属性:
ManyToOne(
m => m.Store,
map => {
map.Class(typeof(Store));
map.Cascade(Cascade.All);
map.Column("store_id");
map.ForeignKey("employee_to_store");
}
);
使用 Bag
方法来映射一对多属性, 比如 Store
的 Staff
属性:
Bag(
m => m.Staff,
map => {
map.Table("employee");
map.Key(k => {
k.Column("store_id");
k.ForeignKey("employee_to_store");
});
},
rel => {
rel.OneToMany(map => map.Class(typeof(Employee)));
}
);
Store
与 Product
两个类之间是多对多映射, 映射代码如下:
Store
类的 Products
属性:
Bag(
m => m.Products,
map => {
map.Table("store_product");
map.Key(k => {
k.Column("store_id");
k.ForeignKey("store_product_to_store");
});
},
rel => rel.ManyToMany(map => {
map.Class(typeof(Product));
map.Column("product_id");
})
);
Product
类的 StoresStockedIn
属性:
Bag(
m => m.StoresStockedIn,
map => {
map.Table("store_product");
map.Key(k => {
k.Column("product_id");
k.ForeignKey("store_product_to_product");
});
},
rel => rel.ManyToMany(map => {
map.Class(typeof(Store));
map.Column("store_id");
})
);
通过下面的代码将上面的映射添加到配置:
var config = new Configuration();
config.Configure("MySql.cfg.xml");
var mapper = new ConventionModelMapper();
mapper.AddMapping(new EmployeeMapping());
mapper.AddMapping(new StoreMapping());
mapper.AddMapping(new ProductMapping());
var mapping = mapper.CompileMappingForAllExplicitlyAddedEntities();
config.AddMapping(mapping);
也可以向 xml 映射那样, 将映射导出到数据库, 创建对应的数据表以及表关系:
var schemaExport = new SchemaExport(config);
schemaExport.SetDelimiter(";");
schemaExport.Execute(true, true, false);
与 xml 映射以及其它第三方映射相比, 使用 NHibernate 代码映射有下面几个优点: