Spring第四谈(spring和MyBatis的整合、spring的事务处理)

在这里插入图片描述

本人是一名物联网工程专业大二的学生,是互联网浪潮中一朵小小的浪花,写博客即是为了记录自己的学习历程,又希望能够帮助到很多和自己一样处于起步阶段的萌新。临渊羡鱼,不如退而结网。一起加油!
博客主页:https://blog.csdn.net/qq_44895397

Spring整合MyBatis

步骤:

    1、新建maven项目
    2、加入maven依赖
        1)spring依赖
        2)mybatis依赖
        3)MySQL驱动
        4)spring的事务依赖
        5)mybatis和spring的集成依赖:mybatis官方提供的,用来在spring框架中创建mybatis的SqlSessionFactory,dao对象的
    3、创建实体类(封装数据库中查询出来的数据)
    4、dao接口和sql映射文件(mapper文件)
    5、mybatis主配置文件
    6、创建service接口和实现类,属性是dao(在service层调用dao层的方法)
    7、创建spring的配置文件:声明mybatis的对象交给spring创建
        1)数据源(DateSource)数据库连接池相关的属性
        2)SqlSessionFeactory
        3)Dao对象SqlSessionFeactory.getMapper(dao.class)
        4)声明自定义的service
    8、创建测试类,获取service对象,通过service调用dao完成数据库的访问

1、新建maven项目

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

2、加入maven依赖

<!--spring依赖ioc-->
	<dependency>
		<groupId>org.springframework</groupId>
		<artifactId>spring-context</artifactId>
		<version>5.2.5.RELEASE</version>
	</dependency>
	<!--spring事务依赖-->
	<dependency>
		<groupId>org.springframework</groupId>
		<artifactId>spring-tx</artifactId>
		<version>5.2.5.RELEASE</version>
	</dependency>
	<dependency>
		<groupId>org.springframework</groupId>
		<artifactId>spring-jdbc</artifactId>
		<version>5.2.5.RELEASE</version>
	</dependency>
	
	<!--mybatis依赖-->
	<dependency>
		<groupId>org.mybatis</groupId>
		<artifactId>mybatis</artifactId>
		<version>3.5.1</version>
	</dependency>
	<!--mybatis和spring集成的依赖-->
	<dependency>
		<groupId>org.mybatis</groupId>
		<artifactId>mybatis-spring</artifactId>
		<version>1.3.1</version>
	</dependency>
	<!--mysql驱动-->
	<dependency>
		<groupId>mysql</groupId>
		<artifactId>mysql-connector-java</artifactId>
		<version>8.0.19</version>
	</dependency>
	<!--阿里公司的数据库连接池-->
	<dependency>
		<groupId>com.alibaba</groupId>
		<artifactId>druid</artifactId>
		<version>1.1.12</version>
	</dependency>

3、创建实体类(封装数据库中查询出来的数据)

4、dao接口和sql映射文件(mapper文件)

在这里插入图片描述
在pom.xml文件中添加插件:

<resources>
	<resource>
		<directory>src/main/java</directory><!--所在的目录-->
			<includes>
				<include>**/*.xml</include>
				<include>**/*.properties</include>
			</includes>
		<filtering>false</filtering>
	</resource>
	<resource>
		<directory>src/main/resources</directory>
			<includes>
				<include>**/*.xml</include>
				<include>**/*.properties</include>
			</includes>
		<filtering>true</filtering>
	</resource>
</resources>

5、mybatis主配置文件

mabatis的主配置文件中的数据源放入到spring框架中去声明

现在的mybatis主配置文件:

  <!--起别名 name,包名,该包下的所有类别名默认是类名-->
    <typeAliases>
        <package name="com.yky.domain"/>
    </typeAliases>


    <!--mysql映射文件的位置 一个mysql映射文件一个mapper
     <mapper resource=""/>
     -->
    <mappers>
        <!--该包下的所有mapper文件一次都能加载-->
        <package name="com.yky.dao"/>
    </mappers>

6、创建spring的配置文件:声明mybatis的对象交给spring创建

  1. 数据源(DateSource)数据库连接池相关的属性
  2. SqlSessionFeactory
  3. Dao对象SqlSessionFeactory.getMapper(dao.class)
  4. 声明自定义的service

