一、mybatis的实现(现在mybatis大多都是通过spring和springboot集成了,因此这种方法很少用了,但是基本的流程要了解)
另外觉得字多的可以重点看我标注红,紫,蓝色的部分,这部分是重点!
1.新建maven项目,在pom.xml中导入相应的依赖
<!-- mybatis依赖--> <dependency> <groupId>org.mybatis</groupId> <artifactId>mybatis</artifactId> <version>3.5.1</version> </dependency> <!-- connection依赖--> <dependency> <groupId>mysql</groupId> <artifactId>mysql-connector-java</artifactId> <version>5.1.9</version> </dependency> <dependency> <groupId>org.junit.jupiter</groupId> <artifactId>junit-jupiter</artifactId> <version>RELEASE</version> <scope>compile</scope> </dependency> </dependencies>
2.由于后续过程中,我们需要配置mapper映射文件及mybatis配置文件,因此需要设置资源过滤路径(尤其是mapper映射文件,它需要跟mapper接口写在同一个包下,即mapper映射文件(dao.xml)会写在Java目录下
<resources> <resource> <directory>src/main/java</directory><!--所在的目录--> <includes><!--包括目录下的.properties,.xml 文件都会扫描到--> <include>**/*.properties</include> <include>**/*.xml</include> </includes> <filtering>false</filtering> </resource> </resources>
3.可以根据数据库中的数据表,创建相应的实体类,注意字段同数据表中的字段对应。
若存在实体类字段无法与表中字段名相对应的情况,则应在sql语句中使用别名进行处理。
下面仅是一个例子,读者可以根据自己的sql表进行创建
@Data @AllArgsConstructor @NoArgsConstructor public class Student { private Integer id; private String name; private String email; private Integer age; }
此处我们用到了lombok插件,通过注解@Data可生成get(),set(),toString()方法,通过@AllArgsConstructor 和@NoArgsConstructor可生成全参和无参构造方法,大大简化了代码量。
有关lombok的安装详见这篇博客:
(2条消息) Lombok插件安装(IDEA)、配置jar包、使用_Hern(宋兆恒)-CSDN博客_lombok插件安装
4.创建dao层
4.1创建dao接口(mapper接口)
接口里写出相应的增删改查方法即可(这里我只写了查,想看增删改的,看下面spring和springboot集成mybatis的即可)
public interface StudentDao { List<Student> selectStudents(); int insert(Student student); }
4.2创建mapper文件(重要!!)
mapper文件的作用主要是将sql语句和mapper接口的方法进行一一映射
根据下面的文件内容,我们可以看到xml文件中有namespace和id两个属性,sql语句和相应方法的映射就是通过这个语句来进行的,而映射的key值即为namespace+id,需要保证这个key值是唯一的,我们就可以找到相应的sql语句与之对应
在mybatis执行时,mybatis会生成mapper接口的代理类,代理类会拦截mapper接口的相应方法,并执行与之对应的sql语句
至于增删改查的类型,传入的参数值和返回值,可以通过标签来设定:
<select> <insert> <update> <delete>分别对应查询,插入,更新,删除
parameterType对应传入参数的类型,resultType对应返回参数的类型。int和string型参数可不进行配置,若进行配置,值可以直接写int 和string。但自定义类型的参数必须进行配置,相应的值要写全路径,若在全局配置文件中配置了type alias,值可以只写类名
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd"> <!-- namespace :必须有值,自定义的唯一字符串 推荐使用: dao 接口的全限定名称 namespace 与 id组合成唯一的key作为 Map <String, MapperStatement> 的 key使用的 --> <mapper namespace="com.cry.dao.StudentDao"> <!-- <select>: 查询数据, 标签中必须是 select 语句 id: sql 语句的自定义名称,推荐使用 dao 接口中方法名称, 使用名称表示要执行的 sql 语句 resultType: 查询语句的返回结果数据类型,使用全限定类名 --> <select id="selectStudents" resultType="com.cry.domain.Student"> <!-- 要执行的 sql 语句 --> select id,name,email,age from student </select> <insert id="insert" > insert into student(id,name,email,age) values(#{id},#{name},#{email},#{age}) </insert> </mapper>
5.配置mybatis全局配置文件(重要!)
resource目录下创建mybatis.xml文件
全局配置文件的我们的主要配置内容可分为三部分:
1)配置类的别名
<typeAliases>
2)配置数据库连接池及事务
<transactionManager>
<dataSource>
但这里要注意数据库连接的四要素通常情况下是不能写死的,也就是要动态地赋值,因此将这四个属性写到properties配置文件中,并导入mybatis.xml
jdbc.driver=com.mysql.jdbc.Driver jdbc.url=jdbc:mysql://localhost:3306/mybatisexe?characterEncoding=utf-8 jdbc.username=root jdbc.password=123456
3)配置mapper接口的路径
<mappers>
具体的配置文件内容如下:
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE configuration PUBLIC "-//mybatis.org//DTD Config 3.0//EN" "http://mybatis.org/dtd/mybatis-3-config.dtd"> <!-- 导入数据库的properties文件 --> <configuration> <properties resource="db.properties"/> <settings> <setting name="logImpl" value="STDOUT_LOGGING" /> </settings> <!-- 配置别名--> <typeAliases> <typeAlias type="com.cry.domain.Student" alias="student"/> </typeAliases> <!-- 配置 mybatis 环境 --> <environments default="mysql"> <!--id: 数据源的名称 --> <environment id="mysql"> <!-- 配置事务类型:使用 JDBC 事务(使用 Connection 的提交和回滚) --> <transactionManager type="JDBC"/> <!-- 数据源 dataSource :创建数据库 Connection 对象 type: POOLED 使用数据库的连接池--> <dataSource type="POOLED"> <!-- 连接数据库的四个要素 --> <property name="driver" value="${jdbc.driver}"/> <property name="url" value="${jdbc.url}"/> <property name="username" value="${jdbc.username}"/> <property name="password" value="${jdbc.password}"/> </dataSource> </environment> </environments> <mappers> <!-- mapper映射文件路径 --> <mapper resource="com/cry/dao/StudentDao.xml"/> </mappers> </configuration>
6.建立测试类,测试相应方法(重要!!)
测试方法所写的代码就是基础的模板,后面spring和springboot的集成都基于此
其主要思路如下:
1.以所写的全局配置文件生成sqlSessionFactory
2.通过sqlSessionFactory对象生成session
3.由于在dao层的mapper文件中sql语句已经与方法进行映射,我们此时调用session的相应方法即会执行相应的sql语句
4.输出我们查询后的结果即可
public class testStart { @Test public void testStart() throws IOException { //1.mybatis 主配置文件,文件写在根目录下 String config = "mybatis.xml"; //2. 读取配置文件,读取里面的数据库配置信息,及mapper接口中sql语句的所在的类 InputStream in = Resources.getResourceAsStream(config); //3. 创建 SqlSessionFactory 对象, , 目的是获取 Sql Session SqlSessionFactory factory = new SqlSessionFactoryBuilder().build(in); //4. 获取 SqlSession,SqlSession 能执行 sql 语句 SqlSession session = factory.openSession(); //5. 执行 SqlSession 的 selectList() 参数中name space +id 匹配相应sql语句 List<Student> studentList =session.selectList("com.cry.dao.StudentDao.selectStudents"); //6. 循环输出查询结果 studentList.forEach( student -> System.out.println(student.toString())); //7. 关闭 SqlSession ,释放资源 session.close(); }
可以看到方法执行成功
二、spring集成mybatis
1)导入相关依赖
<dependency> <groupId>org.mybatis</groupId> <artifactId>mybatis</artifactId> <version>3.5.2</version> </dependency> <dependency> <groupId>mysql</groupId> <artifactId>mysql-connector-java</artifactId> <version>5.1.17</version> </dependency> <dependency> <groupId>org.springframework</groupId> <artifactId>spring-jdbc</artifactId> <version>5.1.10.RELEASE</version> </dependency> <dependency> <groupId>org.mybatis</groupId> <artifactId>mybatis-spring</artifactId> <version>2.0.2</version> </dependency>
注意mybatis-spring的版本问题:
2)配置mapper接口及映射文件
方法同mybatis的相关操作,此处不再赘述方法
public interface StudentDao { List<Student> selectStudents(); int insert(Student student); }
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd"> <!-- namespace :必须有值,自定义的唯一字符串 推荐使用: dao 接口的全限定名称 namespace 与 id组合成唯一的key作为 Map <String, MapperStatement> 的 key使用的 --> <mapper namespace="com.cry.dao.StudentDao"> <!-- <select>: 查询数据, 标签中必须是 select 语句 id: sql 语句的自定义名称,推荐使用 dao 接口中方法名称, 使用名称表示要执行的 sql 语句 resultType: 查询语句的返回结果数据类型,使用全限定类名 --> <select id="selectStudents" resultType="com.cry.domain.Student"> <!-- 要执行的 sql 语句 --> select id,name,email,age from student </select> <insert id="insert" > insert into student(id,name,email,age) values(#{id},#{name},#{email},#{age}) </insert> </mapper>
3)整合mybatis全局配置文件(非常重要!!)
在mybatis配置文件中我已经分析过,mybatis全局配置文件分为3部分,而者三部分可以通过spring的全局配置文件来进行继承
在resoure目录下创建mybatis.xml
我标红的三部分就分别对应了之前mybatis.xml文件中的三个要素
<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd"> <!--配置dataSource --> <bean id="dataSource" class="org.springframework.jdbc.datasource.DriverManagerDataSource"> <property name="driverClassName" value="com.mysql.jdbc.Driver"/> <property name="url" value="jdbc:mysql://localhost:3306/springboot?useSSL=true&useUnicode=true&characterEncoding=utf8"/> <property name="username" value="root"/> <property name="password" value="123456"/> </bean> <!--配置sqlSessionFactory --> <bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean"> <property name="typeAliases" value="com.cry.domain.Student"/> <!--注入数据库--> <property name="dataSource" ref="dataSource"></property> <!-- mapperLocation--> <property name="mapperLocations" value="classpath:com/cry/dao/*.xml"/> </bean> <!--配置sqlSession --> <bean id="sqlSession" class="org.mybatis.spring.SqlSessionTemplate"> <constructor-arg ref="sqlSessionFactory"/> </bean> <bean id="studentDaoimpl" class="com.cry.dao.StudentDaoImpl"> <property name="sqlSession" ref="sqlSession"></property> </bean> </beans>
除此之外,我们再来看之前写的代码
@Test public void testStart() throws IOException { //1.mybatis 主配置文件,文件写在根目录下 String config = "mybatis.xml"; //2. 读取配置文件,读取里面的数据库配置信息,及mapper接口中sql语句的所在的类 InputStream in = Resources.getResourceAsStream(config); //3. 创建 SqlSessionFactory 对象, , 目的是获取 Sql Session SqlSessionFactory factory = new SqlSessionFactoryBuilder().build(in); //4. 获取 SqlSession,SqlSession 能执行 sql 语句 SqlSession session = factory.openSession(); //5. 执行 SqlSession 的 selectList() 参数中name space +id 匹配相应sql语句 List<Student> studentList =session.selectList("com.cry.dao.StudentDao.selectStudents"); //6. 循环输出查询结果 studentList.forEach( student -> System.out.println(student.toString())); //7. 关闭 SqlSession ,释放资源 session.close(); }
通过标红的部分我们可以看到mybatis执行需要一个session对象,而session对象需要通过sqlsessionFactory进行创建
所以我们需要注入sqlSessionFactory的bean对象,而通过观察代码我们可以看到sqlSessionFactory的生成需要一个参数,就是mybatis全局配置文件的输入流(将注释1-4的代码合并成一行)
这个文件对应的三部分通过property 分别进行注入,即为spring配置文件中红色部分,此时相当于我们通过spring配置文件完成了测试代码的1-4行
接下来,我们通过sqlSessionFactroy来生成一个session对象(spring配置文件中紫色部分),由于sqlSessionTemplate中并没有set方法,因此只能通过构造方法来进行赋值操作
接下来,写出接口的继承类,由于继承类中调用的其实是Mapper接口的方法,因此要注入Mapper接口的对象。在实现类中写出set方法,并在spring中进行配置(spring配置文件中蓝色部分)
实现类通过getMapper方法生成Mapper接口的代理类,执行相关的方法
public class StudentDaoImpl implements StudentDao{
//sqlSession不用我们自己创建了,Spring来管理
private SqlSessionTemplate sqlSession;
public void setSqlSession(SqlSessionTemplate sqlSession) {
this.sqlSession = sqlSession;
}
@Override
public List<tStudent> select() {
StudentDao mapper = sqlSession.getMapper(StudentDao.class);
return mapper.select();
}
}
最后,将实现类配置到spring配置文件中,这样我们可以通过bean获得实现类的对象
4.测试
至此,spring的配置文件已经帮我们生成了session对象,接口实现类完成了session对象的注入和Mapper接口代理类的创建,并执行相应的方法。之后我们再将实现类也通过bean配置到spring全局文件中去。
因此,测试类中,我们通过getBean()获取spring配置文件中的实现类对象,再调用这个对象的相关方法即可
@Test public void test7(){ ApplicationContext context = new ClassPathXmlApplicationContext("mybatis.xml"); StudentDaoImpl studentDaoimpl = context.getBean("studentDaoimpl", StudentDaoImpl.class); List<tStudent> studentList = studentDaoimpl.select(); for(tStudent student:studentList){ System.out.println(student.toString()); } }
三、springboot集成mybatis
springboot的集成将基于SSM进行展开
1.创建springboot工程,springboot工程创建步骤如下图
2.导入spring,springmvc,mybatis,数据库,lombok等依赖,并配置资源过滤路径
<?xml version="1.0" encoding="UTF-8"?> <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd"> <modelVersion>4.0.0</modelVersion> <groupId>com.example</groupId> <artifactId>demo</artifactId> <version>0.0.1-SNAPSHOT</version> <name>demo</name> <description>Demo project for Spring Boot</description> <properties> <java.version>1.8</java.version> <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding> <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding> <spring-boot.version>2.3.7.RELEASE</spring-boot.version> </properties> <dependencies> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-thymeleaf</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-devtools</artifactId> <scope>runtime</scope> <optional>true</optional> </dependency> <dependency> <groupId>org.projectlombok</groupId> <artifactId>lombok</artifactId> <optional>true</optional> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-test</artifactId> <scope>test</scope> <exclusions> <exclusion> <groupId>org.junit.vintage</groupId> <artifactId>junit-vintage-engine</artifactId> </exclusion> </exclusions> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-configuration-processor</artifactId> <version>2.4.8</version> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-jdbc</artifactId> <version>2.3.7.RELEASE</version> </dependency> <dependency> <groupId>mysql</groupId> <artifactId>mysql-connector-java</artifactId> <version>5.1.17</version> <scope>runtime</scope> </dependency> <dependency> <groupId>com.alibaba</groupId> <artifactId>druid</artifactId> <version>1.2.4</version> </dependency> <dependency> <groupId>org.mybatis.spring.boot</groupId> <artifactId>mybatis-spring-boot-starter</artifactId> <version>2.1.3</version> </dependency> </dependencies> <dependencyManagement> <dependencies> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-dependencies</artifactId> <version>${spring-boot.version}</version> <type>pom</type> <scope>import</scope> </dependency> </dependencies> </dependencyManagement> <build> <resources> <resource> <directory>src/main/java</directory> <includes> <include>**/*.xml</include> </includes> <filtering>true</filtering> </resource> </resources> <plugins> <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-compiler-plugin</artifactId> <version>3.8.1</version> <configuration> <source>1.8</source> <target>1.8</target> <encoding>UTF-8</encoding> </configuration> </plugin> <plugin> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-maven-plugin</artifactId> <version>2.3.7.RELEASE</version> <configuration> <mainClass>com.cry.DemoApplication</mainClass> </configuration> <executions> <execution> <id>repackage</id> <goals> <goal>repackage</goal> </goals> </execution> </executions> </plugin> <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-surefire-plugin</artifactId> <version>2.12.4</version> <configuration> <!--跳过项目运行测试用例--> <skipTests>true</skipTests> </configuration> </plugin> </plugins> </build> </project>
3.创建实体类
具体过程与上面两种方法相同,不再赘述。
@Data @NoArgsConstructor @AllArgsConstructor public class department { private int id; private String departmentName; }
4.创建dao层
具体过程与上面两种方法相同,不再赘述
@Mapper //告诉springboot此类为mapper接口 @Repository //表明这个类具有对数据库数据增删改查的功能 public interface departmentDao { //通过id查询部门 department selectById(int id); //查询所有部门 List<department> selectAll(); //更改部门的相关信息 int update(department department); //插入部门的信息 int insert(department department); //删除部门的信息 int delete(int id); }
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd"> <!-- namespace :必须有值,自定义的唯一字符串 推荐使用: dao 接口的全限定名称 --> <mapper namespace="com.cry.dao.departmentDao"> <!-- <select>: 查询数据, 标签中必须是 select 语句 id: sql 语句的自定义名称,推荐使用 dao 接口中方法名称, 使用名称表示要执行的 sql 语句 resultType: 查询语句的返回结果数据类型,使用全限定类名 --> <select id="selectById" resultType="com.cry.domain.department" parameterType="int"> <!-- 要执行的 sql 语句 --> select id,department_name as departmentName from department where id = #{id}; </select> <select id="selectAll" resultType="com.cry.domain.department"> select id,department_name as departmentName from department; </select> <update id="update" parameterType="department" > update department set department_name = #{departmentName} where id= #{id}; </update> <insert id="insert" parameterType="com.cry.domain.department"> insert into department (department_name) values (#{departmentName}); </insert> <delete id="delete" parameterType="int"> delete from department where id=#{id}; </delete> </mapper>
5.创建service层
这里首先说明一下,为什么要创建service层?因为dao层的方法只能执行单一的sql语句,无法进行其他的相关操作,那么这些操作只能有service层的方法来进行
为了避免代码冗余,实现代码的重复利用,我们把增删改查相关的方法写入接口类中,通过实现类来对方法进行重写
注意实现类应标注@Service表明这是springboot的服务层
public interface departmentService { department selectById(int id); List<department> selectAll(); int update(department department); int insert (department department); int delete (int id); }
@Service public class departmentServiceImpl implements departmentService{ @Autowired private departmentDao dao; public void setDao(departmentDao dao){ this.dao=dao; } @Override public department selectById(int id) { return dao.selectById(id); } @Override public List<department> selectAll() { return dao.selectAll(); } @Override public int update(department department) { return dao.update(department); } @Override public int insert(department department) { return dao.insert(department); } @Override public int delete(int id) { return dao.delete(id); } }
6.创建controller层
@RestController @RequestMapping("/department") public class departmentController { @Autowired private departmentService service; @RequestMapping("/selectById/{id}") public department select( @PathVariable("id") int id){ department department = service.selectById(id); return department; } @RequestMapping("/selectAll") public List<department> selectAll(){ List<department> departments = service.selectAll(); return departments; } @RequestMapping("/update/{id}") public List<department> update(@PathVariable("id")int id){ department dep = service.selectById(id); dep.setDepartmentName("法务部新"); service.update(dep); return selectAll(); } @RequestMapping("/insert") public List<department>insert(){ department department=new department(); department.setDepartmentName("法务部"); service.insert(department); return selectAll(); } @RequestMapping("/delete/{id}") public List<department> delete(@PathVariable("id") int id){ service.delete(id); return selectAll(); } }
这里注意几点:
1.@RestController相当于@Controller + @Responsebody,前者表示该类为springboot的控制层,后者表示返回的数据转换为JSON对象
2.@PathVariable表示获取url的占位符的值,并赋予相应的属性
四.总结:
1.介绍了mybatis的具体流程跟部分机理。
2.介绍了spring和springboot集成mybatis的操作。