首页 > NHibernate Step by Step (一) 转载

NHibernate Step by Step (一) 转载

转载于http://abluedog.cnblogs.com/archive/2006/04/15/375862.html

基本的软件环境如下:

1.NHibernate http://www.nhibernate.org/ 

2.Code Smith http://www.codesmithtools.com/

3.NHibernate模板 点击这里下载

当然,少不了VS2005跟SQLServer了,我这里用的是SQLServer2005,教程用在SQLServer2000上应该没有问题,默认情况下,我将建立并使用一个叫NHibernate的数据库。

首先,我们先建立一个最简单的Person表,如下完整脚本(你可以进行修改以适合自己的数据库):

 

USE [NHibernate]

GO

SET ANSI_NULLS ON

GO

SET QUOTED_IDENTIFIER ON

GO

SET ANSI_PADDING ON

GO

CREATE TABLE [dbo].[Person](

    [id] [
int] IDENTITY(1,1) NOT NULL,

    [name] [varchar](
50) COLLATE Chinese_PRC_CI_AS NOT NULL,

 CONSTRAINT [PK_Person] PRIMARY KEY CLUSTERED 

(

    [id] ASC

)WITH (IGNORE_DUP_KEY 
= OFF) ON [PRIMARY]

) ON [PRIMARY]



GO

SET ANSI_PADDING OFF

 

仅有两个字段,一个自动增长的id,一个name,如下:



 

然后将下载的nhibernate-template解压,打开Code Smith,将模板加入”Template Explorer”,如下:



 

然后在其中的NHibernate.cst上点右键,选择“Execute”,弹出设置窗口,在左边的属性窗口进行如下设置:



 

注意:SourceDatabase属性在第一次选择时需要配置一个连接字符串,配置好后Code Smith将记录下来。 Assembly属性代表的是生成文件的默认Assembly名,而NameSpace,顾名思义,就是使用的命名空间了,这里我们全部使用”Test.Model”,请记住这个名字,点击左下角的Generate,将会在指定的输出目录下产生两个文件:Person.cs,Person.hbm.xml。

好了,NHibernate需要的类文件和映射文件生成完了,我们可以开始干活了!(生成NHibernate文件均是如此步骤,以后不再赘述)

新建立一个类库工程,为了简洁起见,我们命名为Model,需要注意的是,为了跟刚才生成的文件对应,我们需要在Model工程的属性页中将起Assembly名字设为上面的“Test.Model”,如下:



 

然后将刚才生成的两个文件Person.cs和Person.hbm.xml加入到Model工程中来,选中Person.hbm.xml文件,在属性窗口中将其“Build Action”设置为“Embedded Resource”(这是非常重要的一步,否则NHibernate将无法找到映射文件),如下:

 

build,ok,通过。

然后建立一个控制台工程,命名为Console1,添加NHibernate和上面Model项目的引用,另外添加一个应用程序配置文件,如下:

 

xml version="1.0" encoding="utf-8" ?>

<configuration>

  
<configSections>

    
<section name="nhibernate" type="System.Configuration.NameValueSectionHandler, System,

                    Version=1.0.5000.0,Culture=neutral, PublicKeyToken=b77a5c561934e089"
 />

  
configSections>



  
<nhibernate>

    
<add key="hibernate.connection.provider" value="NHibernate.Connection.DriverConnectionProvider" />

    
<add key="hibernate.connection.driver_class" value="NHibernate.Driver.SqlClientDriver" />

    
<add key="hibernate.connection.connection_string" value="Server=localhost;Initial Catalog=NHibernate;Integrated Security=SSPI" />

    
<add key="hibernate.connection.isolation" value="ReadCommitted"/>

    
<add key="hibernate.dialect" value="NHibernate.Dialect.MsSql2000Dialect" />

  
nhibernate>



configuration>

 

请注意这里,这是引入NHibernate1.0的配置文件.如下引用是NHibernate2.0应该用如下配置