提供链接数据库的信息(数据源)

<bean id="druidDataSource" class="com.alibaba.druid.pool.DruidDataSource"
      init-method="init" destroy-method="close">
	<!--Druid会自动跟url识别驱动类名,如果连接的数据库非常见数据库,配置属性driverClassName-->
	<property name="url" value="jdbc:mysql://localhost:3306/bjpowernode?
				        serverTimezone=UTC&amp;amp&amp;characterEncoding=utf-8" />
	<property name="username" value="root" />
	<property name="password" value="yky" />
	<!--最大连接数-->
	<property name="maxActive" value="20" />
</bean>

声明的是mybatis中提供的SqlSessionFactoryBean类,这个类内部创建 SqlSessionFactory的

<bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">
	<!--set注入,吧数据库连接池付给了dataSource属性-->
	<property name="dataSource" ref="druidDataSource" />
	<!--mybatis主配置文件的路径
	属性是:Resource,读取配置文件
	赋值,使用value,指定文件路径,使用classpath:表示文件的位置
	-->
	<property name="configLocation" value="classpath:mybatis.xml" />
</bean>

创建dao对象 ,使用SqlSession的getMepper(StudentDao.class)
MapperScannerConfigurer:在内部调用getMepper()生成每个dao接口的代理对象

<bean class="org.mybatis.spring.mapper.MapperScannerConfigurer">
	<property name="sqlSessionFactoryBeanName" value="sqlSessionFactory" />
	<!--
	指定包名,包名是dao接口所在的包名
	MapperScannerConfigurer会扫描这个包中的所有接口,把每个接口都执行
	一次getMapper()方法,得到每个接口的dao对象
	创建好的dao对象放入到spring的容器中,dao对象的默认名称是接口的首字母小写在
	-->
	<property name="basePackage" value="com.yky.Dao" />
</bean>

Spring框架的事务

1、什么是事务?

  • 讲mysql的时候,提出了事务。事务是指一组sql语句的集合,集合中有多条sql语句可能是insert,delete,update,select,我们希望这些多个sql语句能够成功,或者都失败,这些sql语句的执行是一致的,作为一个整体执行

2、在什么时候想到使用事务?

  • 当我的操作,涉及到多个表,或者是多个语句的insert,delete,update。需要保证语句都成功才能完成我的功能,或者都失败,保证操作是符合要求的

控制事务,事务应该放在哪里?

  • service类的业务方法会调用多个dao方法,执行多个sql语句

3、通常使用JDBC访问数据库,还是mybatis访问数据库怎么处理事务?

jdbc访问数据库,处理事务Connection con;con.commit();con.rollback();
mybatis访问数据库,处理事务,SqlSession.commit();SqlSession.rollback();

4.3问题中事务中的处理方法,有什么不足?

  1. 不同的数据库访问技术,处理事务的对象,方法不同,需要了解不同数据库访问技术使用事务的原理
  2. 掌握多种数据库事务的处理逻辑,什么时候处理事务,提交事务
  3. 处理事务的多种方法

5、解决不足

  • spring提供一种处理事务的统一模型,能够使用统一步骤,方法完成多种不同数据库的事务处理

6、处理事务步骤:

spring处理事务的模型,使用步骤都是固定的,把事物使用的信息提供给spring就可以了

  • 事务提交回滚,使用的是事物管理器对象,代替你完成commit,rollback事务管理器是一个接口和它的众多实现类

  • 接口:PlaformTransactionManeger定义了事务重要方法,commit…

  • 实现类:spring把每一种数据库访问技术对应的事务处理类都创建好了

  • mybatis访问数据库------->spring创建好的是DataSourceTransctionManager

     怎么使用,告诉spring,你要是用的数据库访问技术,
     声明数据库访问技术对于事务管理器实现类,在spring的配置文件中使用<bean>声明就可以了
    

例如:使用mybatis访问数据库,在xml文件中配置:

<bean id ="自定义" class="…DataSourceTransctionManager" />

事物的类型:

  1. 事物的隔离级别:
    在这里插入图片描述
  2. 事物的超时时间:表示一个方法最长执行时间,如果方法执行超过了时间,事务就回滚
  3. 事物的传播行为:控制业务方法是不是有事务的,是什么样的事务
    七个传播行为,表示你的业务方法调用时,事务在方法之间是如何使用的

