spring快熟

 1 Spring介绍

1.1 Spring概述

Spring是一个开源框架,Spring是于2003 年兴起的一个轻量级的Java 开发框架,由Rod Johnson 在其著作Expert One-On-One J2EE Development and Design中阐述的部分理念和原型衍生而来。它是为了解决企业应用开发的复杂性而创建的。Spring使用基本的JavaBean来完成以前只可能由EJB完成的事情。然而,Spring的用途不仅限于服务器端的开发。从简单性、可测试性和松耦合的角度而言,任何Java应用都可以从Spring中受益

简单来说,Spring是一个轻量级的控制反转(IoC)和面向切面(AOP)的容器框架。

 

1.2 Spring好处

方便解耦,简化开发:

  • Spring就是一个大工厂,专门负责生成Bean,可以将所有对象创建和依赖关系维护由Spring管理

AOP编程的支持:

  • Spring提供面向切面编程,可以方便的实现对程序进行权限拦截、运行监控等功能
  • 声明式事务的支持:

只需要通过配置就可以完成对事务的管理,而无需手动编程

方便程序的测试:

  • Spring对Junit4支持,可以通过注解方便的测试Spring程序

方便集成各种优秀框架:

  • Spring不排斥各种优秀的开源框架,其内部提供了对各种优秀框架(如:Struts、Hibernate、MyBatis、Quartz等)的支持

降低JavaEE API的使用难度 Spring:

  • 对JavaEE开发中一些难用的API(JDBC、JavaMail、远程调webservice用等),都提供了封装,使这些API应用难度大大降低

 

1.3 Spring体系结构

Spring 框架是一个分层架构,,它包含一系列的功能要素并被分为大约20个模块。这些模块分为Core Container、Data Access/Integration、Web、AOP(Aspect Oriented Programming)、Instrumentation和测试部分,如下图所示:

 

1.4 在项目中的架构

web层:Struts,SpringMVC

dao层:Hibernate,mybatis

 

 

2 Spring 快速入门

目标:

掌握web中集成Spring需要哪些包

掌握IOC是什么

 

2.1 编写流程

  1. 下载Spring 开发包
  2. 导入Spring的jar包
  3. 配置Spring的核心xml文件
  4. 在程序中读取Spring的配置文件来获取Bean【Bean其实就是一个new好的对象】

 

2.2 下载官网

  1. Spring现在有很多框架,如Spring SpringMVC,Spring-Data,Sprint-Boot

 

 

2.3 Spring的核心jar包

spring-core-3.2.2.RELEASE.jar

包含Spring框架基本的核心工具类,Spring其它组件要都要使用到这个包里的类,是其它组件的基本核心。

spring-beans-3.2.2.RELEASE.jar

所有应用都要用到的,它包含访问配置文件、创建和管理bean

以及进行Inversion of Control(IoC) / Dependency Injection(DI)操作相关的所有类

spring-context-3.2.2.RELEASE.jar

Spring提供服务的支持,在基础IoC功能上的扩展服务,此外还提供许多企业级

如邮件服务、任务调度、JNDI定位、EJB集成、远程访问、缓存以及各种视图层框架的封装等。

spring-expression-3.2.2.RELEASE.jar

Spring表达式语言

com.springsource.org.apache.commons.logging-1.1.1.jar

第三方的主要用于处理日志

 

 

 

2.4 Spring的入门案例

第一步:下载Spring的包

spring-framework-3.2.0.RELEASE-dist.zip 【Spring的核心包】

spring-framework-3.0.2.RELEASE-dependencies.zip 【Spring的依赖包】

 

第二步:创建Web项目,导Spring的jar包

    1. 导入4核心(beans、core、context,expression) + 1个依赖(common-logging.jar)
    2. 注意导入时,不要导入带sources的源文件了

 

第三步:写个简单的Service 并在main方法中调用

 

第四步:Spring IoC控制反转创建实例

  1. 写了个配置文件beans.xml,配置文件的约束可以访问

spring-framework-3.2.0.RC2-docs/reference/html/xsd-config.html网页查看

 

2> 离线配置文件约束提示的配置

xsd可以在schema目录中找

 

3> Beans.xml文件配置

 

第五步:从beans.xml获取bean

 

总结:【IoC】

  1. IoC Inverse of Control 反转控制的概念,就是将原本在程序中手动创建UserService对象的控制权,交由Spring框架管理,简单说,就是创建UserService对象控制权被反转到了Spring框架

