github:https://github.com/mybatis/mybatis-3
官方文档:http://www.mybatis.org/mybatis-3/zh/index.html
注:一些用法及要注意的地方都写在了代码注释里面,没有来得及分类
相关jar包(maven):pom.xml
<!--mybatis-->
<dependency>
<groupId>org.mybatis</groupId>
<artifactId>mybatis</artifactId>
<version>3.4.1</version>
</dependency>
<!--mySql 驱动-->
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>5.1.39</version>
</dependency>
<!--junit-->
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.12</version>
<scope>test</scope>
</dependency>
相关配置文件:
- mybatis-config.xml //MyBatis核心初始化配置文件
- jdbc.properties //存放一些数据库连接信息
- EmpMapper.xml //emp映射配置文件,在mybatis-config.xml中指定
emp表信息
目录结构
详细配置信息:
- 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>
<!--
这些属性都是可外部配置且可动态替换的,既可以在典型的 Java 属性文件中配置,亦可通过 properties 元素的子元素来传递,测试目的,将username等配置在这边,properties位置必须在settings之前
-->
<properties resource="jdbc.properties">
<property name="username" value="root"/>
<property name="password" value="root"/>
</properties>
<settings>
<!--
允许 JDBC 支持自动生成主键,需要驱动兼容。
如果设置为 true 则这个设置强制使用自动生成主键,
尽管一些驱动不能兼容但仍可正常工作(比如 Derby)
-->
<setting name="useGeneratedKeys" value="true"/>
<!--
是否开启自动驼峰命名规则(camel case)映射,
即从经典数据库列名 A_COLUMN 到经典 Java 属性名 aColumn 的类似映射
-->
<setting name="mapUnderscoreToCamelCase" value="true"/>
</settings>
<environments default="development">
<environment id="development">
<transactionManager type="JDBC"/>
<dataSource type="POOLED">
<property name="driver" value="${mysql.driver.class}"/>
<property name="url" value="${mysql.mine.url}"/>
<property name="username" value="${username}"/>
<property name="password" value="${password}"/>
</dataSource>
</environment>
</environments>
<!--
既然 MyBatis 的行为已经由上述元素配置完了,我们现在就要定义 SQL 映射语句了。
但是首先我们需要告诉 MyBatis 到哪里去找到这些语句。 Java 在自动查找这方面没有提供一个很好的方法,
所以最佳的方式是告诉 MyBatis 到哪里去找映射文件。
你可以使用相对于类路径的资源引用, 或完全限定资源定位符(包括 file:/// 的 URL),或类名和包名等
-->
<mappers>
<!-- 四种指定方式 [类路径的资源引用,完全限定资源定位符(绝对路径) ,类名(未测试通过),包名(未测试通过)] -->
<mapper resource="pers/mine/mappers/EmpMapper.xml"/>
<!-- <mapper class="pers.mine.mappers.EmpMapper"/> -->
<!-- <package name="pers.mine"/> -->
<!-- <mapper url="file:///D:/EmpMapper.xml"/> -->
</mappers>
</configuration>
- jdbc.properties
mysqlOld.driver.class=org.gjt.mm.mysql.Driver
mysql.driver.class=com.mysql.jdbc.Driver
mysql.mine.url=jdbc:mysql://localhost:3306/mine
- EmpMapper.xml
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper
PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<!-- 如果定义了mapper接口,namespace就指定为该接口完全限定名 -->
<mapper namespace="pers.mine.mappers.EmpMapper">
<!-- 自定义一个map映射 -->
<resultMap type="pers.mine.po.Emp" id="abcMap">
<!-- 列名 属性名 -->
<result column="empno" property="empNo"/>
<result column="ename" property="eName"/>
<result column="job" property="job"/>
<result column="hiredate" property="hiredate"/>
<result column="sal" property="sal"/>
<result column="comm" property="comm"/>
</resultMap>
<!-- 定义一个sql静态字符串 ,可用于拼接 -->
<sql id="xSql">
LIMIT 5,3
</sql>
<!-- 带有参数的sql字符串 -->
<sql id="xSqlPro">
LIMIT ${x},${y}
</sql>
<!--
查询语句中列名不能以*号代替
属性id:符合java标识命名规范即可
属性resultType: 查询返回PO实体类路径
属性resultMap: 与resultType 互斥
属性parameterType:参数类型只有一种,如果需要传多个参数,可以将多个参数封装为一个POJO,然后将属性值设为该POJO的完全限定名(包名+类名)或别名
statementType STATEMENT,PREPARED 或 CALLABLE 的一个。
默认值为PREPARED,建议使用默认值,可以防止SQL注入漏洞
-->
<select id="findAll" resultType="pers.mine.po.Emp" statementType="PREPARED">
<!-- SELECT * FROM emp <include refid="xSql"/> -->
SELECT * FROM emp
<include refid="xSqlPro">
<property name="x" value="3"/>
<property name="y" value="5"/>
</include>
</select>
<!-- 可以自定义一个map映射 ,在使用类型时使用该map来完成列名到属性名之间的转换 -->
<select id="findSomeByPage" resultMap="abcMap" parameterType="pers.mine.po.PageInfo">
SELECT * FROM emp LIMIT #{start},#{offset}
</select>
<select id="findSomeByKey" parameterType="string" resultType="pers.mine.po.Emp">
<!--
#{a} 和 ${a} 在替换时 $符号不对字符串类型添加"" #操作则会添加"" 但$操作不会对其内容做出安全性检测,要少用
默认情况下,使用#{}格式的语法会导致 MyBatis 创建预处理语句属性并安全地设置值(比如?)。
这样做更安全,更迅速,通常也是首选做法,不过有时你只是想直接在 SQL 语句中插入一个不改变的字符串。
-->
<!-- SELECT * FROM emp Where ename like "%${value}%" or job like "%${value}%" -->
SELECT * FROM emp Where ename like #{value} or job like #{value}
</select>
<insert id="addOne" parameterType="pers.mine.po.Emp" >
INSERT INTO emp(empno,ename,job,hiredate,sal,comm)
VALUES (#{empNo},#{eName},#{job},#{hiredate},#{sal},#{comm})
</insert>
<!--
对于insert update 标签
没有resultType属性:返回值为影响行数
获取自增长主键(数据库要先设置成自增长):
1、将useGeneratedKeys属性设为true
2、keyProperty属性设定为参数类的主键属性名[注意大小写 要与属性名完全一致,写错是不会报错de]
-->
<insert id="addOneAutoNo" parameterType="pers.mine.po.Emp" useGeneratedKeys="true" keyProperty="empNo" >
<!-- Oracle等无自增长列数据库
<selectKey keyProperty="aid" order="BEFORE">
select seq.nextval from dual
</selectKey>
-->
<!-- MySQL的另一种写法 order="BEFORE" 有了反而没效果-->
<selectKey keyProperty="empNo" resultType="int" >
select LAST_INSERT_ID()
</selectKey>
INSERT INTO emp(ename,job,hiredate,sal,comm)
VALUES (#{eName},#{job},#{hiredate},#{sal},#{comm})
</insert>
<!-- 依靠拼接sql实现一次性插入多条数据,并返回每条数据自增长主键,以及影响行数 -->
<insert id="addSome" parameterType="pers.mine.po.Emp" useGeneratedKeys="true" keyProperty="empNo" >
INSERT INTO emp(ename,job) VALUES
<!-- 循环拼接sql语句 separator="," 表示分隔符 主要依据INSERT 语句 INSERT INTO xxx("xx","xx") Values ("xx","xx"),("xx","xx")...-->
<foreach item="item" collection="list" separator=",">
(#{item.eName},#{item.job})
</foreach>
</insert>
<update id="editOne" parameterType="pers.mine.po.Emp" useGeneratedKeys="true" keyProperty="empno">
UPDATE emp set ename=#{eName},job=#{job} WHERE empno=#{empNo}
</update>
<!-- 参数唯一且为基础类型,包装类型,String时,使用value取值 -->
<delete id="delOne" parameterType="int">
DELETE from emp where empno=#{value}
</delete>
</mapper>
相关测试代码
Emp.java(相关属性)
- private Integer empNo;
- private String eName;
- private String job;
- private Date hiredate;
- private Double sal;
- private Double comm;
PageInfo.java(相关属性)
- private Integer start;
- private Integer offset;
MyBatisTest.java
package pers.mine;
import java.io.IOException;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.List;
import org.apache.ibatis.io.Resources;
import org.apache.ibatis.session.SqlSession;
import org.apache.ibatis.session.SqlSessionFactory;
import org.apache.ibatis.session.SqlSessionFactoryBuilder;
import org.junit.Assert;
import org.junit.Before;
import org.junit.Test;
import pers.mine.po.Emp;
import pers.mine.po.PageInfo;
public class MyBatisTest {
private SqlSessionFactory ssf;
/**
* 初始化数据源等
* 存在问题,mapper映射文件路径只会写其中一种
* @throws IOException
*/
@Before
public void before() throws IOException{
String resource="mybatis-config.xml";
InputStream in=Resources.getResourceAsStream(resource);
ssf=new SqlSessionFactoryBuilder().build(in);
}
@Test
public void selectTest(){
SqlSession ss=ssf.openSession();
List<Emp> emps= ss.selectList("EmpMapper.findAll");
System.out.println(emps.size());
System.out.println(emps);
ss.commit();
ss.close();
}
@Test
public void selectSomeByPageTest(){
SqlSession ss=ssf.openSession();
PageInfo pi=new PageInfo();
pi.setStart(5);
pi.setOffset(5);
List<Emp> emps= ss.selectList("EmpMapper.findSomeByPage",pi);
System.out.println(emps.size());
System.out.println(emps);
ss.commit();
ss.close();
}
@Test
public void selectSomeByKeyTest(){
SqlSession ss=ssf.openSession();
String key="%王%";
List<Emp> emps= ss.selectList("EmpMapper.findSomeByKey",key);
System.out.println(emps.size());
System.out.println(emps);
ss.commit();
ss.close();
}
@Test
public void addTest(){
SqlSession ss=ssf.openSession();
Emp one =new Emp();
one.setEmpNo(10086);
one.seteName("小空空");
one.setJob("测试人员");
int result= ss.update("EmpMapper.addOne",one);
System.out.println(result);
Assert.assertEquals(result,1);
ss.commit();
ss.close();
}
@Test
public void addAutoNoTest(){
SqlSession ss=ssf.openSession();
Emp one =new Emp();
one.seteName("小空空");
one.setJob("测试人员");
int result= ss.update("EmpMapper.addOneAutoNo",one);
System.out.println(result);
System.out.println(one);
Assert.assertEquals(result,1);
ss.commit();
ss.close();
}
@Test
public void addListTest(){
SqlSession ss=ssf.openSession();
List<Emp> ls=new ArrayList<Emp>();
ls.add(new Emp("测试1","测试1"));
ls.add(new Emp("测试2","测试2"));
ls.add(new Emp("测试3","测试3"));
int result= ss.update("EmpMapper.addSome",ls);
System.out.println(result);
System.out.println(ls);
Assert.assertEquals(result,3);
ss.commit();
ss.close();
}
@Test
public void editTest(){
SqlSession ss=ssf.openSession();
Emp one =new Emp();
one.setEmpNo(10086);
one.seteName("小空空2号");
one.setJob("测试人员,拉拉");
int result= ss.insert("EmpMapper.editOne",one);
System.out.println(result);
Assert.assertEquals(result,1);
ss.commit();
ss.close();
}
@Test
public void delTest(){
SqlSession ss=ssf.openSession();
int result= ss.delete("EmpMapper.delOne",10086);
System.out.println(result);
Assert.assertEquals(result,1);
ss.commit();
ss.close();
}
}
后续添加。。。