关于在IDEA中装配持久层接口对象时,使用@Autowired默认报错的解决方案:
改为使用@Resource注解;
配置@Autowired的注解参数为required=false,即:@Autowired(required=false);
在接口之前添加@Repository注解。
如果直接执行以上单元测试,会出现以下错误:
Caused by: org.apache.ibatis.reflection.ReflectionException: Could not set property 'id' of 'class cn.tedu.blog.user.model.User' with value '1282871589072584705' Cause: java.lang.IllegalArgumentException: argument type mismatch
因在插入数据时,MyBatisPlus会自动生成Id值(例如以上错误信息中的1282871589072584705),需要显式的在实体类中与主键对应的属性之前添加@TableId注解,并且将注解属性type设置为IdType.AUTO:
@Data public class User { @TableId(value = "id", type = IdType.AUTO) private Integer id; // 忽略后续代码 }
然后,再次运行,即可正常插入数据。
另外,此次运行可以看到日志中输出了此次执行的SQL语句及相关信息,之所以会显示这些日志,是因为:
MyBatis框架默认就会输出这些信息;
必须在项目中添加SLF4j的依赖,以保证MyBatis输出日志;
MyBatis输出SQL日志的级别是Debug,必须将日志的显示级别设置的更低,例如设置为trace。
2. 项目前期准备–MyBatisPlusGenerator
2.1. 使用MyBatisPlusGenerator生成代码
在IDEA中创建straw项目,作为父级项目,在创建教程中,将Lombok、Spring Web、MySQL、MyBatis Framework并在其中创建straw-portal子模块项目:
MyBatisPlus Generator是一个代码生成器,通过使用它,运行后,就可以直接生成大量代码文件(例如Java类、接口、配置SQL的XML文件),然后,将这些文件复制到正式使用的项目中,就可以省去一些基础的创建过程!
首先,代码生成器的相关使用应该在一个独立的子模块项目中,避免与其它项目产生交集(不要在正式使用的项目中使用代码生成器)!所以,继续在straw父项目中创建代码生成器专用的子模块项目straw-generator,创建过程与一般子模块项目完全相同:
然后,通过http://doc.canglaoshi.org/config/mybatis-plus-generator.zip下载使用代码生成器必要的2个文件(在同一个压缩包中):
以上的2个文件,CodeGenerator是代码生成器的执行文件,通过调整其中的配置并执行即可生成所需要的文件,mapper.java.ftl是需要生成的Java类/接口文件的模版文件。
首先,在straw-generator子模块项目中,将原有的src文件夹下的test文件删除(也可以不删,主要是留着也没用),同样的,还可以将src下的启动类(StrawGeneratorApplication)和配置文件application.properties删除(也用不上)。
在straw-generator子模块项目的pom.xml中,添加必要的依赖:
<dependency> <groupId>com.baomidou</groupId> <artifactId>mybatis-plus-generator</artifactId> <version>3.3.2</version> </dependency> <dependency> <groupId>com.baomidou</groupId> <artifactId>mybatis-plus-extension</artifactId> <version>3.3.2</version> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-freemarker</artifactId> <version>2.3.1.RELEASE</version> </dependency>
然后,将下载解压得到的CodeGenerator.java文件直接复制到项目的cn.tedu.straw.generator包中,并打开该文件夹,检查各全局属性的值,特别是连接哪个数据库、连接数据库的用户名和密码,必须与自己当前使用的MySQL保持一致!还必须检查modelName属性的值,它表示当前聚合项目的某个子模块项目的名称,这个值将作用于最终生成的类、接口文件的包名:
确定无误后,在straw-generator子模块项目的src/main/resources下创建ftl文件夹,并将下载得到的mapper.java.ftl复制到这个文件夹中:
然后,回到CodeGenerator类中,将最后一个全局属性(用于配置模版文件的位置的属性)设置为"/ftl/mapper.java"(与以上放置文件的位置对应)。
package cn.tedu.straw.portal.mapper; import cn.tedu.straw.portal.model.User; import lombok.extern.slf4j.Slf4j; import org.junit.jupiter.api.Test; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.boot.test.context.SpringBootTest; import javax.jws.soap.SOAPBinding; import javax.sql.DataSource; import java.io.Serializable; import java.sql.Connection; import java.sql.SQLException; import java.util.List; @SpringBootTest @Slf4j public class UserMapperTests { @Autowired DataSource dataSource; @Autowired UserMapper userMapper; @Test void contextLoads() { log.debug("UserMapperTests.context"); } @Test void getConnection() throws SQLException { Connection connection = dataSource.getConnection(); log.debug("connection > {}", connection); } @Test void insert() { User user = new User(); user.setUsername("plus"); user.setPassword("1234"); int rows = userMapper.insert(user); log.debug("rows={}", rows); } @Test void selectById() { Integer id = 1; User user = userMapper.selectById(id); log.debug("user > {}", user); } @Test void selectList() { List<User> users = userMapper.selectList(null); log.debug("count={}", users.size()); for (User user : users) { log.debug("user > {}", user); } } }