2.5 DI解释

  • Dependency Injection 依赖注入,在Spring框架负责创建Bean对象时,动态的将依赖对象注入到Bean组件。

例子:

在UserService中提供一个get/set的name方法,在beans.xml中通过property去注入

 

 

  1. 加载Spring容器的三种方式

3.1 类路径获得配置文件

ApplicationContext context =

new ClassPathXmlApplicationContext("com/gyf/spring/demo01/beans.xml");

 

3.2 文件系统路径获得配置文件

 

3.3使用BeanFactory(了解)

 

3.4BeanFactory和ApplicationContext对比

  • BeanFactory 采取延迟加载,第一次getBean时才会初始化Bean
  • ApplicationContext是对BeanFactory扩展,提供了更多功能
  1. 国际化处理
  2. 事件传递
  3. Bean自动装配
  4. 各种不同应用层的Context实现

 

  1. 装配Bean(xml),IoC

4.1 实例化Bean的三种方式

4.1.1 使用构造方法实例化

4.1.2 使用静态工厂方法实例化

4.1.3 使用实例工厂方法实例化

Bean.xml

<!--装配bean的三种方式,所谓的装配bean就是在xml写一个bean标签-->

 <!-- 第一种方式: new 实现类-->
 <bean id="userService1" class="com.gyf.service.UserServiceImpl"></bean>

 <!-- 第二种方式:通过静态工厂方法
    spring的版本过低,3.0版本,把jdk改成1.7
  -->
 <bean id="userService2" class="com.gyf.service.UserSereviceFactory1" factory-method="createUserService"></bean>

 <!--第三种方式:通过实例工厂方法 -->
 <!-- 创建实例factory2 bean-->
 <bean id="factory2" class="com.gyf.service.UserSereviceFactory2"></bean>

 <bean id="userService3" factory-bean="factory2" factory-method="createUserService"></bean>

test

@Test
public void test1(){
    ApplicationContext context = new ClassPathXmlApplicationContext("beans3.xml");

    //new 对象
    //IUserService userService1 = (IUserService) context.getBean("userService1");
    //userService1.add();

    //静态工厂
    //IUserService userService2 = UserSereviceFactory1.createUserService();
    //IUserService userService2 = (IUserService) context.getBean("userService2");
    //userService2.add();

    //实例工厂
    //1.创建工厂, 每次出来的都不是同一个service
   // UserSereviceFactory2 factory2 = new UserSereviceFactory2();
    //IUserService userService3 = factory2.createUserService();

    IUserService userService3 = (IUserService) context.getBean("userService3");
    userService3.add();
}

 

 

 

4.2 bean的作用域

掌握红色两个常用的即可

类别

说明

singleton

在Spring IoC容器中仅存在一个Bean实例,Bean以单例方式存在,默认值

prototype

每次从容器中调用Bean时,都返回一个新的实例,即每次调用getBean()时 ,相当于执行new XxxBean()

request

每次HTTP请求都会创建一个新的Bean,该作用域仅适用于WebApplicationContext环境

session

同一个HTTP Session 共享一个Bean,不同Session使用不同Bean,仅适用于WebApplicationContext 环境

globalSession

一般用于Portlet应用环境,该作用域仅适用于WebApplicationContext 环境

 

案例:

 

  1. bean的生命周期【了解】

生命周期图

 

生命周期图解释

1.instantiate bean对象实例化

2.populate properties 封装属性

3.如果Bean实现BeanNameAware 执行 setBeanName

4.如果Bean实现BeanFactoryAware 执行setBeanFactory ,获取Spring容器

5.如果存在类实现 BeanPostProcessor(后处理Bean) ,执行postProcessBeforeInitialization ;对所有得对象都会使用

6.如果Bean实现InitializingBean 执行 afterPropertiesSet

7.调用<bean init-method="init"> 指定初始化方法 init

8.如果存在类实现 BeanPostProcessor(处理Bean) ,执行postProcessAfterInitialization

执行业务处理

9.如果Bean实现 DisposableBean 执行 destroy

101.调用<bean destroy-method="customerDestroy"> 指定销毁方法 customerDestroy

 

演示

 

 

 

 

  1. 依赖注入Bean属性(xml)

6.1手动装配,使用xml配置

构造方法注入 

 