NHibernate2.0配置如下: 

 

<configuration>

  


  
<configSections>

    
<section name="hibernate-configuration" type="NHibernate.Cfg.ConfigurationSectionHandler, NHibernate" />

  
configSections>

  


  
<hibernate-configuration xmlns="urn:nhibernate-configuration-2.2">

    
<session-factory>

      
<property name="dialect">NHibernate.Dialect.MsSql2000Dialectproperty>

      
<property name="connection.provider">NHibernate.Connection.DriverConnectionProviderproperty>

      
<property name="connection.connection_string">Server=BOCO-TerryDATA;initial catalog=NHibernate;Integrated Security=trueproperty>

    
session-factory>

  
hibernate-configuration>

  


  
<system.web>

  
system.web>

configuration>

 



然后编写如下代码:

 

using System;

using System.Collections.Generic;

using System.Text;

using NHibernate;

using NHibernate.Cfg;

using Test.Model;



namespace Console1

ExpandedBlockStart.gifContractedBlock.gif
{

    
class Program

ExpandedSubBlockStart.gifContractedSubBlock.gif    
{

        
static void Main(string[] args)

ExpandedSubBlockStart.gifContractedSubBlock.gif        
{

            Configuration config 
= new Configuration().AddAssembly("Test.Model");

            ISessionFactory factory 
= config.BuildSessionFactory();

            ISession session 
= factory.OpenSession();



            Person person 
= new Person();

            person.Name 
= "Jackie Chan";



            ITransaction trans 
= session.BeginTransaction();

            
try

ExpandedSubBlockStart.gifContractedSubBlock.gif            
{

                session.Save(person);

                trans.Commit();

                Console.WriteLine(
"Insert Success!");

            }


            
catch (Exception ex)

ExpandedSubBlockStart.gifContractedSubBlock.gif            
{

                trans.Rollback();

                Console.WriteLine(ex.Message);

            }


        }


    }


}


 



运行,ok,执行成功!!

我们到数据库检查一下,如下:



 

我们想要添加的记录已经成功加入到数据库中!!

是不是感觉有些神奇啊?好,我们开始详细解释。

先来看生成的两个文件,第一个是Person.cs,如下:

 

using System;

using System.Collections;



namespace Test.Model

ExpandedBlockStart.gifContractedBlock.gif
{

ContractedSubBlock.gifExpandedSubBlockStart.gif    
Person#region Person



ExpandedSubBlockStart.gifContractedSubBlock.gif    
/**//// 

    
/// Person object for NHibernate mapped table 'Person'.

    
/// 


    public class Person

ExpandedSubBlockStart.gifContractedSubBlock.gif    
{

ContractedSubBlock.gifExpandedSubBlockStart.gif        
Member Variables#region Member Variables

        

        
protected int _id;

        
protected string _name;



        
#endregion




ContractedSubBlock.gifExpandedSubBlockStart.gif        
Constructors#region Constructors



ExpandedSubBlockStart.gifContractedSubBlock.gif        
public Person() { }



        
public Person( string name )

ExpandedSubBlockStart.gifContractedSubBlock.gif        
{

            
this._name = name;

        }




        
#endregion




ContractedSubBlock.gifExpandedSubBlockStart.gif        
Public Properties#region Public Properties



        
public int Id

ExpandedSubBlockStart.gifContractedSubBlock.gif        
{

ExpandedSubBlockStart.gifContractedSubBlock.gif            
get { return _id;}

ExpandedSubBlockStart.gifContractedSubBlock.gif            
set {_id = value;}

        }




        
public string Name

ExpandedSubBlockStart.gifContractedSubBlock.gif        
{

ExpandedSubBlockStart.gifContractedSubBlock.gif            
get return _name; }

            
set

ExpandedSubBlockStart.gifContractedSubBlock.gif            
{

                
if ( value != null && value.Length > 50)

                    
throw new ArgumentOutOfRangeException("Invalid value for Name", value, value.ToString());

                _name 
= value;

            }


        }




        



        
#endregion


    }


    
