Spring3 m: d5 E/ L. T5 I
- 是什么?
. K5 i R9 J" A6 A/ ^* [3 ^
8 }( t- O. u! c# ^3 r; C
Spring是基于JEE的轻量级的应用框架
+ R+ W2 T4 U c2 J9 J8 b' l+ |- 有什么?
% ~! Q4 o! d* M
l. T5 ~0 K3 ^. ?3 V5 }' e. U 6 \# W( r% j4 a s9 e
每个包的功能: Spring MVC:spring 本身提供的web 框架 WEB:集成其他的web 应用的框架,或者说是对其他web应用框架的支持。如struts,webwork JEE :集成一系列的jee的技术(对JEE技术的支持) DAO:封装了JDBC;(对JDBC的支持) ORM:提供了对ORM工具的集成(支持) AOP :面向切面编成 CORE:spring的核心包,提供bean的工厂和IOC容器
f* |$ ^$ r4 ~- ~- 能干什么?1 f2 n+ l& a7 u+ D5 w$ |) z& D
3 P8 z2 H& g- j: Q: i6 U
把一系列的jee的技术有效的组合在一起形成以良好的系统
+ ?0 s8 x# t& ^- g- 怎么用?
8 }" k% D. [+ n; b% M ^: g( a. y% N0 e( C6 w4 Z
- 搭建web工程,引入spring的jar包* y) m4 D# P1 T0 ]
- 在web.xml中添加如下配置3 V. T: W! ^: I0 i( ^+ A2 X M
& S6 x! `; p& j# }- e0 M3 ?; j
# j( _3 R' P( h9 z
) f3 {7 Z( ^" s* Y3 L
contextConfigLocation _7 _9 G( a( q ~" F& U* k
classpath*:applicationContext*.xml
" O0 ]5 r; N3 V4 r, j
9 q4 a! R; c& e* i/ V- \0 [ / I' j# Q1 C+ G( Z) p
struts20 Z- J) g! ^: _4 a( }, j5 l$ P1 p
. H. U; d8 ?5 P% G7 a) `8 q9 Z% |
org.apache.struts2.dispatcher.FilterDispatcher
' d7 `" b" [" N2 w
% b# |; F" o8 @8 D( y2 F 6 L$ X- @7 X( [& B+ z
+ J, C) J' @: e3 V
struts22 ~$ \- I0 h# _' H
/*
6 O( p4 m" @- X# J ) U# D: L9 }* w
0 Q8 ]9 k4 s' d
- b6 A$ X# A* X
org.springframework.web.context.ContextLoaderListener
! I/ H r6 I* O& h4 t 5 t, p+ m7 y3 T" @0 W# ?1 i8 @' ]
- 部署4 t% o* m- \# N& _. I$ d6 l
5 }5 [2 d$ F% ~ 4 I- B$ }& c1 g4 c5 R0 F) q O) x
0 u7 R& B# U% z: }2 `7 \+ C
' L7 C# T* g' D, F$ w" V
- 容器和bean
# I- S& t& k) O' I2 H/ y# |& @# S- `
Bean :是指受spring的ioc管理的对象称为bean 容器 :(与jee的容器类比) Jee :提供组件的运行环境和管理组件的生命周期(不能单独存在) Spring :提供bean的运行环境和管理bean的生命周期(可以单独存在) 9 o$ o6 R+ u& q7 ?2 T: I- e- ]( g r
. _% S3 J ~5 O5 \) F% o6 p
- DI依赖注入
5 j2 E6 i0 e' N" b! e
1. 应用程序依赖spring注入所需要的对象 IOC和DI是对同一种事情的不同描述 2.setter注入: 在配置文件中将接口的实现配置为bean在应用程序中注入bean 例如: 在配置文件中
" S l0 ~! a6 ~- W/ c% n8 O& {. P$ D* W! r+ d
/ l/ Y- [6 [. S6 a$ w$ K0 s+ K
在应用程序中 Public DBDAO dao ; Public void setDao(DBDAO dao){ This.dao = dao; } 3.构造器注入 / @& U& f: |5 E0 H
4.ref 表示参照其它的bean 在参照的过程中一定要注意死循环 5.自动装配———–〉no 自动装配根据名字来匹配相应的bean 尽量不要去自动装配 6.lookup注入 7.singleton 1.单例模式是整个的jvm中只有一个实例 2.spring的singleton是指在spring的容器中只有一个实例 一个生命周期中只有一个实例 8.DI的优点: 1.程序被动等待,强化面向接口编成 2.切断了对象或组件之间的联系,使程序的结构更加松散,运行和维护更加简单
4 t6 Z5 b$ [7 x3 {* S- Aop面向切面编程5 r0 U n' b% P/ b2 p1 x
4 e0 ]- H4 z! E* @3 l
1.AOP面向切面编程 一些较好的模式或者是示例—-范式
% L$ u J- E2 m& W$ S1 x& s3 u2 l8 g 切面:一个切面代表我们所关注的一系列的共同的功能点(模块之间的共同的功能点) 2.AOP的思想: 主动—->被动(追加功能)/ b' y5 u2 h) q. D
3.AOP 的概念0 F9 M% f4 M1 U: C
1.切面 :我们所关注的功能点 2.连接点 :事件的触发点(方法的执行) 3.通知 :连接点触发时执行的动作(方法) 4.切入点 :一系列的连接点的集合 (连接点的模块化) 5.引入 :扩展的功能 6.目标对象 :包含连接点的对象 7.aop代理 :实现机制 8.织入 :把advice和目标对象连接起来 4.AOP的事件机制
d l3 f! A @$ u$ I8 ^5 @( T 1.通过切面找出一系列共同的功能点 2.找到目标对象(在标准的spring 中 接口的实现类为target) 3.找到切入点 4.确定连接点 5.通知spring AOP,查询xml文件,通过代理找到advice。 6.由aop代理来实现动态织入
( A$ B7 U2 i, u& s% L; W) F/ Y0 @/ ^. O2 J5 T$ l
4 X- z$ |/ G" L, w' M
0 E7 T5 c A+ E8 o. D
5 P: v) p& Y# S. W ?, b$ d
( U& d5 a7 ]1 U, i0 d2 r1 ]4 n& M Y X* e7 P) m$ N
5. AspectJ
0 X/ s/ x! t! p, S4 z) t 5.1.在xml中配置比较烦琐/ l. \6 F( u8 ]1 W5 K; \
所有的入口必须从一个代理(ProxyFactoryBean)开始3 \) _3 e$ V: x% L5 I- U
, }2 r, Q2 j! g; [
5 r8 C/ ]; B$ y# o r1 c+ e) G
& o+ e' x ^2 M8 J3 O, z# Y
( o1 m$ P: L' y2 C) Z
0 d+ n- l" I( N w! d 8 v# Y& }9 o0 u( N: w9 N
+ P, F0 I" p0 i$ \6 U 3 f$ g. F2 `1 W& N
expression=“execution(* com.javakc.aop.MyTarget.t*())”/>
, ?7 c& }+ ^$ N( r8 F. p
0 V/ o p" h* [, l( t9 O $ r+ d% b$ I0 {7 ]. t: C
/ J" i: r* U8 `! ~& v; [+ z# H
' B2 O" \* l# C0 I3 v9 V' z9 o! W' C* @1 @+ p
5.3.使用注解的方法相对简单" ~7 M( @2 A2 h1 S4 R5 ]
@AspectJ的基本语法; }* p/ O; `+ p, H. b
1.@Aspect声明一个切面,将一系列的共同的功能定义成一个切面
) S7 D! [9 N. ~" v; r 直接在类上定义@Aspect$ g9 d$ ^4 z5 _$ T. M. Y5 R1 D
2.@Pointcut声明切入点! R8 V1 T) R0 x3 |2 y* D
2.1、用一个专门的类来定义pointcut,类中的方法名就是该pointcut的名字
0 { T* W( L! P8 v& ? 2.2、可以使用匿名的pointcut+ ^: b; F. M$ Z- |: I
2.3、执行切点的几种方法# i% m6 E8 O( b: o1 t9 ~
2.3.1 execute(public * 包结构.*.*.(..)) 可以指定到具体的方法
' K' M; Z' m/ @ 2.3.2 within 指定到包,不能指定到类
+ i$ S* q% w* i7 u* u within(”com.javakc.spring..*”)
6 A9 h3 Q4 m F5 J& s 2.3.3 this 指定到实现接口的所有的实现类) y% h6 _2 k6 M4 ?
2.3.4 target 指定具体的实现类( _9 b: O6 d4 e, v8 p; f- v# _
5.4.advice的五种类型的示例
% r3 W, U- c" `/ b4 {; `% {) Q 客户端必须从接口走才能得到监控,实现想要追加的功能7 g# h+ I' T) U' U1 t# Q+ h
5.4.1.@AfterReturning(pointcut=”” returning=”retVal”)$ z8 h7 \3 }# z- p/ e7 d @6 u
追加的方法的参数名字一定要与retrning的名字相同1 m* p9 A9 C3 Z0 Q$ t: Q& `# W
在注解@AfterReturning中必须加上pointcut和returning两个参数
: z% ~. Z/ ^/ w, M pointcut指所要监控的目标对象的方法$ B, }. Z. [% Q. J$ s
得到目标对象的方法的返回值,来作为参数,进行下一步的处理,参数没有顺序,按参数的名字进行匹配
: x0 W. d E7 }/ _* i0 h# m 完成追加的功能; J# ~1 C3 F+ o& S4 k
1 定义一个pointcut,通过方法名来作为pointcut的名称来引用
! X5 Y0 b8 k+ M: F (1).@AfterReturning(“com.javakc.spring.schemaaop.TestPointcut.t4()”)2 v3 [ W Z/ u8 w8 z
(2).
6 _$ P$ W7 Q! }3 z1 A/ v 2.直接引用匿名的pointcut
' K& n; c5 P) f) d1 e (1).@AfterReturning(“execution(
* j' y1 \2 q1 q. f, M * com.javakc.spring.schemaaop.Api.test4())”)
' E: F% _" x/ q7 s4 k (2).@AfterReturning(pointcut=2 ^7 c- O( W! o3 G+ Y) ~* w1 A' c Q
“com.javakc.spring.schemaaop.TestPointcut.t4() &&: v$ V* \5 H( t
args(str)”, returning=”retVal”)
, B+ C; i$ i, k$ N1 `) w @AfterReturning (pointcut=”com.javakc.spring.schemaaop.TestPointcut.t4() && args(str)”,returning=”retVal”)
; V% p* N1 d1 ]% Z public void testAfterReturning(String str,Object retVal){
- l/ m/ Q- w: m System.out.println(“afterReturning1=>”+retVal+”=>”+str);! Q6 S( E% |' U' T" Y
}" K g5 w; A( ]- ^9 z
5.4.2.@Aronud3 {- y6 y: j( C( @, ~3 H' A$ ^
注解@Around环绕追加功能;- _/ W5 O7 K: p
在执行目标对象的方法的前、后追加功能;3 W/ D3 a/ h1 V( A- \ j5 H$ [+ z
必须有参数;第一个参数的类型必须为ProceedingJoinPoint;
& x" ?/ `! ^% P# H2 \. e3 ^# T9 n 通过ProceedingJoinPoint的实例的proceed来调用所监控的) u. U- J1 @, J) m8 \
目标对象的方法/ j0 D/ W% v3 P, V; }1 u
1 定义一个pointcut,通过方法名来作为pointcut的名称来引用
( v2 @6 S1 p! |) n (1).@Around(“com.javakc.spring.schemaaop.TestPointcut.t1()”)7 A p1 _# G- `% W, ]! U# l. [# x
(2).@Around(“com.javakc.spring.schemaaop.TestPointcut.t2()0 i- o! e# A- G& R
&& args(str)”)
1 l8 m% y; x4 a4 d. X2 J* U 2.直接引用匿名的pointcut+ |1 M% g* L* `$ \( N# p9 b
(1).@Around(“execution(
7 l2 ~' f# {$ L/ v X1 ]5 U* l * com.javakc.spring.schemaaop.Api.test1())”)
6 L; N) D: {: u$ l (2).@Around(“execution(7 y. v; K. W/ P4 W/ ^
* com.javakc.spring.schemaaop.Api.test2(..)) && args(str)”)0 I' p$ q2 `+ ]' P0 C# {
// @Around(“com.javakc.spring.schemaaop.TestPointcut.t2() && args(str)”); ~6 t2 ]4 @9 Z7 j
@Around(“execution(* com.javakc.spring.schemaaop.Api.test2(..)) && args(str)”); f6 D R! `- H: v
public void testAround(ProceedingJoinPoint prj,String str) throws Throwable{1 B6 b' A @( t/ p4 z/ s
System.out.println(“around1==========before1pointcut==>”+str)
2 x+ X7 v+ I- x5 B8 X4 ]$ a Object obj = prj.proceed();
# ?0 z5 K" n! M& V: m8 j& p System.out.println(“around1==========after1pointcut==>”+str);
' G. ^8 c3 u$ m$ W2 P) {2 L }
1 X! V {7 H/ D7 r! R. t, _ 5.4.3.@Before6 I( v9 N$ K) W, H; h8 R$ T' o
注解@Before在执行目标对象的方法前追加相应的功能3 u. Q4 w+ f# c
1 定义一个pointcut,通过方法名来作为pointcut的名称来引用
4 u! G/ y0 [: _" Z3 B5 F- c* D& s (1).@Before(“com.javakc.spring.schemaaop.TestPointcut.t1()”)
5 U4 o% h# w0 X1 X' r; r (2).@Before(“com.javakc.spring.schemaaop.TestPointcut.t2() && args(str)”)
4 E K: M4 p6 {( g. ~7 G& D 注意args后的名称与参数名相同
! |5 ~, H( C9 @! t7 R0 f+ c 2.直接引用匿名的pointcut" z1 K) r- c! @5 f
(1).@Before(“execution(* com.javakc.spring.schemaaop.Api.test1())”)6 g( D8 J$ F) k! j8 h# u5 A
(2).@Before(“execution(* com.javakc.spring.schemaaop.Api.test2(..)) && args(str)”)
5 e) x6 R7 ^% m( U2 ` d$ L+ i 注意args后的名称与参数名相同
/ I5 k+ }( ?& {3 U6 x0 f // @Before(“com.javakc.spring.schemaaop.TestPointcut.t2() && args(str)”)8 |9 C7 V: N% f5 l& {( W* L& P+ f
@Before(“execution(* com.javakc.spring.schemaaop.Api.test2(..)) && args(str)”) F' w- }" m* j
public void testBeforeParam(String str){& I8 C# w8 t+ [$ e
System.out.println(“before1=param=>”+str);9 R5 G' W7 l: j( `
}, D+ v. i4 i' Z. d, b
6 @+ \8 H7 T0 o2 i: m6 A( v
5.4.4.@After" k; t8 E* A8 i5 i' |+ u( z" ~
注解@After在执行目标对象的方法后追加相应的功能
2 }8 @' b, B0 H1 {0 ?: Q 1 定义一个pointcut,通过方法名来作为pointcut的名称来引用
7 c1 @) Q& ]3 u: j0 k. W( V (1).@After(“com.javakc.spring.schemaaop.TestPointcut.t1()”)
, R# T& _$ h+ H v' j 2.直接引用匿名的pointcut; [* q- t) b4 U
(1).@After(“execution(* com.javakc.spring.schemaaop.Api.test1())”): p/ n/ Q7 Z6 ^# T' o
@After(“com.javakc.spring.schemaaop.TestPointcut.t1()”), j8 m( x2 j) B# f' W
public void testAfter(){- R% V! i7 [# Y) ^7 W
System.out.println(“after1== >pointcut”);# R* `2 P! V4 x' }' ]3 z7 y* P
}
2 r6 G ?! U1 F i; k% _" W9 {: b! A3 Y 5.4.5.@AfterThorwing
* A" U1 \& @/ u ?$ Z; _' m+ ~
% j* G Y- ]$ N r
' c2 }- z/ l) U! @- 描述一下spring中BeanFactory和ApplicationContext的差别& G! O/ @, q; Q# o
% ^& Z9 M r" h8 O* @. ]% P* x! }) V
BeanFactory是一个Interface,这是Spring的核心。它仅仅只是提供的一些基本功能。ApplicaionContext 也是一个interface,这是从BeanFactory继承过来的所以它具备了BeanFactory的所有功能。但它也从其它的类或interface得到了一些特性。比如提供国际化的消息访问,资源访问,事件传播。 但其主要区别在于BeanFactory是延迟加载,如果Bean的某一个属性没有注入,BeanFactory加载后,直至第一次使用getBean方法调用此Bean时才会抛出异常;而ApplicationContext则在初始化自身时检验,这样有利于检查所依赖属性是否注入;所以通常情况下我们选择使用ApplicationContext. 代码示例: BeanFactory beanFactory = new XmlBeanFactory(new FileSystemResource(“beans.xml”)); ApplicationContext cxt = new ClassPathXmlApplicationContext(“beans.xml”);
! M4 I. @ ]9 e: g- 谈谈spring对DAO的支持. u2 L' w* R1 |6 O5 Z9 {: \! f
0 p U" b* D& W0 [* `' ^
Spring提供的DAO(数据访问对象)支持主要的目的是便于以标准的方式使用不同的数据访问技术。
`, W' C1 w5 F 简化 DAO 组件的开发。/ J c, h- P' p8 _, n* a: r6 k
Spring提供了一套抽象DAO类供你扩展。这些抽象类提供了一些方法,用来简化代码开发。
5 k, f7 r% r$ O; g2 S( t IoC 容器的使用,提供了 DAO 组件与业务逻辑组件之间的解耦。所有的 DAO 组件,都由容器负责注入到业务逻辑组件中,其业务组件无须关心 DAO 组件的实现。
9 p& g! D3 T' `; Q! z" l+ i 面向接口编程及 DAO 模式的使用,提高了系统组件之间的解耦,降低了系统重构的成本。
; Q u2 F& N3 {( T. L5 g 方便的事务管理: Spring的声明式事务管理力度是方法级。/ p1 a: p$ B* Y
异常包装:Spring能够包装Hibernate异常,把它们从CheckedException变为RuntimeException; 开发者可选择在恰当的层处理数据中不可恢复的异常,从而避免烦琐的 catch/throw 及异常声明。
& F0 P- G- j' U, k) Q0 W
2 X2 u9 e4 o7 F/ X p3 D+ [+ \, I4 L& o; J) [
- 谈谈spring对hibernate的支持1 ]' R- g4 N& @
2 l0 O2 q3 |" f: Q& O
在所有的 ORM 框架中, Sping 对 Hibernate 的支持最好。如 SessionFactory 的注入、HibernateTemplate 的简化操作及 DAO 支持等。另外, Spring 还提供了统一的异常体系及声明式事务管理等。
/ p9 x6 M7 J$ o' S3 I8 ^ 一旦 Hibernate 处于 Spring 的管理下, Hibernate 所需要的基础资源,都由 Spring 提供注入。Hibernate 创建 SessionFactory 必需的 DataSource ,执行持久化必需的 Session 及持久层访问必需的事务控制等,这些原本必须通过代码控制的逻辑,都将由Spring 接管ataSource, SessionFactory, TransactionManager等,都将作为 Spring 容器中的 bean。将这些bean 放在配置文件中管理。
( j' T# h, z6 t H- T 1、通用的资源管理: Spring 的 ApplicationContext 能管理 SessionFactory,使得配置值很容易被管理和修改,无须使用Hibernate 的配置文件。详细配置如下:
: K1 u9 v4 Y3 k1 d5 l ; b/ d6 \ \0 p- _# R2 k! l
class=“org.apache.commons.dbcp.BasicDataSource”>
" Q' Z% ?6 k- S0 L4 ]( d/ s ) u; w2 b+ X# L# r+ I- t
oracle.jdbc.driver.OracleDriver' w8 F2 |6 h6 K2 M+ |6 E
4 v ^9 ~& T. t5 W) v7 Q
4 |4 i: c* y% q' N) A3 i; {/ { jdbcracle:thinlocalhost:1521rcl
3 B! j% G2 e7 E% Z+ p8 V9 P
* ]4 n/ e: H$ o5 o1 I) R6 I
f8 ^" e6 G: |1 o4 t javakc2
3 z: K4 ?* q0 _- z4 T! f/ b % k+ H! q$ J- O Q5 h
+ M1 [) d+ g% h# _1 w. U
javakc2# u6 w6 o1 i5 ^
5 I1 g# k! l1 H2 ]! V) \3 h$ A' ` / H, ~' J7 D4 c: o
" i( D. F0 Y, u0 k# E+ ]" p! L# e( N4 g
class=“org.springframework.orm.hibernate3.LocalSessionFactoryBean”>
8 R* v- H- y$ Q
0 r& S+ L4 k3 M4 z- c% h 4 |' P7 {& |; S2 n3 [0 a& \4 H0 x$ R
, @& d! j; @* A1 ?/ k com/javakc/spring/h3/UserModel.hbm.xml( X1 a$ |0 \5 q% ]+ q
- u' M, z/ u! c0 M# F4 p- s ) x0 H5 W& P! d, v$ f$ ^
+ Z! ~. A7 _! M* _ ; r k: V: T0 L) I7 d
hibernate.dialect=org.hibernate.dialect.OracleDialect1 x- V0 S1 @ @% k7 l- d& c
' i7 a& i% i& Y
" X& c0 E" O1 ^ & j# J& j, r) n- \$ K
7 c1 T. K7 S3 Q/ f9 a: T
8 \9 n1 e$ r* ?' r
8 T- D K, a: {% {* Y 如果需要使用容器管理的数据源,则无须提供数据驱动等信息,只需要提供数据源的JNDI 即可。对上文的SessionFactory只需将dataSource的配置替换成 JNDI 数据源,并将原有的 myDataSource Bean 替换成如下所示: class=“org.springframework.jndi.JndiObjectFactoryBean”>. \9 g/ ]/ s( b. \
; @- j' r" Z, L4 u java:comp/env/jdbc/myds
% H5 B X9 o5 y : x3 l1 V( n8 I7 _6 l: O% k
2、有效的 Session 管理: Dao类继承HibernateDaoSurport后,Spring 提供了 HibernateTemplate,用于持久层访问,该模板类无须显示打开 Session及关闭 Session。它只要获得 SessionFactory 的引用,将可以智能打开 Session,并在持久化访问结束后关闭 Session ,程序开发只需完成持久层逻辑,通用的操作则由HibernateTemplate 完成。 3、统一的事务管理。无论是编程式事务,还是声明式事务, Spring 都提供一致的编程模型,无须烦琐的开始事务、显式提交及回滚。 建议使用声明式事务管理,Spring 的声明式事务以 Spring 的 AOP 为基础。可将事务管理逻辑与代码分离。代码中无须实现任何事务逻辑,程序开发者可以更专注于业务逻辑的实现。声明式事务不与任何事务策略藕合,采用声明式事务可以方便地在全局事务和局部事务之间切换。 Spring声明性事务有两种配置方法,一种是xml配置:
, I# F: z! p. |$ @7 x
$ w5 n0 z/ {4 c* A# p
4 G0 B9 E% p2 ?7 J - C, z+ R& p7 i. A0 R
; ^+ R! g* L4 \ " g# `7 x# v6 g; }7 Z& ~: C
7 o. R2 y- v% }, n# {
% W- r: m' b( C U& Q 4 C1 k& A( }+ p6 J: C! W
" r( v8 S Y& i* x$ p7 U
+ G. p% |! q" @ + Y) {& q6 K4 S
$ h8 h5 y9 k: A$ ]" F 8 W+ I6 ~& N) x/ V* ~0 t: U! H
另一种是通过注解,在需要添加事务的类上注明 @Transactional . R/ i* S( T! L$ V% i
Spring2.0之前事务的写法/ ^8 ]. ?) L% H8 S6 y {
- |$ }9 E. u+ q8 h+ F1 E0 T" q3 L* b. k2 @/ r
class=”org.springframework.transaction.interceptor.TransactionProxyFactoryBean”( a% D& ^0 S! T% A- c7 t5 R. M
; y' W' y8 X- v. g abstract=”true”>
. g8 w! I2 J7 }" N% W: {% P% G0 ~
' _! \' x. y8 I3 G
6 I6 ~6 O3 F) j6 w$ U5 a5 h% p
5 F1 t2 Y! p4 W! q4 X: L) E
PROPAGATION_REQUIRED,readOnly
6 e: D; E& }/ t* }+ ]! M3 I% Q; k8 o
PROPAGATION_REQUIRED, ?( V3 h2 _- }( ]/ k' {
- M: Z( v7 a/ I4 k& T- _9 \& Y# z. z+ f) i; | ^
% h/ @6 u1 k2 ~$ Q$ g: z; }
/ J( y% V u: q |
! g; y0 k$ b' O/ k, @% I( b+ P& {2 q. A: u. [/ z
- 谈谈Spring对事务的支持! {' Y* L# z R
! W7 y1 V3 h- g p e% ~7 V
3 ~. G; x6 ^ _. A1、声明式事务管理:
1.流程:由客户端访问—-aop监控—-调用advice来追加事务 2.做法: 2.1 在配置文件的头中引入xmlns:tx 和schema的文件 2.2 2.3 注入数据源 2 U. M* l* j0 ~1 Q$ N
3 e( \1 V5 l7 ]7 |1 |& o: `3 R
& E" R3 h3 @! }8 s; j) u( K4 r& H. Z
" P+ X6 B) [, T0 h0 O
) ?3 c: a0 ?7 ]# [, W( X( k* ^. T* `
2.4 由spring实现的事务管理,但需要注入数据源
}' }$ c- S3 I& i. T5 e* A( Q9 w% ^, i' Q* \3 b
$ W; ?- o. I4 P# k$ k) F2.5 事务监控所有的方法(事务加强) 2 `4 j& T( `! N& t7 i7 |" }; @# d
" @! M9 D4 V, C) U
, E4 D+ R9 x/ G0 X6 Z7 v4 H( k* e! h. R) b
. J8 q6 A0 b8 T f1 L6 _ E& n
2.6 定义切入点 , [" D* I# e# T: R$ l4 x
2 r6 x6 t4 F# |* s# E% f; w
2 }0 Z5 P! q1 V; S
9 O& J. _+ F6 \. |
6 G7 z' f2 S3 K# P7 T- K9 v! o- I2、使用注解实现事务管理: 1.注解@Transcational (可以在类上,也可以在方法上) 2.在配置文件中同样需要注入dataSource和spring的事务管理 3.使用注解的方法来追加事务 注解驱动
: F% ?& w! L2 j
; K: J' x2 O! c. F) `2 b' j9 \如何在Spring中使用Hibernate的事务:
+ f" l: W, g2 M$ [; x2 G# D 5 N3 D9 X8 ^; |1 O
# V* ]5 j! ^/ h0 v) B7 F3 d
" H; P5 Z8 v, z% e# F如何在Spring中使用JTA的事务:6 `4 u% F/ g, p8 M
) O" h3 _, t0 W1 @6 x7 |% R |