属性setter方法注入

setter方法有两种注入,一般使用第一种直观

<bean id="user" class="com.gyf.spring.demo04.User">

<property name="username" value="zhangsan"></property>

<property name="password" value="123456"></property>

</bean>

 

p命名空间注入【 了解】

 

6.2 SpEL表达式【了解】

Spring 表达式

  • 对<property>进行统一编程,所有的内容都使用value,作为一个对象处理
  • <property name="" value="#{表达式}">

#{123}、#{'jack'} : 数字、字符串

#{beanId} :另一个bean引用

#{beanId.propName} :操作数据

#{beanId.toString()} :执行方法

#{T(类).字段|方法} :静态方法或字段

 

 

6.3 集合注入

集合的注入都是给<property>添加子标签

数组:<array>

List:<list>

Set:<set>

Map:<map> ,map存放k/v 键值对,使用<entry>描述

Properties:<props>  <prop key=""></prop>  【】

 

普通数据:<value>

引用数据:<ref>

List

 

 

Set

 

 

 

Map

 

 

Properties

 

 

数组

6.4 注解注入

  • 注解:就是一个类,使用@注解名称
  • 开发中:使用注解 取代 xml配置文件。

 

6.4.1 @Component

@component取代<bean class="">

6.4.2 @Component("id")

取代 <bean id="" class="">

6.4.4 web开发,提供3个@Component注解衍生注解(功能一样)取代<bean class="">

这些存在加载时间顺序, 当action对象调用service层时,需要service创建完成

 

@Repository(“名称”):dao层

@Service(“名称”):service层

@Controller(“名称”):web层

 

@Autowired:自动根据类型注入

@Qualifier(“名称”):指定自动注入的id名称

@Resource(“名称”)  等效@Autowired跟@Qualifier

 

@ PostConstruct 自定义初始化

@ PreDestroy 自定义销毁

 

 

6.4.5 使用案例

第一个案例

 

第二个案例

 

第三个案例

 

第四个案例

 

第五个案例

 

第六个案例

context.getClass().getMethod(“close”).invoke(context);

 

1、AOP

1.1 AOP概述

  1. 在软件业,AOP为Aspect Oriented Programming的缩写,意为:面向切面编程,通过预编译方式和运行期动态代理实现程序功能的统一维护的一种技术。
  2. AOP是OOP(面向对象编程)的延续,是软件开发中的一个热点,也是Spring框架中的一个重要内容,是函数式编程的一种衍生范型。
  3. 利用AOP可以对业务逻辑的各个部分进行隔离,从而使得业务逻辑各部分之间的耦合度降低,提高程序的可重用性,同时提高了开发的效率。
  4. AOP采取横向抽取机制,取代了传统纵向继承体系重复性代码
  5. 经典应用:事务管理、性能监视、安全检查、缓存 、日志等【画图】
  6. Spring AOP使用纯Java实现,不需要专门的编译过程和类加载器,在运行期通过代理方式向目标类织入增强代码
  7. AspectJ是一个基于Java语言的AOP框架,Spring2.0开始,Spring AOP引入对Aspect的支持,AspectJ扩展了Java语言,提供了一个专门的编译器,在编译时提供横向代码的织入

 

1.2 AOP实现原理

  1. aop底层将采用代理机制进行实现。
    1. 接口 + 实现类 :spring采用 jdk 的动态代理Proxy
    2. 实现类:spring 采用 cglib字节码增强。

 

1.3 AOP术语

1.target:目标类,需要被代理的类。例如:UserService

2.Joinpoint(连接点):所谓连接点是指那些可能被拦截到的方法。例如:所有的方法

3.PointCut 切入点:已经被增强的连接点。例如:addUser()

4.advice 通知/增强增强代码。例如:after、before

5. Weaving(织入):是指把增强advice应用到目标对象target来创建新的代理对象proxy的过程.

6.proxy 代理类

7. Aspect(切面): 是切入点pointcut和通知advice的结合

一个线是一个特殊的面。

一个切入点和一个通知,组成成一个特殊的面。

 

1.4 手动代理

1.4.1 JDK动态代理

目标类

 

切面类

 

工厂类

 

测试类

 

1.4.2 cglib 增强字节码

  1. 没有接口,只有实现类。
  2. 采用字节码增强框架 cglib,在运行时 创建目标类的子类,从而对目标类进行增强。
  3. 导入jar包:

