Java Persistence with MyBatis 小结2
MyBatis 最關(guān)鍵的組成部分是 SqlSessionFactory,我們可以從中獲取 SqlSession,并執(zhí)行映射的 SQL 語句。SqlSessionFactory 對象可以通過基于 XML 的配置信息或者 Java API 創(chuàng)建。
?
1 mybatis環(huán)境,environments 配置默認(rèn)的數(shù)據(jù)庫環(huán)境
MyBatis 支持配置多個(gè) dataSource 環(huán)境,可以將應(yīng)用部署到不同的環(huán)境上,如 DEV(開發(fā)環(huán)境),TEST(測試換將),QA(質(zhì)量評估環(huán)境),UAT(用戶驗(yàn)收環(huán)境),PRODUCTION(生產(chǎn)環(huán)境),可以通過將默認(rèn) environment 值設(shè)置成想要的environment id 值。
?
2 每個(gè)environment 環(huán)境配置,需要有dataSource 和?transactionManager
dataSource 元素被用來配置數(shù)據(jù)庫連接屬性。典型配置如下
<dataSource type="POOLED"> <property name="driver" value="${jdbc.driverClassName}" /> <property name="url" value="${jdbc.url}" /> <property name="username" value="${jdbc.username}" /> <property name="password" value="${jdbc.password}" /> </dataSource>?
2.1 dataSource 的類型可以配置成其內(nèi)置類型之一,如 UNPOOLED,POOLED,JNDI。
? 如果將類型設(shè)置成 UNPOOLED,MyBatis 會(huì)為每一個(gè)數(shù)據(jù)庫操作創(chuàng)建一個(gè)新的連接,并關(guān)閉它。該方式
適用于只有小規(guī)模數(shù)量并發(fā)用戶的簡單應(yīng)用程序上。
? 如果將屬性設(shè)置成 POOLED,MyBatis 會(huì)創(chuàng)建一個(gè)數(shù)據(jù)庫連接池,連接池中的一個(gè)連接將會(huì)被用作數(shù)據(jù)
庫操作。一旦數(shù)據(jù)庫操作完成,MyBatis 會(huì)將此連接返回給連接池。在開發(fā)或測試環(huán)境中,經(jīng)常使用此
種方式。
? 如果將類型設(shè)置成 JNDI,MyBatis 從在應(yīng)用服務(wù)器向配置好的 JNDI 數(shù)據(jù)源 dataSource 獲取數(shù)據(jù)庫
連接。在生產(chǎn)環(huán)境中,優(yōu)先考慮這種方式。
?
如果屬性在不只一個(gè)地方進(jìn)行了配置,那么 MyBatis 將按照下面的順序來加載:
- 在 properties 元素體內(nèi)指定的屬性首先被讀取。
- 然后根據(jù) properties 元素中的 resource 屬性讀取類路徑下屬性文件或根據(jù) url 屬性指定的路徑讀取屬性文件,并覆蓋已讀取的同名屬性。
- 最后讀取作為方法參數(shù)傳遞的屬性,并覆蓋已讀取的同名屬性。
因此,通過方法參數(shù)傳遞的屬性具有最高優(yōu)先級(jí),resource/url 屬性中指定的配置文件次之,最低優(yōu)先級(jí)的是 properties 屬性中指定的屬性。
?
2.2?事務(wù)管理器 TransactionManager
MyBatis 支持兩種類型的事務(wù)管理器: JDBC and MANAGED.
- ?JDBC 事務(wù)管理器被用作當(dāng)應(yīng)用程序負(fù)責(zé)管理數(shù)據(jù)庫連接的生命周期(提交、回退等等)的時(shí)候。當(dāng)你將TransactionManager 屬性設(shè)置成 JDBC,MyBatis 內(nèi)部將使用 JdbcTransactionFactory 類創(chuàng)建TransactionManager。例如,部署到 Apache Tomcat 的應(yīng)用程序,需要應(yīng)用程序自己管理事務(wù)。它依賴于從數(shù)據(jù)源得到的連接來管理事務(wù)作用域。
- ?MANAGED 事務(wù)管理器是當(dāng)由應(yīng)用服務(wù)器負(fù)責(zé)管理數(shù)據(jù)庫連接生命周期的時(shí)候使用。當(dāng)你將TransactionManager 屬性設(shè)置成 MANAGED 時(shí),MyBatis 內(nèi)部使用 ManagedTransactionFactory 類創(chuàng)建事務(wù)管理器TransactionManager。例如,當(dāng)一個(gè)JavaEE的應(yīng)用程序部署在類似 JBoss,WebLogic,GlassFish 應(yīng)用服務(wù)器上時(shí),它們會(huì)使用 EJB 進(jìn)行應(yīng)用服務(wù)器的事務(wù)管理能力。在這些管理環(huán)境中,你可以使用 MANAGED 事務(wù)管理器。
Managed 是托管的意思,即是應(yīng)用本身不去管理事務(wù),而是把事務(wù)管理交給應(yīng)用所在的服務(wù)器進(jìn)行管理。
如果你正在使用 Spring + MyBatis,則沒有必要配置事務(wù)管理器, 因?yàn)?Spring 模塊會(huì)使用自帶的管理器來覆蓋前面的配置。
?
3?類型別名 typeAliases,
配置文件中,對于 resultType 和 parameterType 屬性值,我們需要使用 JavaBean 的完全限定名。
我們可以為完全限定名取一個(gè)別名(alias),然后其需要使用完全限定名的地方使用別名,而不是到處使用完全限定名。
<typeAliases> <typeAlias alias="Student" type="com.mybatis3.domain.Student" /> <typeAlias alias="Tutor" type="com.mybatis3.domain.Tutor" /> <package name="com.mybatis3.domain" /> </typeAliases>另一種方式為 JavaBeans 起別名,使用注解@Alias:
@Alias("StudentAlias") public class Student{}注意:@Alias 注解將會(huì)覆蓋配置文件中的<typeAliases>定義。
?
4?類型處理器 typeHandlers
MyBatis 是怎么知道對于 Integer 類型屬性使用 setInt() 和 String 類型屬性使用 setString()方法呢?
其實(shí) MyBatis 是通過使用類型處理器(type handlers)來決定這么做的。
MyBatis 對于以下的類型使用內(nèi)建的類型處理器:所有的基本數(shù)據(jù)類型、基本類型的包裹類型、byte[]、java.util.Date、java.sql.Date、java,sql.Time、java.sql.Timestamp、java 枚舉類型等。所以當(dāng) MyBatis 發(fā)現(xiàn)屬性的類型屬于上述類型,他會(huì)使用對應(yīng)的類型處理器將值設(shè)置到 PreparedStatement 中,同樣地,當(dāng)從 SQL 結(jié)果集構(gòu)建 JavaBean 時(shí),也有類似的過程。
?
對于自定義的類型,需要自己創(chuàng)建自定義類型處理器。
MyBatis 提供了抽象類 BaseTypeHandler<T> ,我們可以繼承此類創(chuàng)建自定義類型處理器。
例如,假設(shè)表 STUDENTS 有一個(gè) PHONE 字段,類型為 VARCHAR(15),而 JavaBean Student 有一個(gè) PhoneNumber 類定義類型的 phoneNumber 屬性。
有一個(gè)屬性是如下的類,?PhoneNumber 類
public class PhoneNumber { private String countryCode; private String stateCode; private String number; public PhoneNumber() { } public PhoneNumber(String countryCode, String stateCode, String number) { this.countryCode = countryCode; this.stateCode = stateCode; this.number = number; } public PhoneNumber(String string) { if(string != null) { String[] parts = string.split("-"); if(parts.length > 0) this.countryCode = parts[0]; if(parts.length > 1) this.stateCode = parts[1]; if(parts.length > 2) this.number = parts[2]; } } public String getAsString() { return countryCode + "-" + stateCode + "-" + number; } // Setters and getters } View Code?
而Student 定義如下
public class Student { private Integer id; private String name; private String email; private PhoneNumber phone; // Setters and getters } View Code4.1 創(chuàng)建的類型處理器如下
importjava.sql.CallableStatement; importjava.sql.PreparedStatement; importjava.sql.ResultSet; importjava.sql.SQLException; importorg.apache.ibatis.type.BaseTypeHandler; importorg.apache.ibatis.type.JdbcType; importcom.mybatis3.domain.PhoneNumber; public class PhoneTypeHandler extends BaseTypeHandler<PhoneNumber> { @Override public void setNonNullParameter(PreparedStatement ps, int i, PhoneNumber parameter, JdbcType jdbcType) throws SQLException { ps.setString(i, parameter.getAsString()); } @Override public PhoneNumber getNullableResult(ResultSet rs, String columnName) throws SQLException { return new PhoneNumber(rs.getString(columnName)); } @Override public PhoneNumber getNullableResult(ResultSet rs, int columnIndex) throws SQLException { return new PhoneNumber(rs.getString(columnIndex)); } @Override public PhoneNumber getNullableResult(CallableStatement cs, int columnIndex) throws SQLException { return new PhoneNumber(cs.getString(columnIndex)); } }說明:我們使用 ps.setString()和 rs.getString()方法是因?yàn)?phone 列是 VARCHAR 類型。
4.2?一旦我們實(shí)現(xiàn)了自定義的類型處理器,我們需要在 mybatis-config.xml 中注冊它:
<?xml version="1.0" encoding="utf-8"?> <!DOCTYPE configuration PUBLIC "-//mybatis.org//DTD Config 3.0//EN" "http://mybatis.org/dtd/mybatis-3-config.dtd"> <configuration> <properties resource="application.properties" /> <typeHandlers><typeHandler handler="com.mybatis3.typehandlers.PhoneTypeHandler" /> </typeHandlers> </configuration>注冊 PhoneTypeHandler 后, MyBatis 就能夠?qū)?Phone 類型的對象值存儲(chǔ)到 VARCHAR 類型的列上。
?
5?SQL 映射定義 Mappers
Mapper XML 文件中包含的 SQL 映射語句將會(huì)被應(yīng)用通過使用其 statementid 來執(zhí)行。我們需要在 mybatis-config.xml 文件中配置 SQL Mapper 文件的位置。
<mappers><mapper resource="com/mybatis3/mappers/StudentMapper.xml" /><mapper url="file:///D:/mybatisdemo/app/mappers/TutorMapper.xml" /><mapper class="com.mybatis3.mappers.TutorMapper" /><package name="com.mybatis3.mappers" /> </mappers>以上每一個(gè)<mapper> 標(biāo)簽的屬性有助于從不同類型的資源中加載映射 mapper:
? resource 屬性用來指定在 classpath 中的 mapper 文件。
? url 屬性用來通過完全文件系統(tǒng)路徑或者 web URL 地址來指向 mapper 文件
? class 屬性用來指向一個(gè) mapper 接口
? package 屬性用來指向可以找到 Mapper 接口的包名
?
總結(jié)
以上是生活随笔為你收集整理的Java Persistence with MyBatis 小结2的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 梦到别人车翻了人没事是什么意思
- 下一篇: 梦到大牙掉了有什么预兆