#endregion


}


 



你可以发现,这完全是一个普通的poco类(Plain Old CLR Object),仅仅是对数据库person表的一个完全映射,不依赖于任何框架,可以用来作为持久化类,你可以在任何地方使用而不用担心依赖于某些神秘的运行时东西。



另外,NHibernate需要知道怎样去加载(load)和存储(store)持久化类的对象。这正是NHibernate映射文件发挥作用的地方。映射文件告诉NHibernate它应该访问数据库(database)里面的哪个表(table)及应该使用表里面的哪些字段(column),这就是我们今天要讲的重点了,Person.hbm.xml,如下:

 

xml version="1.0" encoding="utf-8" ?>

<hibernate-mapping xmlns="urn:nhibernate-mapping-2.0">

 
<class name="Test.Model.Person, Test.Model" table="Person">

  
<id name="Id" type="Int32" unsaved-value="0">

   
<column name="id" sql-type="int" not-null="true" unique="true" index="PK_Person"/>

   
<generator class="native" />

  
id>

  
<property name="Name" type="String">

   
<column name="name" length="50" sql-type="varchar" not-null="true"/>

  
property>

 
class>

hibernate-mapping>

 



不用说,最顶层的hibernate-mapping节点是NHibernate用来进行映射的根了,其中,包含一个class节点,里面的name属性对应我们的Person类,注意,需要完整的限定名;而table属性,则显而易见是对应数据库中的Person表了。

我们再往里面看,分别有两个节点,一个是id,对应数据库中的id,一个是属性name,对应表中的column name和Person类中的name属性,整个映射文件简捷明了,一看即知。实际上这是由代码产生工具产生的映射文件,里面很多东西我们其实可以省略,如下写法:



NHibernate将自动去匹配数据库中的列而不需要我们来设置。

下面,我们来看一下应用程序配置文件中都记录了那些东西,如下:

hibernate.connection.provider_class  

定制IConnectionProvider的类型.

例如:full.classname.of.ConnectionProvider (如果提供者创建在NHibernate中), 或者 full.classname.of.ConnectionProvider, assembly (如果使用一个自定义的IConnectionProvider接口的实现,它不属于NHibernate)。

 

hibernate.connection.driver_class  

定制IDriver的类型.

full.classname.of.Driver (如果驱动类创建在NHibernate中), 或者 full.classname.of.Driver, assembly (如果使用一个自定义IDriver接口的实现,它不属于NHibernate)。



hibernate.connection.connection_string  

用来获得连接的连接字符串.



hibernate.connection.isolation  

设置事务隔离级别. 请检查 System.Data.IsolationLevel 来得到取值的具体意义并且查看数据库文档以确保级别是被支持的。

例如: Chaos, ReadCommitted, ReadUncommitted, RepeatableRead, Serializable, Unspecified



hibernate.dialect 

NHibernate方言(Dialect)的类名 - 可以让NHibernate使用某些特定的数据库平台的特性

例如: full.classname.of.Dialect(如果方言创建在NHibernate中), 或者full.classname.of.Dialect, assembly (如果使用一个自定义的方言的实现,它不属于NHibernate)。



接着,我们开始解释代码的执行,如下:

 

 

 

Configuration config = new Configuration().AddAssembly("Test.Model");



//通过配置对象来产生一个SessionFactory对象,这是一个Session工厂,

//那么Session是用来干什么的呢?一个Session就是由NHibernate封装

//的工作单元,我们可以近似地认为它起到ADO.Net中Connection的作用。

ISessionFactory factory = config.BuildSessionFactory();

ISession session 
= factory.OpenSession();



Person person 
= new Person();

person.Name 
= "Jackie Chan";



//这里,开启一个由NHibernate封装的事务,当然,在这里最终代表

//的还是一个真实的数据库事务,但是我们已经不需要再区分到底是