自己导包(了解):

核心:hibernate-distribution-3.6.10.Final\lib\bytecode\cglib\cglib-2.2.jar

依赖:struts-2.3.15.3\apps\struts2-blank\WEB-INF\lib\asm-3.3.jar

spring-core..jar 已经整合以上两个内容

 

 

 

工厂类

 

测试结果

 

1.5 AOP联盟通知类型

AOP联盟为通知Advice定义了org.aopalliance.aop.Advice

Spring按照通知Advice在目标类方法的连接点位置,可以分为5类

前置通知 org.springframework.aop.MethodBeforeAdvice

•在目标方法执行前实施增强

 

后置通知 org.springframework.aop.AfterReturningAdvice

•在目标方法执行后实施增强

 

环绕通知 org.aopalliance.intercept.MethodInterceptor

•在目标方法执行前后实施增强

 

异常抛出通知 org.springframework.aop.ThrowsAdvice

•在方法抛出异常后实施增强

 

引介通知 org.springframework.aop.IntroductionInterceptor

在目标类中添加一些新的方法和属性

 

环绕通知必须手动执行目标方法

try{

   //前置通知

   //执行目标方法

   //后置通知

} catch(){

   //抛出异常通知

}

 

 

1.6 Spring编写代理半自动

目标:掌握让spring 创建代理对象,从spring容器中手动的获取代理对象。

第一步:导Jar包

【核心4+1 、AOP联盟(规范)、spring-aop (实现)】

 

第二步:目标类

 

第三步:切面类

 

第四步:spring配置

 

第五步:测试

 

 

1.7 Spring AOP全自动编程

目录:明白什么是全自动织入

第一步:导入jar包

spring-framework-3.0.2.RELEASE-dependencies\org.aspectj\com.springsource.org.aspectj.weaver\1.6.8.RELEASE


第二步:Spring 的AOP配置

 

第三步:测试

 

 

  1. AspectJ框架

2.1 AspectJ简介

  1. AspectJ是一个基于Java语言的AOP框架
  2. Spring2.0以后新增了对AspectJ切点表达式支持
  3. @AspectJ 是AspectJ1.5新增功能,通过JDK5注解技术,允许直接在Bean类中定义切面
  4. 新版本Spring框架,建议使用AspectJ方式来开发AOP
  5. 主要用途:自定义开发

 

2.2 切入点表达式【掌握】

execution()  

用于描述方法 【掌握】

语法:execution(修饰符  返回值  包.类.方法名(参数) throws异常)

 

修饰符,一般省略

public 公共方法

* 任意

返回值,不能省略

void 返回没有值

String 返回值字符串

* 任意

包,[省略]

com.gyf.crm 固定包

com.gyf.crm.*.service crm包下面子包任意 (例如:com.gyf.crm.staff.service)

com.gyf.crm.. crm包下面的所有子包(含自己)

com.gyf.crm.*.service.. crm包下面任意子包,固定目录service,service目录任意包

类,[省略]

UserServiceImpl 指定类

*Impl 以Impl结尾

User* 以User开头

* 任意

方法名,不能省略

addUser 固定方法

add* 以add开头

*Do 以Do结尾

* 任意

(参数)

() 无参

(int) 一个整型

(int ,int) 两个

(..) 参数任意

throws ,可省略,一般不写

 

案例1:

execution(* com.gyf.crm.*.service..*.*(..))

 

案例2:或

<aop:pointcut expression="execution(* com.gyf.crm.service.*.*(..)) ||

                          execution(* com.gyf.*Do.*(..))" id="myPointCut"/>

within:

匹配包或子包中的方法(了解)

within(com.gyf.aop..*)

 

this:

匹配实现接口的代理对象中的方法(了解)

this(com.gyf.aop.user.UserDAO)

 

target:

匹配实现接口的目标对象中的方法(了解)

target(com.gyf.aop.user.UserDAO)

args:

匹配参数格式符合标准的方法(了解)

args(int,int)

bean(id)  

对指定的bean所有的方法(了解)

bean('userServiceId')

 

 

2.3 AspectJ 通知类型

aop联盟定义通知类型,具有特性接口,必须实现,从而确定方法名称。

aspectj 通知类型,只定义类型名称,以及方法格式。

个数:6种,知道5种,掌握1中。

before:前置通知(应用:各种校验)

