2015.4.10学习mybatis
来源:互联网 发布:余额宝 阿里云 编辑:程序博客网 时间:2024/06/16 06:05
没太明白数据源,JNDI上下文是什么意思,用的时候照葫芦画瓢试试吧
JNDI– 这个数据源的实现是为了能在如 EJB 或应用服务器这类容器中使用,容器可以集中或在外部配置数据源,然后放置一个 JNDI 上下文的引用。这种数据源配置只需要两个属性:
- initial_context – 这个属性用来在 InitialContext 中寻找上下文(即,initialContext.lookup(initial_context))。这是个可选属性,如果忽略,那么 data_source 属性将会直接从 InitialContext 中寻找。
- data_source – 这是引用数据源实例位置的上下文的路径。提供了 initial_context 配置时会在其返回的上下文中进行查找,没有提供时则直接在 InitialContext 中查找。
和其他数据源配置类似,可以通过名为“env.”的前缀直接向初始上下文发送属性(send properties)。比如:
- env.encoding=UTF8
这就会在初始化时以值“UTF8”向初始上下文的构造方法传递名为“encoding”的属性。
也可使用任何第三方数据源,需要实现这个接口 org.apache.ibatis.datasource.DataSourceFactory:
public interface DataSourceFactory { void setProperties(Properties props); DataSource getDataSource();}org.apache.ibatis.datasource.unpooled.UnpooledDataSourceFactory 可被用作父类来构建新的数据源适配器,比如下面这段插入 C3P0 所必需的代码:
import org.apache.ibatis.datasource.unpooled.UnpooledDataSourceFactory;import com.mchange.v2.c3p0.ComboPooledDataSource; public class C3P0DataSourceFactory extends UnpooledDataSourceFactory { public C3P0DataSourceFactory() { this.dataSource = new ComboPooledDataSource(); }}
为了令其工作,可在每个需要 MyBatis 调用的 setter 方法中增加一个属性。下面是一个可以连接至 PostgreSQL 数据库的例子:
<dataSource type="org.myproject.C3P0DataSourceFactory"> <property name="driver" value="org.postgresql.Driver"/> <property name="url" value="jdbc:postgresql:mydb"/> <property name="username" value="postgres"/> <property name="password" value="root"/></dataSource>
databaseIdProvider provide提供
MyBatis 可以根据不同的数据库厂商执行不同的语句,这种多厂商的支持是基于映射语句中的 databaseId 属性的。MyBatis 会加载不带 databaseId 属性和带有匹配当前数据库 databaseId 属性的所有语句。如果同时找到带有 databaseId 和不带 databaseId 的相同语句,则后者会被舍弃。为支持多厂商特性只要像下面这样在 mybatis-config.xml 文件中加入 databaseIdProvider 即可:
<databaseIdProvider type="DB_VENDOR" />
这里的 DB_VENDOR 会通过 DatabaseMetaData#getDatabaseProductName() 返回的字符串进行设置。由于通常情况下这个字符串都非常长而且相同产品的不同版本会返回不同的值,所以最好通过设置属性别名来使其变短,如下:
<databaseIdProvider type="DB_VENDOR"> <property name="SQL Server" value="sqlserver"/> <property name="DB2" value="db2"/> <property name="Oracle" value="oracle" /></databaseIdProvider>
在有 properties 时,DB_VENDOR databaseIdProvider 元素会搜索所返回数据库产品名称的第一个对应键值,如果没有匹配的将会返回 null。在这个例子中,如果 getDatabaseProductName() 返回“Oracle (DataDirect)”,databaseId 将被设置为“oracle”。
你可以通过实现接口 org.apache.ibatis.mapping.DatabaseIdProvider 并在 mybatis-config.xml 中注册来构建自己的 database provider:
public interface DatabaseIdProvider { void setProperties(Properties p); String getDatabaseId(DataSource dataSource) throws SQLException;}
映射器(mappers)
既然 MyBatis 的行为已经由上述元素配置完了,我们现在就要定义 SQL 映射语句了。但是首先我们需要告诉 MyBatis 到哪里去找到这些语句。Java 在自动查找这方面没有提供一个很好的方法,所以最佳的方式是告诉 MyBatis 到哪里去找映射文件。你可以使用相对于类路径的资源引用,或完全限定资源定位符(包括 file:/// 的 URL),或类名和包名等。例如:
<!-- Using classpath relative resources --><mappers> <mapper resource="org/mybatis/builder/AuthorMapper.xml"/> <mapper resource="org/mybatis/builder/BlogMapper.xml"/> <mapper resource="org/mybatis/builder/PostMapper.xml"/></mappers>
<!-- Using url fully qualified paths --><mappers> <mapper url="file:///var/mappers/AuthorMapper.xml"/> <mapper url="file:///var/mappers/BlogMapper.xml"/> <mapper url="file:///var/mappers/PostMapper.xml"/></mappers>
<!-- Using mapper interface classes --><mappers> <mapper class="org.mybatis.builder.AuthorMapper"/> <mapper class="org.mybatis.builder.BlogMapper"/> <mapper class="org.mybatis.builder.PostMapper"/></mappers>
<!-- Register all interfaces in a package as mappers --><mappers> <package name="org.mybatis.builder"/></mappers>
这些配置会告诉了 MyBatis 去哪里找映射文件
XML映射文件
Mapper XML 文件
MyBatis 的真正强大在于它的映射语句。映射器的 XML 文件就显得相对简单。如果拿它跟具有相同功能的 JDBC 代码进行对比,会发现省掉了将近 95% 的代码。MyBatis 就是针对 SQL 构建的,并且比普通的方法做的更好。
SQL 映射文件有很少的几个顶级元素:- cache – 给定命名空间的缓存配置。
- cache-ref – 其他命名空间缓存配置的引用。
- resultMap – 是最复杂也是最强大的元素,用来描述如何从数据库结果集中来加载对象。
- sql – 可被其他语句引用的可重用语句块。
- insert – 映射插入语句
- update – 映射更新语句
- delete – 映射删除语句
- select – 映射查询语句
select
<select id="selectPerson" parameterType="int" resultType="hashmap"> SELECT * FROM PERSON WHERE ID = #{id}</select>这个语句被称作 selectPerson,接受一个 int(或 Integer)类型的参数,并返回一个 HashMap 类型的对象,其中的键是列名,值便是结果行中的对应值。
注意参数符号:#{id}
这就告诉 MyBatis 创建一个预处理语句参数,通过 JDBC,这样的一个参数在 SQL 中会由一个“?”来标识,并被传递到一个新的预处理语句中,就像这样:
// Similar JDBC code, NOT MyBatis…String selectPerson = "SELECT * FROM PERSON WHERE ID=?";PreparedStatement ps = conn.prepareStatement(selectPerson);ps.setInt(1,id);
这需要很多单独的 JDBC 的代码来提取结果并将它们映射到对象实例中,这就是 MyBatis 节省你时间的地方。我们需要深入了解参数和结果映射
select 元素有很多属性允许你配置,来决定每条语句的作用细节。
<select id="selectPerson" parameterType="int" parameterMap="deprecated" resultType="hashmap" resultMap="personResultMap" flushCache="false" useCache="true" timeout="10000" fetchSize="256" statementType="PREPARED" resultSetType="FORWARD_ONLY">
insert, update 和 delete
<insert id="insertAuthor" parameterType="domain.blog.Author" flushCache="true" statementType="PREPARED" keyProperty="" keyColumn="" useGeneratedKeys="" timeout="20"><update id="insertAuthor" parameterType="domain.blog.Author" flushCache="true" statementType="PREPARED" timeout="20"><delete id="insertAuthor" parameterType="domain.blog.Author" flushCache="true" statementType="PREPARED" timeout="20">
<insert id="insertAuthor"> insert into Author (id,username,password,email,bio) values (#{id},#{username},#{password},#{email},#{bio})</insert><update id="updateAuthor"> update Author set username = #{username}, password = #{password}, email = #{email}, bio = #{bio} where id = #{id}</update><delete id="deleteAuthor"> delete from Author where id = #{id}</delete>
插入语句的配置规则更加丰富,在插入语句里面有一些额外的属性和子元素用来处理主键的生成,而且有多种生成方式。
首先,如果你的数据库支持自动生成主键的字段(比如 MySQL 和 SQL Server),那么你可以设置 useGeneratedKeys=”true”,然后再把 keyProperty 设置到目标属性上就OK了。例如,如果上面的 Author 表已经对 id 使用了自动生成的列类型,那么语句可以修改为:
<insert id="insertAuthor" useGeneratedKeys="true" keyProperty="id"> insert into Author (username,password,email,bio) values (#{username},#{password},#{email},#{bio})</insert>
对于不支持自动生成类型的数据库或可能不支持自动生成主键 JDBC 驱动来说,MyBatis 有另外一种方法来生成主键。
这里有一个简单的示例,它可以生成一个随机 ID(最好不要这么做,但这里展示了 MyBatis 处理问题的灵活性及其所关心的广度):
<span style="color:#3333ff;"><insert id="insertAuthor"> <selectKey keyProperty="id" resultType="int" order="BEFORE"> select CAST(RANDOM()*1000000 as INTEGER) a from SYSIBM.SYSDUMMY1 </selectKey> insert into Author (id, username, password, email,bio, favourite_section) values (#{id}, #{username}, #{password}, #{email}, #{bio}, #{favouriteSection,jdbcType=VARCHAR})</insert></span>
在上面的示例中,selectKey 元素将会首先运行,Author 的 id 会被设置,然后插入语句会被调用。这给你了一个和数据库中来处理自动生成的主键类似的行为,避免了使 Java 代码变得复杂。
selectKey 元素描述如下:
<selectKey keyProperty="id" resultType="int" order="BEFORE" statementType="PREPARED">
sql
这个元素可以被用来定义可重用的 SQL 代码段,可以包含在其他语句中。比如:
<sql id="userColumns"> id,username,password </sql>这个 SQL 片段可以被包含在其他语句中,例如:
<select id="selectUsers" resultType="map"> select <include refid="userColumns"/> from some_table where id = #{id}</select>
参数(Parameters)
<span style="font-family: 'Helvetica Neue', Helvetica, Arial, sans-serif;"><select id="selectUsers" resultType="User"></span>
select id, username, password from users where id = #{id}</select>
面的这个示例说明了一个非常简单的命名参数映射。参数类型被设置为 int,这样这个参数就可以被设置成任何内容。原生的类型或简单数据类型(比如整型和字符串)因为没有相关属性,它会完全用参数值来替代。然而,如果传入一个复杂的对象,行为就会有一点不同了。比如:
<insert id="insertUser" parameterType="User"> insert into users (id, username, password) values (#{id}, #{username}, #{password})</insert>
如果 User 类型的参数对象传递到了语句中,id、username 和 password 属性将会被查找,然后将它们的值传入预处理语句的参数中。
这点对于向语句中传参是比较好的而且又简单,不过参数映射的功能远不止于此。
首先,像 MyBatis 的其他部分一样,参数也可以指定一个特殊的数据类型。
#{property,javaType=int,jdbcType=NUMERIC}像 MyBatis 的剩余部分一样,javaType 通常可以从参数对象中来去确定,前提是只要对象不是一个 HashMap。那么 javaType 应该被确定来保证使用正确类型处理器。
如果 null 被当作值来传递,对于所有可能为空的列,JDBC Type 是需要的。你可以自己通过阅读预处理语句的 setNull() 方法的 JavaDocs 文档来研究这种情况。
为了以后定制类型处理方式,你也可以指定一个特殊的类型处理器类(或别名),比如:
#{age,javaType=int,jdbcType=NUMERIC,typeHandler=MyTypeHandler}
看起来配置变得越来越繁琐,但实际上是很少去设置它们。
对于数值类型,还有一个小数保留位数的设置,来确定小数点后保留的位数。
#{height,javaType=double,jdbcType=NUMERIC,numericScale=2}
mode 属性允许你指定 IN,OUT 或 INOUT 参数。如果参数为 OUT 或 INOUT,参数对象属性的真实值将会被改变,就像你在获取输出参数时所期望的那样。如果 mode 为 OUT(或 INOUT),而且 jdbcType 为 CURSOR(也就是 Oracle 的 REFCURSOR),你必须指定一个 resultMap 来映射结果集到参数类型。要注意这里的 javaType 属性是可选的,如果左边的空白是 jdbcType 的 CURSOR 类型,它会自动地被设置为结果集。
#{department, mode=OUT, jdbcType=CURSOR, javaType=ResultSet, resultMap=departmentResultMap}
- 2015.4.10学习mybatis
- 2015.4.9学习mybatis
- Mybatis学习(10)-MyBatis中的延迟加载
- Mybatis学习---了解Mybatis
- 【Mybatis学习】Mybatis缓存
- MyBatis学习
- MyBatis学习
- MyBatis学习
- Mybatis学习
- mybatis学习
- Mybatis学习
- mybatis学习
- MyBatis 学习
- MyBatis学习
- MyBatis学习
- MyBatis学习
- MyBatis学习
- mybatis学习
- Anagrams 寻找相同的乱序的字母排列
- Python 关于 name main的使用 if __name__ == '__main__':
- 显示遮罩层并从屏幕上方滑出div
- oracle数据库导入与导出
- 【安全健行】(一):Hacker编程技能
- 2015.4.10学习mybatis
- 斯坦福大学机器学习第四课“逻辑回归(Logistic Regression)”
- Pow(x, n)
- 黑马程序员---JAVA中成员变量初始化规则
- PHP调用webservice的用法
- 【线段树】【SOJ1136】【cogs775】山海经
- 同步和异步概念
- Unity3D使用RenderCommand渲染外轮廓
- C/C++中extern关键字详解