在企业中为了提高开发效率,有很多通用代码实际上是直接使用代码生成器生成出来的。
官方网址:
http://mybatis.org/generator/
使用步骤:
1、添加插件
<plugins>
<plugin>
<groupId>org.mybatis.generatorgroupId>
<artifactId>mybatis-generator-maven-pluginartifactId>
<version>1.3.2version>
<configuration>
<verbose>trueverbose>
<overwrite>trueoverwrite>
configuration>
<dependencies>
<dependency>
<groupId>org.mybatisgroupId>
<artifactId>mybatisartifactId>
<version>3.4.6version>
dependency>
<dependency>
<groupId>mysqlgroupId>
<artifactId>mysql-connector-javaartifactId>
<version>5.1.25version>
dependency>
dependencies>
plugin>
plugins>
2、添加配置文件
配置好maven插件,下面需要配置插件需要天健的配置文件.
在maven项目下的src/main/resources 目录下建立名为maven的项目配置文件存放路径如下图:generatorConfig.xml 和 generator.properties 配置文件。
<generatorConfiguration>
<properties resource="generator.properties">properties>
<context id="default" targetRuntime="MyBatis3">
<commentGenerator>
<property name="suppressDate" value="true"/>
<property name="suppressAllComments" value="true"/>
commentGenerator>
<jdbcConnection
driverClass="${driver}"
connectionURL="${url}"
userId="${username}"
password="${password}">
jdbcConnection>
<javaTypeResolver>
<property name="forceBigDecimals" value="false"/>
javaTypeResolver>
<javaModelGenerator targetPackage="com.acoffee.maven.pojo" targetProject="src/main/java">
<property name="enableSubPackages" value="true"/>
<property name="constructorBased" value="true"/>
<property name="trimStrings" value="true"/>
<property name="immytable" value="false"/>
javaModelGenerator>
<sqlMapGenerator targetPackage="mapper" targetProject="src/main/resources">
<property name="enableSubPackages" value="false"/>
sqlMapGenerator>
<javaClientGenerator type="XMLMAPPER" targetPackage="com.acoffee.maven.dao" targetProject="src/main/java">
<property name="enableSubPackages" value="true"/>
javaClientGenerator>
<table tableName="dept" domainObjectName="Dept"
enableCountByExample="false" enableUpdateByExample="false"
enableDeleteByExample="false" enableSelectByExample="false"
selectByExampleQueryId="false">
table>
context>
generatorConfiguration>
3、Intellj配置
MyBatis Generator 生成代码的运行方式:命令行,使用Ant,使用Maven、Java编码、我们采用Maven插件mybatis-generator-maven-plugin来运行MyBatis Generator,用的是命令行的方式。
添加运行maven 的配置
将generatorConfig.xml配置文件中的table全部改为true:
<table tableName="dept" domainObjectName="Dept"
enableCountByExample="true" enableUpdateByExample="true"
enableDeleteByExample="true" enableSelectByExample="true"
selectByExampleQueryId="true">
table>
public class AppTest {
@Test
public void shouldAnswerWithTrue() {
SqlSession sqlSession = MyBatisUtil.createSession();
DeptMapper deptMapper = sqlSession.getMapper(DeptMapper.class);
DeptExample deptExample = new DeptExample();
DeptExample.Criteria criteria = deptExample.createCriteria();
// criteria.andDeptnoEqualTo(10);//按部门编号查
criteria.andDnameLike("%e%");//模糊查询
List<Dept> deptList = deptMapper.selectByExample(deptExample);
for (Dept dept : deptList) {
System.out.println(dept);
}
MyBatisUtil.closeSession(sqlSession);
}
}
执行结果:
其中还有很多功能:动态sql等等(这个组件算是比较古老的)。
注解 | 功能 |
---|---|
@Insert | 实现新增 |
@Update | 实现更新 |
@Delete | 实现删除 |
@Select | 实现查询 |
@Result | 实现结果集封装 |
@Results | 可以与@Result 一起使用,封装多个结果集 |
@ResultMap | 实现引用 |
@Results | 定义的封装 |
@One | 实现一对一结果集封装 |
@Many | 实现一对多结果集封装 |
@SelectProvider | 实现动态 SQL 映射 |
@CacheNamespace | 实现注解二级缓存的使用 |
1、MyBatis的基本注解
注解的方式没有映射文件
实体对象:
@Data
public class Dept {
private byte deptno;
private String dname;
private String loc;
private List<Emp> emps;
}
接口:
@Mapper
public interface DeptMapper {
@Insert("insert into dept(dname,loc)values(#{dname},#{loc})")
public void add(Dept dept);
@Delete("delete from dept where deptno=#{deptno}")
public void delete(byte deptno);
@Update("update dept set dname=#{dname},loc=#{loc} where deptno=#{deptno}")
public void update(Dept dept);
@Select("select * from dept where dept=#{dept}")
public Dept selectOne(byte deptno);
@Select("select * from dept")
public List<Dept> selectAll();
}
mybatis-config.xml配置文件:
<configuration>
<settings>
<setting name="logImpl" value="LOG4J"/>
<setting name="lazyLoadingEnabled" value="true">setting>
settings>
<typeAliases>
<package name="com.acoffee.maven.pojo">package>
typeAliases>
<environments default="mysql">
<environment id="mysql">
<transactionManager type="JDBC">transactionManager>
<dataSource type="POOLED">
<property name="driver" value="com.mysql.jdbc.Driver">property>
<property name="url" value="jdbc:mysql://localhost:3306/mydb?useUnicode=true&characterEncoding=UTF-8"/>
<property name="username" value="root">property>
<property name="password" value="7777">property>
dataSource>
environment>
environments>
<mappers>
<mapper class="com.acoffee.maven.mapper.DeptMapper">mapper>
mappers>
configuration>
测试文件:
查询全部
public class AppTest {
private Logger logger = Logger.getLogger(this.getClass());
@Test
public void testList(){
SqlSession sqlSession = MyBatisUtil.createSession();
DeptMapper deptMapper = sqlSession.getMapper(DeptMapper.class);
List<Dept> deptList = deptMapper.selectAll();
for (Dept dept:deptList) {
logger.info(dept);
}
MyBatisUtil.closeSession(sqlSession);
}
@Test
public void testAdd(){
SqlSession sqlSession = MyBatisUtil.createSession();
DeptMapper deptMapper = sqlSession.getMapper(DeptMapper.class);
Dept dept = new Dept();
dept.setDeptno((byte)50);
dept.setDname("研发部");
dept.setLoc("成都市");
deptMapper.add(dept);
sqlSession.commit();
MyBatisUtil.closeSession(sqlSession);
}
一对多
“一对多” 多的一方写@Many
实体对象:
Dept 类:
@Data
public class Dept {
private byte deptno;
private String dname;
private String loc;
private List<Emp> emps;
}
Emp类
@Data
public class Emp {
private short empno;
private String ename;
private String job;
private short mgr;
private Date hiredate;
private double sal;
private double comm;
}
接口:
DeptMapper
@Mapper
public interface DeptMapper {
@Results({
@Result(property = "deptno", column = "deptno"),
@Result(property = "dname", column = "dname"),
@Result(property = "loc", column = "loc"),
@Result(property = "emps", column = "deptno", many = @Many(select = "com.acoffee.maven.mapper.EmpMapper.slectEmpsByDeptno", fetchType = FetchType.EAGER))
})
@Select("select * from dept where deptno=#{deptno}")
public Dept selectOne(byte deptno);
}
EmpMapper
@Mapper
public interface EmpMapper {
@Select("select * from emp where deptno=#{deptno}")
public List<Emp> slectEmpsByDeptno(byte deptno);
}
测试文件:
@Test
public void testOneToMany() {
SqlSession sqlSession = MyBatisUtil.createSession();
DeptMapper deptMapper = sqlSession.getMapper(DeptMapper.class);
Dept dept = deptMapper.selectOne((byte) 10);
logger.info(dept);
MyBatisUtil.closeSession(sqlSession);
}
多对一
“多对一” 一的一方写@One
实体对象
Dept 类:
@Data
public class Dept {
private byte deptno;
private String dname;
private String loc;
private List<Emp> emps;
}
Emp 类:
@Data
public class Emp {
private short empno;
private String ename;
private String job;
private short mgr;
private Date hiredate;
private double sal;
private double comm;
private Dept depts;
}
接口:
EmpMapper
@Mapper
public interface EmpMapper {
@Results({
@Result(property = "empno",column = "empno"),
@Result(property = "ename",column = "ename"),
@Result(property = "job",column = "job"),
@Result(property = "mgr",column = "mgr"),
@Result(property = "hiredate",column = "hiredate"),
@Result(property = "sal",column = "sal"),
@Result(property = "comm",column = "comm"),
@Result(property = "depts",column = "deptno", one = @One(select = "com.acoffee.maven.mapper.DeptMapper.selectDeptByDeptnoWithStep",fetchType = FetchType.LAZY))
})
@Select("select * from emp where empno=#{empno}")
public Emp selectEmpByEmpno(Short empno);
}
@Mapper
public interface DeptMapper {
@Select("select * from dept where deptno=#{deptno}")
public Dept selectDeptByDeptnoWithStep(@Param("deptno")byte deptno);
}
测试文件:
@Test
public void testManyToOne() {
SqlSession sqlSession = MyBatisUtil.createSession();
EmpMapper empMapper = sqlSession.getMapper(EmpMapper.class);
Emp empno = empMapper.selectEmpByEmpno((short) 7369);
logger.info(empno);
MyBatisUtil.closeSession(sqlSession);
}
执行结果:
我们这里emps返回的null,如果我们想它继续返回部门的员工信息,可以直接将selectDeptByDeptnoWithStep改成一对多种的selectone的形式即可。
MyBatis动态SQL
使用 @SelectProvider 注解,type 参数是提供构建 SQL 的类,method 是构建 SQL 的方法。
接口:
@Mapper
public interface EmpMapper {
@SelectProvider(type = EmpDynamicSqlProvider.class,method = "select")
public List<Emp> selectEmpsByMap( String ename, Double sal);
}
EmpDynamicSqlProvider 方法:
public class EmpDynamicSqlProvider {
public String select(final String ename, final Double sal) {
String result = new SQL() {
{
SELECT("*");
FROM("emp");
StringBuilder sb = new StringBuilder();
if (ename != null && !"".equals(ename)) {
sb.append("AND ename Like");
sb.append("'%");
sb.append(ename);
sb.append("%'");
}
if (sal != null && sal != 0.0) {
sb.append("AND sal>");
sb.append(sal);
}
if (!"".equals(sb.toString())) {
WHERE(sb.toString().replaceFirst("AND", ""));
}
}
}.toString();
return result;
}
}
测试代码:
@Test
public void testDynamic() {
SqlSession sqlSession = MyBatisUtil.createSession();
EmpMapper empMapper = sqlSession.getMapper(EmpMapper.class);
List<Emp> emps = empMapper.selectEmpsByMap("s", 0.0);
for (Emp emp : emps) {
logger.info(emp);
}
MyBatisUtil.closeSession(sqlSession);
}
接口
@Mapper
@CacheNamespace//缓存配置
public interface EmpMapper {
.....
当然如果我们想去改变缓存的一些参数可以直接在@CacheNamespace
后面写即可,不设置就全是默认设置。
@CacheNamespace(eviction=LruCache.class flushInterval=60000 readOnly=true size=512)
序列化
@Data
public class Dept implements Serializable {
.....
@Data
public class Emp implements Serializable {
......
由于我们是关联查询所以连个都需要序列化。
测试代码:
@Test
public void testCache() {
SqlSession sqlSession = MyBatisUtil.createSession();
EmpMapper empMapper = sqlSession.getMapper(EmpMapper.class);
Emp emp = empMapper.selectEmpByEmpno((short) 7369);
logger.info(emp);
MyBatisUtil.closeSession(sqlSession);
SqlSession sqlSession2 = MyBatisUtil.createSession();
EmpMapper empMapper2 = sqlSession2.getMapper(EmpMapper.class);
Emp emp1 = empMapper2.selectEmpByEmpno((short) 7369);
logger.info(emp1);
MyBatisUtil.closeSession(sqlSession2);
}