在方法执行前执行,如果通知抛出异常,阻止方法运行

afterReturning:后置通知(应用:常规数据处理)

方法正常返回后执行,如果方法中抛出异常,通知无法执行

必须在方法执行后才执行,所以可以获得方法的返回值。

around:环绕通知(应用:十分强大,可以做任何事情)

方法执行前后分别执行,可以阻止方法的执行

必须手动执行目标方法

afterThrowing:抛出异常通知(应用:包装异常信息)

方法抛出异常后执行,如果方法没有抛出异常,无法执行

after:最终通知(应用:清理现场)

方法执行完毕后执行,无论方法中是否出现异常

 

 

查看源码

 

 

2.4 Aspect案例讲解【其于xml】

第一步:导包

AOP联盟规范

AOP实现

规范

aspectj实现

 

 

第二步:实现类和切面类

 

第三步:spring的xml配置

 

第四步:测试

 

 

2.5 Aspect案例讲解【其于xml】

第1步:声明使用注解

 

第2步:替换service和 切面 bean

 

第3步:声明切面

 

第4步:声明前置通知

 

第6步:声明后置通知

 

第5步:声明公共切入点

 

第7步:声明环绕通知

 

第8步:声明异常通知

 

第9步:声明最终通知

 

注解总结

@Aspect  声明切面,修饰切面类,从而获得 通知。

通知

@Before 前置

@AfterReturning 后置

@Around 环绕

@AfterThrowing 抛出异常

@After 最终

切入点

@PointCut ,修饰方法 private void xxx(){}  之后通过“方法名”获得切入点引用

 

 

3 JdbcTemplate

3.1 简介

  • jdbcTemplate类似人DBUtils,用于操作Jdbc的工具类,它需要依赖于连接池DataSource(数据源)
  • JDBC(Java DataBase Connectivity,java数据库连接)是一种用于执行SQL语句的Java API
  • ODBC(Open Database Connectivity,ODBC)开放数据库连接,是微软公司开提供了一组对数据库访问的标准API(应用程序编程接口)
  • DBCP(DataBase Connection Pool)数据库连接池,是java数据库连接池的一种,由Apache开发
  • C3P0是一个开源的JDBC连接池,它实现了数据源和JNDI绑定,支持JDBC3规范和JDBC2的标准扩展。目前使用它的开源项目有Hibernate,Spring等。

c3p0与dbcp区别

dbcp没有自动回收空闲连接的功能

c3p0有自动回收空闲连接功能

 

 

3.2 环境搭建

创建数据库和表

create database spring_day02;

use spring_day02;

create table t_user(

  id int primary key auto_increment,

  username varchar(50),

  password varchar(32)

);

 

insert into t_user(username,password) values('jack','520');

insert into t_user(username,password) values('rose','521');

 

创建工程导入Jar包

 

创建JavaBean,数据模型

 

3.3 API使用【了解】

 

3.4 配置DBCP

beans.xml

测试

 

3.5 配置c3p0

 

 

3.6 使用JdbcDaoSupport

dao层

 

Beans.xml

通过数据源创建模板

3.7 配置properties

目数据库的连接信息配置到一个独立的文件中

在src写个db.properties文件

beans.xml

  1. 事务管理

1.1 事务回顾

事务简介

一组业务ABCD操作,要么全部成功,要么全部不成功。

事务特性:ACID

  • 原子性:整体 【原子性是指事务包含的所有操作要么全部成功,要么全部失败】
  • 一致性:数据 【一个事务执行之前和执行之后都必须处于一致性状态】
  • 隔离性:并发 【对于任意两个并发的事务T1和T2,在事务T1看来,T2要么在T1开始之前就已经结束,要么在T1结束之后才开始,这样每个事务都感觉不到有其他事务在并发地执行。
  • 持久性:结果 【持久性是指一个事务一旦被提交了,那么对数据库中的数据的改变就是永久性的

隔离问题

  • 脏读:一个事务读到另一个事务未提交的内容【读取未提交内容】

在该隔离级别,所有事务都可以看到其他未提交事务的执行结果。本隔离级别很少用于实际应用,因为它的性能也不比其他级别好多少。

  • 不可重复读:一个事务读到另一个事务已提交的内容(insert)【读取提交内容】