spring框架中提供的事务处理方案

1、适合中小项目使用的,注解方案

  • spring框架自己用aop实现给业务方法增加事物的功能,使用**@Transactional注解**增加事务
  • @Transactional注解是spring框架自己注解,放在public方法上面,表示当前方法具有事务
  • 以给注解的属性赋值,表示具有的隔离级别,传播行为,异常信息

使用@Transactional的步骤:

  1. 声明事务管理器对象
<bean id="xxx" class="DataSourceTransactionManager">
  1. 开启事务注解驱动
    • spring使用aop机制,创建@Transactional所在的类代理对象,给方法加入事务的功能
    • 在你的业务方法执行之前,先开启事务,在业务方法之后提交或者回滚事务,使用aop的环绕通知
@Around("增加业务功能的业务方法")
Object md{
	开启事务,spring开启
	try{
	运行成功提交事务
		commit();
	}catch(Exception e){
	发生异常回滚
		roolback();
	}
}

声明事务管理器对象:

<bean id="transactionManager"class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
<property name="dataSource" ref="dataSource" /><!--指定数据源-->
</bean>

开启注解驱动,创建代理对象transaction-manager:事务管理器id

<tx:annotation-driven transaction-manager="transactionManager" />

注意:
在这里插入图片描述

  1. 在公共事务方法上添加注解
  @Transactional(//完整写法
	    propagation = Propagation.REQUIRED,//传播行为
	    isolation = Isolation.DEFAULT,//事务隔离级别
	    readOnly = false,
	    rollbackFor = {//发生什么异常时进行回滚
	    NullPointerException.class,
	    RuntimeException.class
    }
 )

roolback:处理逻辑

  1. spring框架会首先检查方法抛出的异常,rollbackFor的属性值中如果异常在rollbackFor列表中,不管是什么类型的异常,一定会滚
  2. 如果你抛出的异常rollbackFor列表中,spring会判断异常是不是RuntimeException。如果是,一定会滚

适合大型项目的事务,使用aspectj框架

实现步骤:都在配置文件中完成

  1. 使用aspectj框架,添加依赖
  2. 声明事务管理器对象
  3. 声明方法需要的事务类型(配置方法的事务属性【隔离级别,传播行为,超时】)
  4. 配置aop:指定哪些类创建代理

不用更改源代码,只需要修改配置文件即可

  1. 声明事务管理器
<bean id="transactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
	<!--数据源-->
	<property name="dataSource" ref="dataSource" />
</bean>  
  1. 声明业务方法它的事务属性(隔离级别,传播行为,超时时间)

    id:自定义名称,表示tx:advice标签中间的内容
    transaction-manager:事务管理器的id
    tx:attributes:事务属性
    tx:method:给具体的方法配置属性,method可以有多个可以给不同的方法设置属性
        name:1)完整的方法名称,不带有包和类
              2)方法可以使用通配符,*表示任意字符
        propagation:传播行为,枚举值
        isolation:隔离级别
        rollback-for:指定的异常类名,全限定类名,发生异常一定回滚
    
<tx:advice id="transactionInterceptor" transaction-manager="transactionManager">
<tx:attributes>
    <tx:method name="buy" propagation="REQUIRED" isolation="DEFAULT"
               rollback-for="java.lang.RuntimeException,java.lang.NullPointerException"/>
</tx:attributes>
</tx:advice>
  1. 配置aop
<aop:config>
	<!--配置切入点表达式:指定哪些包中的类,要使用事务
	    id:切入点表达式的名称
	    expression:切入点表达式,指定哪些类要用到事务,aspectj会创建代理对象
	-->
	<aop:pointcut id="servicePt" expression="execution(* *..service..*.*(..))"/>
	<!--配置增强器,关联advice和pointcut
	advice-ref:通知,tx
	pointcut-ref:切入点表达式
	-->
	<aop:advisor advice-ref="transactionInterceptor" pointcut-ref="servicePt"/>
</aop:config>

本站所有文章均为原创,欢迎转载,请注明文章出处:爱敲代码的小游子

猜你喜欢

转载自blog.csdn.net/qq_44895397/article/details/106681134