springboot集成mybatis-plus3.1

springboot集成mybatis-plus

  • 1.mybatis-plus说明
  • 2.开发环境
  • 3. 编码常用类
  • 4.mybatis-plus构造器QueryWrapper说明
  • 5. 整合mybatis-plus基本完成,但是在集成过程中出现了两个bug:
    • 1. java传递多个基本参数会报错:
    • 2.项目启动没有报错,但是调用接口的时候会报错:

1.mybatis-plus说明

MyBatis-Plus(简称 MP)是一个 MyBatis 的增强工具,在 MyBatis 的基础上只做增强不做改变,为简化开发、提高效率而生,最近工作中需要使用,所以结合其他稍作整理,以后他用;

2.开发环境

MyBatis-Plus版本: 3.1.0
SpringBoot版本:2.2.6
JDK版本:1.8
Maven: 3.5
maven依赖:

<parent>
		<groupId>org.springframework.bootgroupId>
		<artifactId>spring-boot-starter-parentartifactId>
		<version>2.2.6.RELEASEversion>
	parent>

	<properties>
		<java.version>1.8java.version>
	properties>
	
	<dependencies>
		<dependency>
			<groupId>org.springframework.bootgroupId>
			<artifactId>spring-boot-starter-webartifactId>
		dependency>
		<dependency>
			<groupId>mysqlgroupId>
			<artifactId>mysql-connector-javaartifactId>
			<scope>runtimescope>
		dependency>
		<dependency>
			<groupId>org.projectlombokgroupId>
			<artifactId>lombokartifactId>
			<optional>trueoptional>
		dependency>
		<dependency>
			<groupId>org.springframework.bootgroupId>
			<artifactId>spring-boot-starter-testartifactId>
			<scope>testscope>
		dependency>
		
		<dependency>
			<groupId>com.baomidougroupId>
			<artifactId>mybatis-plus-boot-starterartifactId>
			<version>3.1.0version>
		dependency>
		
		<dependency>
			<groupId>com.alibabagroupId>
			<artifactId>druidartifactId>
			<version>1.1.6version>
		dependency>
	dependencies>
	<build>
		<plugins>
			<plugin>
				<groupId>org.springframework.bootgroupId>
				<artifactId>spring-boot-maven-pluginartifactId>
			plugin>
		plugins>
	build>

application.yml配置如下:

# server config
server:
  port: 8081
# dataSource config
spring:
  datasource:
    driver-class-name: com.mysql.cj.jdbc.Driver
    url: jdbc:mysql://127.0.0.1:3306/mybatis_plus?useUnicode=true&characterEncoding=utf-8&serverTimezone=UTC
    username: root
    password: root