这是大多数数据库系统的默认隔离级别(但不是MySQL默认的)。它满足了隔离的简单定义:一个事务只能看见已经提交事务所做的改变。

  • 虚读(幻读):一个事务读到另一个事务已提交的内容(update)

这是MySQL的默认事务隔离级别,它确保同一事务的多个实例在并发读取数据时,会看到同样的数据行。不过理论上,这会导致另一个棘手的问题:幻读 (Phantom Read)。简单的说,幻读指当用户读取某一范围的数据行时,另一个事务又在该范围内插入了新行,当用户再读取该范围的数据行时,会发现有新的“幻影” 行。

  • Serializable(可串行化)

这是最高的隔离级别,它通过强制事务排序,使之不可能相互冲突,从而解决幻读问题。简言之,它是在每个读的数据行上加上共享锁。在这个级别,可能导致大量的超时现象和锁竞争。

隔离级别--解决问题

  • read uncommittd,读未提交。存在3个问题。
  • read committed,读已提交。解决:脏读。存在2个问题。
  • repeatable read ,可重复读。解决:脏读、不可重复读。存在1个问题。
  • serializable,串行化。单事务。没有问题。

mysql 事务操作--简单

ABCD 一个事务

Connection conn = null;

try{

  //1 获得连接

  conn = ...;

  //2 开启事务

  conn.setAutoCommit(false)

  //3 提交事务

  conn.commit();

} catche(){

  //4 回滚事务

  conn.rollback();

}

mysql 事务操作--Savepoint

需求:AB(必须),CD(可选)

Connection conn = null;

Savepoint savepoint = null;  //保存点,记录操作的当前位置,之后可以回滚到指定的位置。(可以回滚一部分)

try{

  //1 获得连接

  conn = ...;

  //2 开启事务

  conn.setAutoCommit(false);

  savepoint = conn.setSavepoint();

  //3 提交事务

  conn.commit();

} catche(){

  if(savepoint != null){   //CD异常

     // 回滚到CD之前

     conn.rollback(savepoint);

     // 提交AB

     conn.commit();

  } else{   //AB异常

     // 回滚AB

     conn.rollback();

  }

}

 

1.2 Spring事务管理介绍

1.2.1 Spring提供的事务jar包

transaction = tx

1.2.2 Jar中的三个顶级接口

 

PlatformTransactionManager

平台事务管理器,spring要管理事务,必须使用事务管理器,进行事务配置时,必须配置事务管理器

TransactionDefinition:

事务详情(事务定义、事务属性),spring用于确定事务具体详情,

例如:隔离级别、是否只读、超时时间 等

进行事务配置时,必须配置详情。spring将配置项封装到该对象实例。

TransactionStatus:

事务状态,spring用于记录当前事务运行状态。例如:是否有保存点,事务是否完成。

spring底层根据状态进行相应操作。

1.2.3 PlatformTransactionManager 事务管理器

先导入两个包
常用的两个事务管理器

1.2.4 TransactionStatus 事务状态

1.2.5 TransactionDefinition

传播行为:在两个业务之间如何共享事务

PROPAGATION_REQUIRED

required , 必须  【默认值】

支持当前事务,A如果有事务,B将使用该事务。

如果A没有事务,B将创建一个新的事务。

PROPAGATION_SUPPORTS

supports ,支持

支持当前事务,A如果有事务,B将使用该事务。

如果A没有事务,B将以非事务执行。

PROPAGATION_MANDATORY

mandatory ,强制

支持当前事务,A如果有事务,B将使用该事务。

如果A没有事务,B将抛异常。

PROPAGATION_REQUIRES_NEW 

requires_new ,必须新的

如果A有事务,将A的事务挂起,B创建一个新的事务

如果A没有事务,B创建一个新的事务

PROPAGATION_NOT_SUPPORTED

not_supported ,不支持

如果A有事务,将A的事务挂起,B将以非事务执行

如果A没有事务,B将以非事务执行

PROPAGATION_NEVER

never,从不

如果A有事务,B将抛异常

如果A没有事务,B将以非事务执行

PROPAGATION_NESTED

nested ,嵌套

A和B底层采用保存点机制,形成嵌套事务。

 

掌握:PROPAGATION_REQUIRED、PROPAGATION_REQUIRES_NEW、PROPAGATION_NESTED

以上了解及掌握重点spring基本上就会了

 

 

转载于:https://my.oschina.net/u/4083965/blog/3030303

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值