在开发中基本都是要使用数据库,编写数据库层的代码。比如我们使用mybatis,需要建立表对应的POJO类,对应的mapper接口,对应的mapperxml文件,这些都是一些繁琐的代码,一般在开发中都会考虑自动生成这些代码,利用mybatis-generator-maven-plugin插件自动生成这些代码,解放大脑和手了。但是虽然自动生成了这些代码但是对于一些单表的简单查询还是需要我们写一些sql,这时候我们可以采用通用的mapper方式,让所有的mapper继承一个通用的mapper,这样一些简单的操作就自动有了。这样我们有更多的时间休息,享受生活了。下面是mybatis-generator-maven-plugin插件和集成通用mapper示例。
创建一个spring boot项目,确保项目已经集成了mybatis,参考:http://blog.csdn.net/j903829182/article/details/75643661
在第一步的基础上,添加通用mapper包的依赖和代码自动生成的依赖,并添加相应的插件,修改完成后的pom.xml代码如下:
4.0.0
com.jack
springbootstudy
0.0.1-SNAPSHOT
jar
springbootstudy
Demo project for Spring Boot
org.springframework.boot
spring-boot-starter-parent
1.5.4.RELEASE
UTF-8
UTF-8
1.8
${basedir}/src/main/java
com.jack.mapper
com.jack.entity
${basedir}/src/main/resources
mapper
org.springframework.boot
spring-boot-starter
org.springframework.boot
spring-boot-starter-test
test
org.springframework.boot
spring-boot-starter-web
org.springframework.cloud
spring-cloud-starter-eureka-server
1.3.1.RELEASE
org.springframework.cloud
spring-cloud-starter-feign
1.3.1.RELEASE
org.springframework.cloud
spring-cloud-starter-ribbon
1.3.1.RELEASE
org.springframework.boot
spring-boot-starter-jdbc
org.mybatis.spring.boot
mybatis-spring-boot-starter
1.3.0
mysql
mysql-connector-java
com.alibaba
druid
1.1.1
org.mybatis
mybatis
3.4.4
org.mybatis
mybatis-spring
1.3.1
tk.mybatis
mapper
3.4.2
org.springframework.boot
spring-boot-maven-plugin
org.mybatis.generator
mybatis-generator-maven-plugin
1.3.5
true
true
mysql
mysql-connector-java
5.1.42
runtime
tk.mybatis
mapper
3.4.2
generatorConfig.xml文件配置了代码自动生成的一些规则和基本属性,并配置通用mapper的插件,使所有的mapper都继承通用mapper,代码如下:
server:
port: 9092
spring:
application:
name: spring-cloud-consumer
datasource:
name: test
url: jdbc:mysql://192.168.9.107:3306/jack?characterEncoding=utf8&useSSL=true
username: root
password: root
#使用druid数据源
type: com.alibaba.druid.pool.DruidDataSource
driverClassName: com.mysql.jdbc.Driver
filters: stat
maxActive: 20
initialSize: 1
maxWait: 60000
minIdle: 1
timeBetweenEvictionRunsMillis: 60000
minEvictableIdleTimeMillis: 300000
validationQuery: select 'x'
testWhileIdle: true
testOnBorrow: false
testOnReturn: false
poolPreparedStatements: true
maxOpenPreparedStatements: 20
eureka:
client:
serviceUrl:
defaultZone: http://localhost:9090/eureka/
mybatis:
mapperLocations: classpath:mapper/*.xml #指定*Mapper.xml的位置
#设置日志级别,打印mybatis的日志
logging:
level:
root: debug
MybatisConfig是mybatis的配置类,代码如下:
package com.jack.config;
import com.alibaba.druid.pool.DruidDataSource;
import org.apache.ibatis.logging.LogFactory;
import org.apache.ibatis.session.SqlSessionFactory;
import org.mybatis.spring.SqlSessionFactoryBean;
import org.mybatis.spring.SqlSessionTemplate;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.core.env.Environment;
import org.springframework.core.io.support.PathMatchingResourcePatternResolver;
import org.springframework.core.io.support.ResourcePatternResolver;
import org.springframework.jdbc.datasource.DataSourceTransactionManager;
import javax.sql.DataSource;
/**
* Created by jackc on 2017/7/20.
*/
@Configuration
public class MybatisConfig {
/**
* 注入环境变量的值
*/
@Autowired
private Environment environment;
/**
* 获取数据源DataSource
* @return
*/
@Bean
public DataSource druidDataSource() {
DruidDataSource druidDataSource = new DruidDataSource();
druidDataSource.setUrl(environment.getProperty("spring.datasource.url"));
druidDataSource.setUsername(environment.getProperty("spring.datasource.username"));
druidDataSource.setPassword(environment.getProperty("spring.datasource.password"));
druidDataSource.setDriverClassName(environment.getProperty("spring.datasource.driverClassName"));
druidDataSource.setMaxActive(Integer.parseInt(environment.getProperty("spring.datasource.maxActive")));
druidDataSource.setInitialSize(Integer.parseInt(environment.getProperty("spring.datasource.initialSize")));
druidDataSource.setMaxWait(Long.parseLong(environment.getProperty("spring.datasource.maxWait")));
druidDataSource.setMinIdle(Integer.parseInt(environment.getProperty("spring.datasource.minIdle")));
druidDataSource.setTimeBetweenEvictionRunsMillis(Long.parseLong(environment.getProperty("spring.datasource.timeBetweenEvictionRunsMillis")));
druidDataSource.setMinEvictableIdleTimeMillis(Long.parseLong(environment.getProperty("spring.datasource.minEvictableIdleTimeMillis")));
druidDataSource.setValidationQuery(environment.getProperty("spring.datasource.validationQuery"));
druidDataSource.setTestWhileIdle(Boolean.parseBoolean(environment.getProperty("spring.datasource.testWhileIdle")));
druidDataSource.setTestOnBorrow(Boolean.parseBoolean(environment.getProperty("spring.datasource.testOnBorrow")));
druidDataSource.setTestOnReturn(Boolean.parseBoolean(environment.getProperty("spring.datasource.testOnReturn")));
druidDataSource.setPoolPreparedStatements(Boolean.parseBoolean(environment.getProperty("spring.datasource.poolPreparedStatements")));
druidDataSource.setMaxOpenPreparedStatements(Integer.parseInt(environment.getProperty("spring.datasource.maxOpenPreparedStatements")));
return druidDataSource;
}
/**
* 获取SqlSessionFactory
* @param druidDataSource
* @return
*/
@Bean(name = "sqlSessionFactory")
public SqlSessionFactory sqlSessionFactoryBean(DataSource druidDataSource) {
SqlSessionFactoryBean bean = new SqlSessionFactoryBean();
bean.setDataSource(druidDataSource);
bean.setTypeAliasesPackage("com.jack.entity");
LogFactory.useLog4JLogging();
//添加XML目录
ResourcePatternResolver resolver = new PathMatchingResourcePatternResolver();
String xmlPath = environment.getProperty("mybatis.mapperLocations");
try {
bean.setMapperLocations(resolver.getResources(xmlPath));
return bean.getObject();
} catch (Exception e) {
e.printStackTrace();
throw new RuntimeException(e);
}
}
/**
*
* @param sqlSessionFactory
* @return
*/
@Bean
public SqlSessionTemplate sqlSessionTemplate(SqlSessionFactory sqlSessionFactory) {
return new SqlSessionTemplate(sqlSessionFactory);
}
/**
* 增加事务
* @param druidDataSource
* @return
*/
@Bean
public DataSourceTransactionManager transactionManager(DataSource druidDataSource) {
return new DataSourceTransactionManager(druidDataSource);
}
}
MabatisMapperScanConfig类是mapper的扫描类:
package com.jack.config;
import org.springframework.boot.autoconfigure.AutoConfigureAfter;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import tk.mybatis.spring.mapper.MapperScannerConfigurer;
/**
* Created by jack on 2017/7/20.
*/
@Configuration
//注意,由于MabatisMapperScanConfig执行的比较早,所以必须有下面的注解
@AutoConfigureAfter(MybatisConfig.class)
public class MabatisMapperScanConfig {
@Bean
public MapperScannerConfigurer mapperScannerConfigurer() {
//不使用通用mapper的时候使用,org包开头的MapperScannerConfigurer扫描配置类
//MapperScannerConfigurer mapperScannerConfigurer = new MapperScannerConfigurer();
//使用通用mapper的时候,使用tk开头的MapperScannerConfigurer扫描配置类
MapperScannerConfigurer mapperScannerConfigurer = new MapperScannerConfigurer();
//注意这里的sqlSessionFactory就是MybatisConfig里面的sqlSessionFactoryBean方法,注解bean的名字
mapperScannerConfigurer.setSqlSessionFactoryBeanName("sqlSessionFactory");
//接口路径,通过这些接口调用sql的配置,操作数据库
mapperScannerConfigurer.setBasePackage("com.jack.mapper");
return mapperScannerConfigurer;
}
}
MapperScannerConfigurer必须是tk开头包里面的类
/*
Navicat MySQL Data Transfer
Source Server : MyLocalMySQL192.168.9.107
Source Server Version : 50718
Source Host : 192.168.9.107:3306
Source Database : jack
Target Server Type : MYSQL
Target Server Version : 50718
File Encoding : 65001
Date: 2017-07-24 15:06:07
*/
SET FOREIGN_KEY_CHECKS=0;
-- ----------------------------
-- Table structure for student
-- ----------------------------
DROP TABLE IF EXISTS `student`;
CREATE TABLE `student` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(12) DEFAULT NULL COMMENT '姓名',
`sex` tinyint(255) DEFAULT NULL COMMENT '性别,女为0,男为1',
`note` varchar(255) DEFAULT NULL COMMENT '备注',
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=8 DEFAULT CHARSET=utf8;
点击最下面的红色框的,进行代码的自动生成,如果没有问题,生成日志会输出building success。
1)生成的POJO对象Student.java,代码如下:
package com.jack.entity;
import javax.persistence.*;
public class Student {
@Id
private Integer id;
/**
* 姓名
*/
private String name;
/**
* 性别,女为0,男为1
*/
private Byte sex;
/**
* 备注
*/
private String note;
/**
* @return id
*/
public Integer getId() {
return id;
}
/**
* @param id
*/
public void setId(Integer id) {
this.id = id;
}
/**
* 获取姓名
*
* @return name - 姓名
*/
public String getName() {
return name;
}
/**
* 设置姓名
*
* @param name 姓名
*/
public void setName(String name) {
this.name = name;
}
/**
* 获取性别,女为0,男为1
*
* @return sex - 性别,女为0,男为1
*/
public Byte getSex() {
return sex;
}
/**
* 设置性别,女为0,男为1
*
* @param sex 性别,女为0,男为1
*/
public void setSex(Byte sex) {
this.sex = sex;
}
/**
* 获取备注
*
* @return note - 备注
*/
public String getNote() {
return note;
}
/**
* 设置备注
*
* @param note 备注
*/
public void setNote(String note) {
this.note = note;
}
}
2)查看生成的mapper,StudentMapper.java代码如下:
package com.jack.mapper;
import com.jack.entity.Student;
import tk.mybatis.mapper.common.Mapper;
/**
* StudentMapper集成了通用Mapper,提供了单表的基础操作
*/
public interface StudentMapper extends Mapper {
}
package com.jack.controller;
import com.jack.entity.Student;
import com.jack.mapper.StudentMapper;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
/**
* Created by jack on 2017/7/24.
* 使用通用mapper进行操作
* 文档地址:https://mapperhelper.github.io/docs/
*/
@RestController
public class StudentTestController {
@Autowired
StudentMapper studentMapper;
/**
*添加学生
* @return
*/
@RequestMapping(value = "/student/add")
public String addStudent(){
Student student = new Student();
student.setName("jackmapper1");
student.setSex((byte) 0);
student.setNote("采用通用mapper和代码自动生成");
int result = studentMapper.insert(student);
if (result > 0) {
return "添加学生成功";
}else {
return "添加学生失败";
}
}
/**
* 删除学生
* @return
*/
@RequestMapping(value = "/student/delete")
public String deleteStudent(){
Student student = new Student();
student.setId(2);
int result = studentMapper.delete(student);
if (result > 0) {
return "删除学生成功";
}else {
return "删除学生失败";
}
}
/**
* 更新学生信息
* @return
*/
@RequestMapping(value = "/student/update")
public String updateStudent(){
Student student = new Student();
student.setId(3);
student.setName("nameupdate");
student.setSex((byte) 0);
student.setNote("this is update note");
int result = studentMapper.updateByPrimaryKey(student);
if (result > 0) {
return "修改学生成功";
}else {
return "修改学生失败";
}
}
/**
* 查找学生信息
* @return
*/
@RequestMapping(value = "/student/select")
public Student selectStudent(){
Student student = new Student();
student.setId(5);
Student result = studentMapper.selectByPrimaryKey(student);
return result;
}
}
通用mapper只提供了基本的单表操作的功能,如果需要负责的功能,只要在对应的mapper文件写接口,然后在对应的xml文件里面写sql就行了,然后在需要的地方调用接口,就可以使用复杂的sql操作数据库了。
项目的完整代码在github上,代码如下:https://github.com/wj903829182/springboot/tree/master/springbootstudy