#mybatis-plus config
mybatis-plus:
  type-aliases-package: com.changcheng.pojo
  # xml 扫描,多个目录用逗号分开
  mapper-locations: classpath:mapper/*.xml
  #一下配置均有默认值,可以不配置
  global-config:
    db-config:
      #数据库类型
      db-type: MYSQL
      #主键类型  auto:"数据库ID自增" 1:"用户输入ID",2:"全局唯一ID (数字类型唯一ID)", 3:"全局唯一ID UUID";
      id-type: auto
      #字段策略 IGNORED:"忽略判断"  NOT_NULL:"非 NULL 判断")  NOT_EMPTY:"非空判断"
      field-strategy: NOT_EMPTY
  configuration:
    # 是否开启自动驼峰命名规则映射:从数据库列名到Java属性驼峰命名的类似映射
    map-underscore-to-camel-case: true
    # 如果查询结果中包含空值的列,则 MyBatis 在映射的时候,不会映射这个字段
    call-setters-on-nulls: true
    # 这个配置会将执行的sql打印出来,在开发或测试的时候可以用
    log-impl: org.apache.ibatis.logging.stdout.StdOutImpl   
  

表结构和数据:

-- ----------------------------
-- Table structure for user_info
-- ----------------------------
DROP TABLE IF EXISTS `user_info`;
CREATE TABLE `user_info` (
  `id` bigint(11) NOT NULL AUTO_INCREMENT COMMENT 'ID',
  `name` varchar(32) DEFAULT NULL COMMENT '姓名',
  `age` int(11) DEFAULT NULL COMMENT '年龄',
  `skill` varchar(32) DEFAULT NULL COMMENT '技能',
  `evaluate` varchar(64) DEFAULT NULL COMMENT '评价',
  `fraction` bigint(11) DEFAULT NULL COMMENT '分数',
  PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=16 DEFAULT CHARSET=utf8mb4 COMMENT='学生信息表';

-- ----------------------------
-- Records of user_info
-- ----------------------------
INSERT INTO `user_info` VALUES ('1', '小明', '20', '画画', '该学生在画画方面有一定天赋', '89');
INSERT INTO `user_info` VALUES ('2', '小兰', '19', '游戏', '近期该学生由于游戏的原因导致分数降低了', '64');
INSERT INTO `user_info` VALUES ('3', '张张', '18', '英语', '近期该学生参加英语比赛获得二等奖', '90');
INSERT INTO `user_info` VALUES ('4', '大黄', '20', '体育', '该学生近期由于参加篮球比赛,导致脚伤', '76');
INSERT INTO `user_info` VALUES ('5', '大白', '17', '绘画', '该学生参加美术大赛获得三等奖', '77');
INSERT INTO `user_info` VALUES ('7', '小龙', '18', 'JAVA', '该学生是一个在改BUG的码农', '59');
INSERT INTO `user_info` VALUES ('9', 'Sans', '18', '睡觉', 'Sans是一个爱睡觉,并且身材较矮骨骼巨大的骷髅小胖子', '60');
INSERT INTO `user_info` VALUES ('10', 'papyrus', '18', 'JAVA', 'Papyrus是一个讲话大声、个性张扬的骷髅,给人自信、有魅力的骷髅小瘦子', '58');
INSERT INTO `user_info` VALUES ('11', '删除数据1', '3', '画肖像', null, '61');
INSERT INTO `user_info` VALUES ('12', '删除数据2', '3', null, null, '61');
INSERT INTO `user_info` VALUES ('13', '删除数据3', '3', null, null, '61');
INSERT INTO `user_info` VALUES ('14', '删除数据4', '5', '删除', null, '10');
INSERT INTO `user_info` VALUES ('15', '删除数据5', '6', '删除', null, '10');

3. 编码常用类

springboot启动类:

@SpringBootApplication
@MapperScan(basePackages= {"com.changcheng.mapper"})//扫描mapper
public class DemoApplication {

	public static void main(String[] args) {
		SpringApplication.run(DemoApplication.class, args);
	}
}

web类:

@RestController
@RequestMapping("/userInfo")
public class UserInfoWeb {

	@Autowired
	private UserInfoService userInfoService;

	/**
	 * 查询全部
	 * 
	 * @return
	 */
	@RequestMapping("/list")
	public List<UserInfo> list() {
		List<UserInfo> list = userInfoService.list();
		return list;
	}

	/**
	 * 根据id查询
	 * 
	 * @param userId
	 * @return
	 */
	@RequestMapping("/getUserInfo")
	public UserInfo getUserInfo(String userId) {
		UserInfo userInfo = userInfoService.getById(userId);
		return userInfo;
	}

	/**
	 * 分页查询
	 * 
	 * @param curr
	 * @param limit
	 * @return
	 */
	@RequestMapping("/getListForPage")
	public IPage<UserInfo> getListForPage(int curr, int limit) {
		IPage<UserInfo> page = new Page<UserInfo>();
		page.setCurrent(curr);
		page.setSize(limit);
		page = userInfoService.page(page);
		return page;

	}

	/**
	 * 根据指定字段查询
	 * key是字段名, value是字段值
	 * 
	 * @return
	 */
	@RequestMapping("/getListForCondition")
	public Collection<UserInfo> getListForCondition() {
		Map<String, Object> map = new HashMap<>();
		// key是字段名, value是字段值
		map.put("age", 20);
		Collection<UserInfo> userInfos = userInfoService.listByMap(map);
		return userInfos;

	}

	/**
	 * 新增用户
	 */
	@RequestMapping("/saveInfo")
	public void saveInfo() {
		UserInfo userInfo = UserInfo.builder().name("小红").skill("Java").age(32).fraction(50L).evaluate("冒牌程序中的码农")
				.build();
		userInfoService.save(userInfo);
	}

	/**
	 * 批量新增
	 */
	@RequestMapping("/saveList")
	public void saveList() {
		UserInfo userInfo1 = UserInfo.builder().name("小红1").skill("Java").age(32).fraction(50L).evaluate("冒牌程序中的码农")
				.build();
		UserInfo userInfo2 = UserInfo.builder().name("小红2").skill("Java").age(32).fraction(50L).evaluate("冒牌程序中的码农")
				.build();
		List<UserInfo> list = new ArrayList<>();
		list.add(userInfo1);
		list.add(userInfo2);
		userInfoService.saveBatch(list);
	}

	/**
	 * 根据id更新 
	 * 根据id更新,其他字段为null则不会更新;
	 */
	@RequestMapping("/updateUserInfo")
	public void updateUserInfo() {
		// 根据id更新,其他字段为null则不会更新;
		UserInfo userInfo = UserInfo.builder().id(1L).age(20).build();
		userInfoService.updateById(userInfo);
	}

	/**
	 * 新增或更新 
	 * 传入的实体类中id为null,则增加; 
	 * 实体类id存在,如果数据库中存在id就会更新,如果不存在就会新增;
	 */
	@RequestMapping("/saveOrupdateUserInfo")
	public void saveOrupdateUserInfo() {
		// 传入的实体类中id为null,则增加;
		// 实体类id存在,如果数据库中存在id就会更新,如果不存在就会新增;
		UserInfo userInfo = UserInfo.builder().id(1L).age(33).build();
		userInfoService.saveOrUpdate(userInfo);
	}
	
	/**
	 * 根据id删除
	 */
	@RequestMapping("/deleteUserInfo")
	public void deleteUserInfo(String userId) {
		userInfoService.removeById(userId);
	}
	
	/**
	 * 批量删除
	 */
	@RequestMapping("/deleteBatchUserInfo")
	public void deleteBatchUserInfo() {
		List<String>list=new ArrayList<>();
		list.add("11");
		list.add("12");
		userInfoService.removeByIds(list);
	}
	
	/**
	 * 根据字段条件删除
	 * key 是字段名,value是字段值
	 */
	@RequestMapping("/deleteUserByCondition")
	public void deleteUserByCondition() {
		Map<String,Object>map=new HashMap<>();
		map.put("skill", "删除");
		map.put("fraction", 10L);
		userInfoService.removeByMap(map);
	}
	
	/**
	 * mp的扩展:MyBatis-Plus的QueryWrapper条件构造器
	 */
	
	@RequestMapping("/getListPlus")
	public Map<String,Object> getListPlus(){
		Map<String,Object> result=new HashMap<>();
		
		//查询条件 age=18
		QueryWrapper<UserInfo> queryWrapper1=new QueryWrapper<>();
		queryWrapper1.lambda().eq(UserInfo::getAge, 18);
		List<UserInfo> list1 = userInfoService.list(queryWrapper1);
		result.put("age=18", list1);
		
		//查询条件 age>5 and age<=18
		QueryWrapper<UserInfo> queryWrapper2=new QueryWrapper<>();
		queryWrapper2.lambda().gt(UserInfo::getAge, 5);
		queryWrapper2.lambda().le(UserInfo::getAge, 18);
		List<UserInfo> list2 = userInfoService.list(queryWrapper2);
		result.put(" age>5 and age<=18", list2);
		
		//模糊查询技能字段有'画'的数据并按照age降序
		QueryWrapper<UserInfo> queryWrapper3=new QueryWrapper<>();
		queryWrapper3.lambda().like(UserInfo::getSkill, "画");
		queryWrapper3.lambda().orderByDesc(UserInfo::getAge);
		List<UserInfo> list3 = userInfoService.list(queryWrapper3);
		result.put("like 画  and age 降序", list3);
		
		//模糊查询名字有‘小’ or age >18
		QueryWrapper<UserInfo> queryWrapper4=new QueryWrapper<>();
		queryWrapper4.lambda().like(UserInfo::getName, "小");
		queryWrapper4.lambda().or().gt(UserInfo::getAge, 18);
		List<UserInfo> list4 = userInfoService.list(queryWrapper4);
		result.put("like name or age>18", list4);
		
		//查询评价不为null and 分页
		IPage<UserInfo>page=new Page<>(1,5);
		QueryWrapper<UserInfo> queryWrapper5=  new QueryWrapper<>();
		queryWrapper5.lambda().isNotNull(UserInfo::getEvaluate);
		page = userInfoService.page(page, queryWrapper5);
		result.put("page", page);
		return result;
		
	}
	
	/**
	 * 自定义sql
	 * @return
	 */
	@RequestMapping("/getPage")
	public IPage<UserInfo> getPage(){
		IPage<UserInfo> page=new Page<>(1,5);
		page=userInfoService.selectListByFraction(page,60L);
		return page;
	}
}

