Mybatis和Hibernate是Java很常用的两款ORM框架,Hibernate框架,强大但是有些过重,Mybatis相对轻量级一些,总之这两种框架各有优劣势,在国内,Mybatis的使用率明显高于Hibernate。由于我也是比较倾向于自己写SQL,所以,在工作中,Mybatis用得较为多一些,某些项目也在使用Hibernate。虽然Mybatis用得较多,但是也只是会一些简单的单表增、删、改、查操作,没有进行深入,最近稍微时间充裕一些,便想着花点精力去学复杂一些的场景。
我们去start.spring.io新建一个Spring Boot
项目,这选择了四个组件:
- spring-boot-starter-web
- mybatis-spring-boot-starter
- mysql-connector-java
- lombok
创建完成后,直接导入到IDEA中,现在先新建一张表:
1 2 3 4 5 6 7 8
| CREATE TABLE `mybatis`.`user` ( `id` int NOT NULL AUTO_INCREMENT, `name` varchar(32) NULL, `age` varchar(255) NULL, `phone` varchar(11) NULL, `address` varchar(255) NULL, PRIMARY KEY (`id`) );
|
并在user
中加入几条测试数据,现在我们去程序新建一个User类型作为映射类
1 2 3 4 5 6 7
| @Data public class User { private Long id; private String name; private int age; private String address; }
|
在application.yml
配置数据库连接
1 2 3 4 5 6 7
| spring: #数据库连接配置 datasource: driver-class-name: com.mysql.cj.jdbc.Driver url: jdbc:mysql://127.0.0.1:3306/mybatis?characterEncoding=utf-8&useSSL=false username: root password: root
|
准备就绪后,新建一个UserMapper
的接口,使用注解的方式来获取user
表中的数据,
1 2 3 4 5 6
| @Mapper public interface UserMapper { @Select("select * from user") List<User> queryUser(); }
|
@Mapper用于注入该Mapper接口,注入后就可以在IOC容器中使用,@Select用于查询数据,现在我们来调用该UserMapper
接口看看效果
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21
| @SpringBootApplication public class DemoApplication {
public static void main(String[] args) { SpringApplication.run(DemoApplication.class, args); }
private UserMapper userMapper; public DemoApplication(UserMapper userMapper){ this.userMapper=userMapper; }
@Bean CommandLineRunner commandLineRunner() { return args -> { List<User> users=userMapper.queryUser(); System.out.println(users); }; }
}
|
运行起来后,会看到如下效果:
1 2 3
| 2021-08-27 09:48:28.523 INFO 21728 --- [ main] com.zaxxer.hikari.HikariDataSource : HikariPool-1 - Starting... 2021-08-27 09:48:28.701 INFO 21728 --- [ main] com.zaxxer.hikari.HikariDataSource : HikariPool-1 - Start completed. [User(id=1, name=张三, age=60, address=四川某隐秘地区), User(id=2, name=李四, age=58, address=山东某隐秘地区)]
|
我们也可以看到,Spring Boot
默认会使用hikari
作为我们的数据库连接池。
Mybatis除了@Select
外,还有@Update
、@Insert
、@Delete
、@Results
等,前面三个注解,我相信大部分人并不陌生,顾名思义吗,就是单表的修改、新增和删除。那么@Results
是做什么的呢?Mybatis
作为ORM,那么它如何把表数据的字段和我们的类属性映射起来呢?一般是数据库的字段名和类的字段名能够匹配上,如果不能匹配上,那就想办法匹配上,比如在写查询语句的时候给字段加别名,或者是用 @Results
建立一个映射关系,我们来演示一把吧。
我们在user
表新增一个dept_name
字段,在字段中添加任意内容,然后在User
类中加上deptName
属性,再次运行看看效果
1 2 3
| 2021-08-27 10:16:21.659 INFO 44628 --- [ main] com.zaxxer.hikari.HikariDataSource : HikariPool-1 - Starting... 2021-08-27 10:16:22.064 INFO 44628 --- [ main] com.zaxxer.hikari.HikariDataSource : HikariPool-1 - Start completed. [User(id=1, name=张三, age=60, address=四川某隐秘地区, deptName=null), User(id=2, name=李四, age=58, address=山东某隐秘地区, deptName=null)]
|
我们可以看到deptName
没有值,接下来就想办法映射上,给字段加别名
1 2 3 4 5 6 7 8 9
| @Mapper public interface UserMapper { @Select("select id,name,age,address,dept_name deptName from user") List<User> queryUser(); }
2021-08-27 10:18:37.978 INFO 35624 --- [ main] com.zaxxer.hikari.HikariDataSource : HikariPool-1 - Starting... 2021-08-27 10:18:38.078 INFO 35624 --- [ main] com.zaxxer.hikari.HikariDataSource : HikariPool-1 - Start completed. [User(id=1, name=张三, age=60, address=四川某隐秘地区, deptName=OK), User(id=2, name=李四, age=58, address=山东某隐秘地区, deptName=很OK)]
|
接下来我们尝试用@Results
来建立映射关系
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
| @Mapper public interface UserMapper { @Select("select * from user") @Results(id="resultMap",value = { @Result(id = true,column = "id",property = "id"), @Result(column = "name",property = "name"), @Result(column = "age",property = "age"), @Result(column = "address",property = "address"), @Result(column = "dept_name",property = "deptName"), }) List<User> queryUser(); } 2021-08-27 10:22:17.198 INFO 35536 --- [ main] com.zaxxer.hikari.HikariDataSource : HikariPool-1 - Starting... 2021-08-27 10:22:17.376 INFO 35536 --- [ main] com.zaxxer.hikari.HikariDataSource : HikariPool-1 - Start completed. [User(id=1, name=张三, age=60, address=四川某隐秘地区, deptName=OK), User(id=2, name=李四, age=58, address=山东某隐秘地区, deptName=很OK)]
|
创建好的Results
是可以复用的,直接使用@ResultMap
注解,引用前面定义好的映射关系即可,我们把代码稍作修改
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45
| @Mapper public interface UserMapper { @Select("select * from user") @Results(id="resultMap",value = { @Result(id = true,column = "id",property = "id"), @Result(column = "name",property = "name"), @Result(column = "age",property = "age"), @Result(column = "address",property = "address"), @Result(column = "dept_name",property = "deptName"), }) List<User> queryUser();
@Select("select * from user where id=#{id}") @ResultMap(value = "resultMap") User queryUserById(Long id); }
@SpringBootApplication public class DemoApplication {
public static void main(String[] args) { SpringApplication.run(DemoApplication.class, args); }
private UserMapper userMapper; public DemoApplication(UserMapper userMapper){ this.userMapper=userMapper; }
@Bean CommandLineRunner commandLineRunner() { return args -> { List<User> users=userMapper.queryUser(); System.out.println(users); User user=userMapper.queryUserById(1L); System.out.println(user); }; }
}
2021-08-27 10:30:35.153 INFO 11916 --- [ main] com.zaxxer.hikari.HikariDataSource : HikariPool-1 - Starting... 2021-08-27 10:30:35.275 INFO 11916 --- [ main] com.zaxxer.hikari.HikariDataSource : HikariPool-1 - Start completed. [User(id=1, name=张三, age=60, address=四川某隐秘地区, deptName=OK), User(id=2, name=李四, age=58, address=山东某隐秘地区, deptName=很OK)] User(id=1, name=张三, age=60, address=四川某隐秘地区, deptName=OK)
|
当然,如果觉得定义Results
和写字段别名很麻烦,Mybatis
还给我们提供了另外一种方式,就是驼峰映射,只要我们的命名符合驼峰规则,便可使用,如果开启驼峰映射像上面的dept_name
就会去掉下划线,自动映射到deptName
上,那么我们如何开启驼峰映射呢?很简单,在配置文件中加入如下配置即可
1 2 3 4
| mybatis: #mapper配置文件 configuration: map-underscore-to-camel-case: true
|
好了,这里先就说到简单的使用@Select
、@Results
注解来获取单表数据,后面,我使用xml文件来代替注解的方式