MyBatis.NET的前身为IBatis,是JAVA版MyBatis在.NET平台上的翻版,相对NHibernate、EntityFramework等重量级ORM框架而言,MyBatis.NET必须由开发人员手动写SQL,相对灵活性更大,更容易保证DB访问的性能,适用开发团队里有SQL熟手的场景。
下面是使用步骤:
1、到官网http://code.google.com/p/mybatisnet/ 下载相关dll和文档
Doc-DataAccess-1.9.2.zip
Doc-DataMapper-1.6.2.zip
IBatis.DataAccess.1.9.2.bin.zip
IBatis.DataMapper.1.6.2.bin.zip
一共有4个zip包
2、创建一个Web应用,参考下图添加程序集引用
3、修改web.config,主要是配置log4net,参考下面的内容:
<?xml version="1.0"?> <configuration> <configSections> <sectionGroup name="iBATIS"> <section name="logging" type="IBatisNet.Common.Logging.ConfigurationSectionHandler, IBatisNet.Common"/> </sectionGroup> <section name="log4net" type="log4net.Config.Log4NetConfigurationSectionHandler, log4net"/> </configSections> <system.web> <compilation debug="true" targetFramework="4.0"/> </system.web> <iBATIS> <logging> <logFactoryAdapter type="IBatisNet.Common.Logging.Impl.Log4NetLoggerFA, IBatisNet.Common.Logging.Log4Net"> <arg key="configType" value="inline"/> <arg key="showLogName" value="true"/> <arg key="showDataTime" value="true"/> <arg key="level" value="ALL"/> <arg key="dateTimeFormat" value="yyyy/MM/dd HH:mm:ss:SSS"/> </logFactoryAdapter> </logging> </iBATIS> <log4net> <!-- Define some output appenders --> <appender name="RollingLogFileAppender" type="log4net.Appender.RollingFileAppender"> <param name="File" value="mybatis.log"/> <param name="AppendToFile" value="true"/> <param name="MaxSizeRollBackups" value="2"/> <param name="MaximumFileSize" value="100KB"/> <param name="RollingStyle" value="Size"/> <param name="StaticLogFileName" value="true"/> <layout type="log4net.Layout.PatternLayout"> <param name="Header" value="[Header] "/> <param name="Footer" value="[Footer] "/> <param name="ConversionPattern" value="%d [%t] %-5p %c [%x] - %m%n"/> </layout> </appender> <appender name="ConsoleAppender" type="log4net.Appender.ConsoleAppender"> <layout type="log4net.Layout.PatternLayout"> <param name="ConversionPattern" value="%d [%t] %-5p %c [%x] <%X{auth}> - %m%n"/> </layout> </appender> <!-- Set root logger level to ERROR and its appenders --> <root> <level value="DEBUG"/> <appender-ref ref="RollingLogFileAppender"/> <appender-ref ref="ConsoleAppender"/> </root> <!-- Print only messages of level DEBUG or above in the packages --> <logger name="IBatisNet.DataMapper.Configuration.Cache.CacheModel"> <level value="DEBUG"/> </logger> <logger name="IBatisNet.DataMapper.Configuration.Statements.PreparedStatementFactory"> <level value="DEBUG"/> </logger> <logger name="IBatisNet.DataMapper.LazyLoadList"> <level value="DEBUG"/> </logger> <logger name="IBatisNet.DataAccess.DaoSession"> <level value="DEBUG"/> </logger> <logger name="IBatisNet.DataMapper.SqlMapSession"> <level value="DEBUG"/> </logger> <logger name="IBatisNet.Common.Transaction.TransactionScope"> <level value="DEBUG"/> </logger> <logger name="IBatisNet.DataAccess.Configuration.DaoProxy"> <level value="DEBUG"/> </logger> </log4net> </configuration>
4、添加Providers.config
把从官方下载的压缩包解开,就能找到providers.config文件,里面定义了MyBatis.Net支持的各种数据库驱动,本例以oracle为例,把其它不用的db provider全删掉,只保留下oracleClient1.0,同时把enabled属性设置成true,参考下面这样:
<?xml version="1.0"?> <providers xmlns="http://ibatis.apache.org/providers" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"> <clear/> <!--Oracle Support--> <provider name="oracleClient1.0" description="Oracle, Microsoft provider V1.0.5000.0" enabled="true" assemblyName="System.Data.OracleClient, Version=1.0.5000.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" connectionClass="System.Data.OracleClient.OracleConnection" commandClass="System.Data.OracleClient.OracleCommand" parameterClass="System.Data.OracleClient.OracleParameter" parameterDbTypeClass="System.Data.OracleClient.OracleType" parameterDbTypeProperty="OracleType" dataAdapterClass="System.Data.OracleClient.OracleDataAdapter" commandBuilderClass="System.Data.OracleClient.OracleCommandBuilder" usePositionalParameters="false" useParameterPrefixInSql="true" useParameterPrefixInParameter="false" parameterPrefix=":" allowMARS="false" /> </providers>
5、添加SqlMap.config,内容如下:
<?xml version="1.0" encoding="utf-8"?> <sqlMapConfig xmlns="http://ibatis.apache.org/dataMapper" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"> <settings> <setting useStatementNamespaces="false"/> <setting cacheModelsEnabled="true"/> </settings> <!--db provider配置文件路径--> <providers resource="providers.config"/> <!--db provider类型及连接串--> <database> <provider name="oracleClient1.0" /> <dataSource name="oracle" connectionString="Data Source=ORCL;Persist Security Info=True;User ID=scott;Password=tiger;Unicode=True" /> </database> <!--db与Entity的映射文件--> <sqlMaps> <sqlMap resource="Maps/ProductMap.xml"/> </sqlMaps> </sqlMapConfig>
这个文件也复制到Web项目根目录下,它的作用主要是指定db连接串,告诉系统providers.config在哪? 以及db与entity的映射文件在哪?(映射文件后面会讲到,这里先不管)
6、在Oraccle中先建表Product以及Sequence,方便接下来测试
-- CREATE TABLE CREATE TABLE PRODUCT ( PRODUCTID NUMBER NOT NULL, PRODUCTNAME VARCHAR2(100), PRODUCTCOMPANY VARCHAR2(100), SIGNDATE DATE, UPDATEDATE DATE ); -- CREATE/RECREATE PRIMARY, UNIQUE AND FOREIGN KEY CONSTRAINTS ALTER TABLE PRODUCT ADD CONSTRAINT PK_PRODUCT_ID PRIMARY KEY (PRODUCTID); -- CREATE SEQUENCE CREATE SEQUENCE SQ_PRODUCT MINVALUE 1 MAXVALUE 9999999999999999999999999 START WITH 1 INCREMENT BY 1 CACHE 20;
7、创建Maps目录,并在该目录下,添加映射文件ProductMap.xml,内容如下:
<?xml version="1.0" encoding="utf-8" ?> <sqlMap namespace="EntityModel" xmlns="http://ibatis.apache.org/mapping" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"> <alias> <!--类的别名--> <typeAlias alias="Product" type="Web.Product,Web"/> </alias> <resultMaps> <!--Product类与db表的映射--> <resultMap id="SelectAllResult" class="Product"> <result property="ProductId" column="ProductId"/> <result property="ProductName" column="ProductName"/> <result property="ProductCompany" column="ProductCompany" /> <result property="SignDate" column="SignDate" /> <result property="UpdateDate" column="UpdateDate" /> </resultMap> </resultMaps> <statements> <!--查询所有记录--> <select id="SelectAllProduct" resultMap="SelectAllResult"> <![CDATA[SELECT ProductId,ProductName,ProductCompany,SignDate,UpdateDate FROM Product]]> </select> <!--查询单条记录--> <select id="SelectByProductId" parameterClass="int" resultMap="SelectAllResult" extends="SelectAllProduct"> <![CDATA[ where ProductId = #value# ]]> </select> <!--插入新记录--> <insert id="InsertProduct" parameterClass="Product"> <!--oracle sequence的示例用法--> <selectKey property="ProductId" type="pre" resultClass="int"> select SQ_Product.nextval as ProductId from dual </selectKey> <![CDATA[INSERT into Product(ProductId,ProductCompany,ProductName,SignDate,UpdateDate) VALUES(#ProductId#,#ProductCompany#, #ProductName# , #SignDate# , #UpdateDate#)]]> </insert> <!--更新单条记录--> <update id="UpdateProduct" parameterClass="Product"> <![CDATA[Update Product SET ProductName=#ProductName#, ProductCompany=#ProductCompany#, SignDate=#SignDate#, UpdateDate=#UpdateDate# Where ProductId=#ProductId#]]> </update> <!--根据主键删除单条记录--> <delete id="DeleteProductById" parameterClass="int"> <![CDATA[Delete From Product Where ProductId=#value#]]> </delete> </statements> </sqlMap>
它的作用就是指定各种sql,以及db表与entity的映射规则,注意下insert中Sequence的用法!
8、创建实体类Product
using System; namespace Web { public class Product { public int ProductId { get; set; } public string ProductName { get; set; } public string ProductCompany { get; set; } public DateTime SignDate { get; set; } public DateTime UpdateDate { get; set; } public Product() { } } }
9、写一个通用的BaseDA类,对MyBatis.Net做些基本的封装
using IBatisNet.DataMapper; using System.Collections.Generic; namespace Web { public static class BaseDA { public static int Insert<T>(string statementName, T t) { ISqlMapper iSqlMapper = Mapper.Instance(); if (iSqlMapper != null) { return (int)iSqlMapper.Insert(statementName, t); } return 0; } public static int Update<T>(string statementName, T t) { ISqlMapper iSqlMapper = Mapper.Instance(); if (iSqlMapper != null) { return iSqlMapper.Update(statementName, t); } return 0; } public static int Delete(string statementName, int primaryKeyId) { ISqlMapper iSqlMapper = Mapper.Instance(); if (iSqlMapper != null) { return iSqlMapper.Delete(statementName, primaryKeyId); } return 0; } public static T Get<T>(string statementName, int primaryKeyId) where T : class { ISqlMapper iSqlMapper = Mapper.Instance(); if (iSqlMapper != null) { return iSqlMapper.QueryForObject<T>(statementName, primaryKeyId); } return null; } public static IList<T> QueryForList<T>(string statementName, object parameterObject = null) { ISqlMapper iSqlMapper = Mapper.Instance(); if (iSqlMapper != null) { return iSqlMapper.QueryForList<T>(statementName, parameterObject); } return null; } } }
10、然后就可以在Default.aspx.cs上测试了,参考下面的代码:
using System; using System.Web.UI; namespace Web { public partial class Default : Page { protected void Page_Load(object sender, EventArgs e) { //插入 var insertProductId = BaseDA.Insert<Product>("InsertProduct", new Product() { ProductCompany = "INFOSKY", ProductName = "iGSA2", SignDate = DateTime.Now, UpdateDate = DateTime.Now }); //查单条记录 var model = BaseDA.Get<Product>("SelectByProductId", insertProductId); ShowProduct(model); Response.Write("<hr/>"); //修改记录 if (model != null) { model.ProductName = (new Random().Next(0, 99999999)).ToString().PadLeft(10, '0'); int updateResult = BaseDA.Update<Product>("UpdateProduct", model); Response.Write("update影响行数:" + updateResult + "<br/><hr/>"); } //查列表 var products = BaseDA.QueryForList<Product>("SelectAllProduct"); foreach (var pro in products) { ShowProduct(pro); } Response.Write("<hr/>"); //删除记录 int deleteResult = BaseDA.Delete("DeleteProductById", insertProductId); Response.Write("delete影响行数:" + deleteResult + "<br/><hr/>"); } void ShowProduct(Product pro) { if (pro == null) return; Response.Write(string.Format("{0} , {1} , {2} , {3} , {4}<br/>", pro.ProductId, pro.ProductName, pro.ProductCompany, pro.SignDate, pro.UpdateDate)); } } }
示例源码下载:源码附件