service接口和实现类:

public interface UserInfoService extends IService<UserInfo>{

	IPage<UserInfo> selectListByFraction(IPage<UserInfo> page, Long fraction);

}
@Service
@Transactional
public class UserInfoServiceImpl extends ServiceImpl<UserInfoMapper, UserInfo> implements UserInfoService {

	@Override
	public IPage<UserInfo> selectListByFraction(IPage<UserInfo> page, Long fraction) {
		return this.baseMapper.selectListByFraction(page,fraction);
	}

}

pojo类:

@Data
@Builder
//@TableName中的值对应着表名
@TableName("user_info")
public class UserInfo {
	/**
	 * 主键
	 * @TableId 中可以决定主键的类型,不写会采用默认值,默认值可以在yml中配置
	 * AUTO: 数据库ID自增
     * INPUT: 用户输入ID
     * ID_WORKER: 全局唯一ID,Long类型的主键
     * ID_WORKER_STR: 字符串全局唯一ID
     * UUID: 全局唯一ID,UUID类型的主键
     * NONE: 该类型为未设置主键类型
	 */
	@TableId(value="id",type=IdType.AUTO)
	private Long id;
	
	private String name;
	
	private Integer age;
	
	private String skill;
	
	private String evaluate;
	
	private Long fraction;
}