//一个SqlTransaction还是一个ODBCTransaction了

ITransaction trans = session.BeginTransaction();

try

ExpandedBlockStart.gifContractedBlock.gif
{

    
//保存,提交,就这么简单!!

         session.Save(person);

        trans.Commit();

        Console.WriteLine(
"Insert Success!");

}


catch (Exception ex)

ExpandedBlockStart.gifContractedBlock.gif
{

        trans.Rollback();

        Console.WriteLine(ex.Message);

}


 

更多相关:

  • 引言 在这个-SLAM建图和导航仿真实例-项目中,主要分为三个部分,分别是 (一)模型构建(二)根据已知地图进行定位和导航(三)使用RTAB-MAP进行建图和导航 该项目的slam_bot已经上传我的Github。 这是第三部分,完成效果如下 图1 建图和导航 三、使用RTAB-Map进行建图和导航 1. rtab...

  • 引言 在这个-SLAM建图和导航仿真实例-项目中,主要分为三个部分,分别是 (一)模型构建(二)根据已知地图进行定位和导航(三)使用RTAB-MAP进行建图和导航 该项目的slam_bot已经上传我的Github。 由于之前的虚拟机性能限制,我在这个项目中使用了新的ubantu 16.04环境,虚拟机配置 内存 8GCPU...

  • [{name:1},{name:2}].forEach((v,i,ar) => {console.log(v,i,ar)});//基础遍历[{name:1},{name:2}].map((v) => v.name);//[1,2]返回对象数组中指定字段值的一位数组(不改变原始数组)[{name:1},{name:2},{name:3}...

  • 体验内容 使用gmapping方法利用turtlebot底盘移动信息和激光雷达数据进行建图。 1. 安装一些依赖包 sudo apt-get install ros-melodic-move-base* sudo apt-get install ros-melodic-map-server* sudo apt-get insta...

  • 前言 我们知道Java/Python这种语言能够很好得 支持反射。反射机制 就是一种用户输入的字符串到对应实现方法的映射,比如http接口中 用户传入了url,我们需要调用该url对应的方法/函数对象 从而做出对应的操作。 而C++ 并没有友好得支持这样的操作,而最近工作中需要通过C++实现http接口,这个过程想要代码实现得优雅...

  • 原文出处: 韩昊    1 2 3 4 5 6 7 8 9 10 作 者:韩 昊 知 乎:Heinrich 微 博:@花生油工人 知乎专栏:与时间无关的故事   谨以此文献给大连海事大学的吴楠老师,柳晓鸣老师,王新年老师以及张晶泊老师。   转载的同学请保留上面这句话,谢谢。如果还能保留文章来源就更感激不尽了。 我保证这篇文章...

  • 原文出处: 韩昊   我保证这篇文章和你以前看过的所有文章都不同,这是 2012 年还在果壳的时候写的,但是当时没有来得及写完就出国了……于是拖了两年,嗯,我是拖延症患者…… 这篇文章的核心思想就是: 要让读者在不看任何数学公式的情况下理解傅里叶分析。 傅里叶分析不仅仅是一个数学工具,更是一种可以彻底颠覆一个人以前世界观的思维...

  • 很多Linux高手都喜欢使用screen命令,screen命令可以使你轻松地使用一个终端控制其他终端。尽管screen本身是一个非常有用的工具,byobu作为screen的增强版本,比screen更加好用而且美观,并且提供有用的信息和快捷的热键。 想象一下这样一个场景:你通过Secure Shell(ssh)链接到一个服务器,并...

  • NarrowbandPrimary Synchronization Signal时域位置每1个SFN存在一个NPSSSFNSubframeSymbol长度每个SFN5最后11个symbol11个symbols频域位置NB-IOT下行带宽固定180kHz,一个PRB,12个子载波。...

  •  [h1]反斜杠只能够阻止一个字符  [h2]位于键盘的左上角,和~公用一个键。...