分页插件config类:

@Configuration
public class MybatisPlusConfig {
	/**
	 * 分页插件
	 * 
	 * @return
	 */
	@Bean
	public PaginationInterceptor paginationInterceptor() {
		return new PaginationInterceptor();
	}
}

mapper接口:

public interface UserInfoMapper extends BaseMapper<UserInfo>{

	IPage<UserInfo> selectListByFraction(IPage<UserInfo> page,@Param("fraction") Long fraction);

}

xml配置文件:


  
<mapper namespace="com.changcheng.mapper.UserInfoMapper">
<select id="selectListByFraction" resultType="com.changcheng.pojo.UserInfo" parameterType="long">
		SELECT * FROM user_info WHERE fraction > #{fraction}
	select>      
mapper>

4.mybatis-plus构造器QueryWrapper说明

当查询条件复杂的时候,可以使用MP的QueryWrapper进行查询,比较快速:
springboot集成mybatis-plus3.1_第1张图片

5. 整合mybatis-plus基本完成,但是在集成过程中出现了两个bug:

1. java传递多个基本参数会报错:

org.apache.ibatis.binding.BindingException
Parameter ‘fraction’ not found. Available parameters are [arg1, arg0, param1, param2]] with root cause

解决方案:在传递的形参前面进行转义,使用注解 @Param(“xxx”) 即可;

IPage<UserInfo> selectListByFraction(IPage<UserInfo> page,@Param("fraction") Long fraction);

2.项目启动没有报错,但是调用接口的时候会报错:

The server time zone value ‘�й���׼ʱ��’ is unrecognized or represents more than one time zone. You must configure either the server or JDBC driver (via the serverTimezone configuration property) to use a more specifc time zone value if you want to…

解决方案:在application.yml配置文件中添加:serverTimezone=UTC

url: jdbc:mysql://127.0.0.1:3306/mybatis_plus?useUnicode=true&characterEncoding=utf-8&serverTimezone=UTC

你可能感兴趣的:(springboot)