Spring概述
Spring介紹
Spring它是一個一站式的分層輕量級框架。php
Spring體系結構
1. core containercss
a) beans與core 它們提供spring框架最基本功能,包含ioc與dihtml
b) context 上下文對象,基於beans與coresjava
c) spel它是sprng提供的一個表達式語言web
2. Data access/integration面試
a) 數據訪問正則表達式
b) 集成spring
3. Websql
a) Spring自己提供springmvc數據庫
b) 也能夠與其它的web層進行集成
4. AOP
AOP大部分狀況下是使用動態代理來實現的。
5. Test
使用spring能夠方便的進行測試
Spring框架優勢
n 方便解耦,簡化開發
Spring就是一個大工廠,能夠將全部對象建立和依賴關係維護,交給Spring管理
n AOP編程的支持
Spring提供面向切面編程,能夠方便的實現對程序進行權限攔截、運行監控等功能
n 聲明式事務的支持
只須要經過配置就能夠完成對事務的管理,而無需手動編程
n 方便程序的測試
Spring對Junit4支持,能夠經過註解方便的測試Spring程序
n 方便集成各類優秀框架
Spring不排斥各類優秀的開源框架,其內部提供了對各類優秀框架(如:Struts、Hibernate、MyBatis、Quartz等)的直接支持
n 下降JavaEE API的使用難度
Spring 對JavaEE開發中很是難用的一些API(JDBC、JavaMail、遠程調用等),都提供了封裝,使這些API應用難度大大下降
IOC與DI
Spring的jar包下載
Spring的官網:spring.io
咱們課程中講解使用的是spring4.2.4
在spring3.0.2版本後,不在提供依賴jar包
docs 存在API和規範文檔
libs 開發jar包
schema 開發過程當中須要的xml的schema約束
spring開發環境搭建
在spring開發中,咱們要根據不一樣的狀況來導入不一樣的jar包,當前咱們要講解的是關於ioc與di
對於ioc與di講解咱們只須要使用spring的核心功能。
1. beans相關
2. core相關
3. context相關
4. spel相關
咱們使用spring框架也會使用到配置文件,咱們須要在src下建立一個關於spring的配置文件,通常狀況名稱叫applicationContext.xml
問題:applicationContext.xml約束?
它的路徑:
spring-framework-4.2.4.RELEASE-dist\spring-framework-4.2.4.RELEASE\docs\spring-framework-reference\html
IOC快速入門
Ioc它是什麼,解決什麼問題,它的原理是如何實現。
IOC inversion ofController 控制反轉。
在程序中所說的IOC其實簡單說,就是原來由咱們本身實例化的對象交給spring容器來實始化。這時對象的實始化的權利就會反轉。
程序運行時報錯
緣由:當前環境須要一個commons-loggin的jar包
總結spring使用步驟:
1. 在applicationContext.xml文件中配置bean
2. 建立一個AppliCationContext對象
ApplicationContext它是BeanFactory的一個子接口,咱們在使用時使用的是AppliCationContext的實現類ClassPathXmlApplicationContext
能夠經過getBean(配置文件中id名稱)來獲取指定的對象。
DI
DI:dependencyinjection 依賴注入
在spring框架負責建立Bean對象時,動態將依賴對象注入到Bean組件。
簡單說,這時UserServiceImpl中的info屬性值就是ITCAST
面試題:IOC和DI區別?
IOC控制反轉,是指對象實例化權利由spring容器來管理
DI依賴注入 在spring建立對象的過程當中,對象所依賴的屬性經過配置注入對象中。
Bean獲取與實例化
ApplicationContext與BeanFactory關係
ApplicationContext它是擴展BeanFactory接口。
BeanFactory它採起延遲加載的方案,只有真正在getBean時纔會實例化Bean
在開發中咱們通常使用的是ApplicationContext,真正使用的是其實現類,
FileSystemXmlAppliCationContext 根據文件路徑獲取
ClassPathXmlApplicationContext 根據類路徑獲取
AppliCationContext它會在配置文件加載時,就會初始化Bean,而且ApplicationContext它提供不一樣的應用層的Context實現。例如在web開發中可使用WebApplicationContext.
Bean的實例化方式
無參數構造
對於這種方式,注意Bean類中必須提供無參數構造。
靜態工廠方法
須要建立一個工廠類,在工廠類中提供一個static返回bean對象的方法就能夠。
實例工廠方法
須要建立一個工廠類,在工廠類中提供一個非static的建立bean對象的方法,在配置文件中須要將工廠配置,還須要配置bean
Bean的做用域
在bean聲明時它有一個scope屬性,它是用於描述bean的做用域。
可取值有:
singleton:單例 表明在spring ioc容器中只有一個Bean實例 (默認的scope)
prototype多例 每一次從spring容器中獲取時,都會返回一個新的實例
request用在web開發中,將bean對象request.setAttribute()存儲到request域中
session用在web開發中,將bean對象session.setAttribute()存儲到session域中
在開如經常使用的值是singleton與prototype
Bean的生命週期
1. instantiate bean對象實例化
2. populate properties 封裝屬性
3. 若是Bean實現BeanNameAware執行setBeanName
4. 若是Bean實現BeanFactoryAwar或ApplicationContextAwar設置工廠setBeanFactory或上下文對象setApplicationContext
5. 若是存在類實現BeanPostProcessor(後處理Bean),執行postProcessBeforeInitialization
6. 若是Bean實現InitializingBean執行afterPropertiesSet
7. 調用自定義的init-method方法
8. 若是存在類實現BeanPostProcessor(處理Bean),執行postProcessAfterInitialization
9. 執行業務處理
10. 若是Bean實現DisposableBean執行destroy
11. 調用自定義的destroy-method
對於bean的生命週期方法:
第三步與第四步是讓Bean瞭解spring容器。
第五步與第八步能夠針對指定的Bean進行功能加強,這時通常會使用動態代理.
第六步與第十步:經過實現指定的接口來完成init與destroy操做
可是在開發中通常不使用第6步與第10步,緣由是咱們可使用第7步與第11步來完成。
第7步與第11步的初始化與銷燬操做它無耦合,推薦使用的。可是必須在配置文件中指定初始化與銷燬的方法
總結:
對於bean的生命週期,咱們須要關注的主要有兩個方法:
1. 加強bean的功能可使用後處理Bean, BeanPostProcessor
2. 若是須要初始化或銷燬操做咱們可使用init-method destroy-method
注意:destroy-method只對scope=singleton有效果。
Bean的屬性注入
在spring中bean的屬性注入有兩種
構造器注入
Setter方法注入
關於ref屬性做用
使用ref來引入另外一個bean對象,完成bean之間注入
集合屬性的注入
在spring中對於集合屬性,可使用專門的標籤來完成注入例如:list set map properties等集合元素來完成集合屬性注入.
List屬性注入
若是屬性是數組類型也可使用list完成注入
Set屬性注入
Map屬性注入
Properties屬性注入
Java.util.Properties是java.utilsMap的實現類,它的key與value都是String類型.
名稱空間p和c的使用
Spring2.0之後提供了xml命名空間。
P名稱空間
C名稱空間
首先它們不是真正的名稱空間,是虛擬的。它是嵌入到spring內核中的。
使用p名稱空間能夠解決咱們setter注入時<property>簡化
使用c名稱空間能夠解決咱們構造器注入時<constructor-arg>簡化
使用setter注入
在applicationContext.xml文件中添加p名稱空間簡化setter注入
使用c名稱空間來解決構造器注入
在applicationContext.xml文件中添加c名稱空間
注:若是c或p名稱空間操做的屬性後綴是」-ref」表明要引入另外一個已經存在的bean,例如
SpEl
spring expression language 是在spring3.0之後的版本提供
它相似於ognl或el表達式,它能夠提供在程序運行時構造複雜表達式來完成對象屬性存儲及方法調用等。
Spel表達式的格式 #{表達式}
示例1:完成bean之間的注入
示例2 支持屬性調用及方法調用
Spring註解開發
在spring中使用註解,咱們必須在applicationContext.xml文件中添加一個標籤
<context:annotation-config/>做用是讓spring中經常使用的一些註解生效。
要使用contex名稱空間,必須在applicationContext.xml文件中引入
完成bean註冊操做
@Component
測試時報錯
緣由:若是你使用的是spring3.x那麼不會出現這個錯誤,若是使用的是spring4.x會報錯,緣由是缺乏jar包。
導入jar後運行還有錯誤
咱們在applicationContext.xml文件中使用了一個標籤 <context:annotation-config/>,它表明的是可使用spring的註解,可是咱們在類上添加的註解,spring不知道位置。
要解決這個問題,咱們可使用<context:component-sacn base-package=」」>
在spring2.5後爲@Component添加了三個衍生的註解
@Rpository 用於DAO層
@Service 用於service層
@Controller 用於表現層
對於咱們的bean所處在的位置能夠選擇上述三個註解來應用,若是你的bean不明確位置,就可使用@Component.
屬性依賴注入
1. 簡單的屬性注入
2. 複雜的屬性注入
注意:若是要掃描多個包下的註解能夠寫成如下:
或
注意:@Value @Autowired它們能夠修飾屬性,也能夠修飾setter方法,若是寫在屬性上,就不須要提供setter方法。
@Autowired它默認是根據類型進行注入。
若是與@Qualifier一塊兒使用,就能夠根據名稱來進行注入。
咱們也可使用下面的方式來根據名稱進行屬性注入
其它註解
@Scope它以描述bean的做用域。
它至關於init-method=」myInit
它至關因而destroy-method=」myDestroy」
注意:對於銷燬的方法它只對bean的scope=singleton有效。
Spring在web開發中的應用
1.,在web項目中要使用spring須要導入一個jar包
2.在web.xml文件中配置Listener
這個ContextLoaderListener它實現了ServletContextListener
在這個listener中,當服務器啓動時,將ApplicationContext對象,實際上是它的一個實現類
WebApplicationContext,對象存入到了ServletContext中。
3.咱們還須要在web.xml文件中配置applicationContext.xml文件的位置
默認狀況下會在WEB-INF目錄 下查找applicationContext.xmls
若是applicationContext.xml文件不是在默認位置,咱們能夠在web.xml文件中配置
Classpath:applicationContext.xml 它表明的是在當前工程的類路徑下(能夠理解成是在src)下來查找applicationContext.xml文件。
contextConfigLocation它是在listener中聲明的一個常量,描述的就是spring配置文件的位置。
Spring整合junit4測試
Spring整合junit4能夠方便咱們的測試。
1. 須要導入一個spring-test.jar包
2. 能夠在測試類上以下操做
Spring AOP
AOP概述
在軟件業,AOP爲Aspect Oriented Programming的縮寫,意爲:面向切面編程,經過預編譯方式和運行期動態代理實現程序功能的統一維護的一種技術。AOP是OOP的延續,是軟件開發中的一個熱點,也是Spring框架中的一個重要內容,是函數式編程的一種衍生範型。利用AOP能夠對業務邏輯的各個部分進行隔離,從而使得業務邏輯各部分之間的耦合度下降,提升程序的可重用性,同時提升了開發的效率。
AOP是一個概念,並無設定具體語言的實現,它能克服那些只有單繼承特性語言的缺點,spring2.0以後整合AspectJ第三方AOP技術。
AspectJ是一個面向切面的框架,它擴展了Java語言。AspectJ定義了AOP語法因此它有一個專門的編譯器用來生成遵照Java字節編碼規範的Class文件。
主要功能
日誌記錄,性能統計,安全控制,事務處理,異常處理等等
主要意圖
將日誌記錄,性能統計,安全控制,事務處理,異常處理等代碼從業務邏輯代碼中劃分出來,經過對這些行爲的分離,咱們但願能夠將它們獨立到非指導業務邏輯的方法中,進而改變這些行爲的時候不影響業務邏輯的代碼。
AOP與OOP區別
OOP(面向對象編程)針對業務處理過程的實體及其屬性和行爲進行抽象封裝,以得到更加清晰高效的邏輯單元劃分。
而AOP則是針對業務處理過程當中的切面進行提取,它所面對的是處理過程當中的某個步驟或階段,以得到邏輯過程當中各部分之間低耦合性的隔離效果。這兩種設計思想在目標上有着本質的差別。
換而言之,OOD/OOP面向名詞領域,AOP面向動詞領域。
AOP相關術語
目標對象target
指的是須要被加強的對象,因爲spring aop是經過代理模式實現,從而這個對象永遠是被代理對象。
鏈接點(join point)
所謂鏈接點是指那些被攔截到的點,在spring中這些點指的是方法,由於spring只支持方法類型的鏈接點
切入點(pointcut)
表示一組 joint point,這些 joint point 或是經過邏輯關係組合起來,或是經過通配、正則表達式等方式集中起來,它定義了相應的 Advice 將要發生的地方
簡單說切入點是指咱們要對哪些鏈接點進行攔截的定義
通知(advice)
所謂通知是指攔截到鏈接點以後所要作的事情就是通知,通知分爲前置通知,後置通知,異常通知,最終通知,環繞通知
Advice 定義了在 pointcut 裏面定義的程序點具體要作的操做
引介introduction
引介是一種特殊的通知,在不修改類代碼的前提下,introduction能夠在運行期爲類動態地添加一些方法或屬性
切面aspect
是切入點和通知的結合
織入weaving
織入是一個過程,是將切面應用到目標對象從而建立出AOP代理對象的過程,織入能夠在編譯期,類裝載期,運行期進行。
Spring採用動態織入,而aspectj採用靜態織入
代理Proxy
一個類被AOP織入加強後,就產生一個結果代理類
AOP底層實現
AOP分爲靜態AOP和動態AOP。靜態AOP是指AspectJ實現的AOP,他是將切面代碼直接編譯到Java類文件中。動態AOP是指將切面代碼進行動態織入實現的AOP。Spring的AOP爲動態AOP,實現的技術爲: JDK提供的動態代理技術 和 CGLIB(動態字節碼加強技術)
JDK動態代理
在運行,在JVM內部動態生成class字節碼對象(Class對象)
Jdk動態代理只針對於接口操做
第一個參數:目標類的類加載器對象
第二個參數:目標類的實現接口的Class[]
第三個參數:InvocationHandler它是一個接口,它的做用是是代理實例的調用處理程序實現的接口,接口中定義了一個方法
目標Target
代理工廠
CGLIB動態代理
CGLIB(Code Generation Library)是一個開源項目
是一個強大的,高性能,高質量的Code生成類庫,它能夠在運行期擴展Java類與實現Java接口。CGLIB包的底層是經過使用一個小而快的字節碼處理框架ASM,來轉換字節碼並生成新的類
若是你要單獨使用CGLIB,那麼須要導入cglib的jar包還須要一個asm相關jar包,可是spring框架的spring-core.jar包中已經集成了cglib與asm
注意:jdk的動態代理只能夠爲接口去完成操做,而cglib它能夠爲沒有實現接口的類去作代理,也能夠爲實現接口的類去作代理。
Cglib動態代理
setCallback傳遞的參數是Callback類型,咱們使用的是MethodInterceptor
注意:cglib它能夠爲沒有實現接口的類作代理,也能夠爲接口類作代理.
問題:spring採用的是哪種動態機制:
若是目標對象,有接口,優先使用jdk動態代理
若是目標對象,無接口,使用cglib動態代理。
Spring AOP編程
Spring的傳統aop編程
講解的目的是爲了更好的理解aop。
在傳統的spring aop開發中它支持加強(advice)有五種:
1. 前置通知 目標方法執行前加強 org.springframework.aop.MethodBeforeAdvice
2. 後置通知 目標方法執行後加強 org.springframework.aop.AfterReturningAdvice
3. 環繞通知 目標方法執行先後進行加強 org.aopalliance.intercept.MethodInterceptor
4. 異常拋出通知目標方法拋出異常後的加強org.springframework.aop.ThrowsAdvice
5. 引介通知在目標類中添加一些新的方法或屬性(不講解)
org.springframework.aop.IntroductionInterceptor
經典的基於代理的AOP開發(瞭解)
基本的jar包
1. bean
2. core
3. context
4. expression
5. aop
6. 須要aop聯盟的依賴jar包
第一步:編寫目標(target)
第二步加強(advice)
第三步在applicationContext.xml文件中配置
第四測試
基於aspectJ切點傳統開發
第一步:在spring的配置文件中定義目標與通知
第二步:使用<aop:xxx>標籤來完成切面與切點聲明
注意1:須要在xml配置文件中導入aop聲明
注意2:由於咱們使用aspectj的切面聲明方式須要在導入aspectj的jar包
傳統spring aop開發總結
第一步:編寫目標對象(target)
第二步:編寫通知(advice)
傳統的aop開發中,通知是須要實現指定接口。
第三步在配置文件中配置切面(切面=切點+通知)
<aop:config>來聲明要對aop進行配置
<aop:pointcut>它是用於聲明切點(簡單說就是對哪些方法進行攔截)
<aop:advisor> 定義傳統的aop的切面,傳統的aop切面它只能包含一個切點與一個加強
<aop:aspect>定義aspectj框架的切面.,它能夠包含多個切點與多個通知
關於切點表達式寫法
這個語法源於aspectJ的語法,spring中aop開發,對aspectj不是徹底支持,只支持部分語法。
在開發中使用的比較多的是execution語法.
關於execution語法經常使用:
1. execution(public * *()) 全部的public的方法
2. execution(*cn.itheima.aop.*(..)) 全部的aop包下的全部類的方法(不包含子包)
3. execution(*cn.itheima.aop..*(..)) 全部的aop包及其子包下的全部類的方法
4. execution(*cn.itheima.aop.IOrderService.*(..)) IOrderService接口中定義的全部方法
5. execution(*cn.itheima.aop.IOrderService+.*(..)) 匹配實現特定接口全部類的方法
6. execution(* save*(..)) 區配全部的以save開頭的方法
Spring整合aspectj框架實現的aop
在如今的開發中使用這種方案比較多.
在spring2.0之後它支持jdk1.5註解,而整合aspectj後可使用aspectj語法,能夠簡化開發。
Aspect:切面 =切點+通知(多個切點與多個通知的組合)
AspectJ 它是一個第三方框架,spring從2.0後可使用aspectJ框架的部分語法.
AspectJ框架它定義的通知類型有6種
1. 前置通知Before 至關於BeforeAdvice
2. 後置通知AfterReturning 至關於AfterReturningAdvice
3. 環繞通知 Around 至關於MethodInterceptor
4. 拋出通知AfterThrowing 至關於ThrowAdvice
5. 引介通知DeclareParents 至關於IntroductionInterceptor
6. 最終通知After 無論是否異常,該通知都會執行
相比spring 的傳統AOP Advice多了一個最終通知
基於xml配置方案
第一步:建立目標(target)
第二步:建立通知(加強 advice)
注意:在aspectj中它的加強能夠不實現任何接口,只須要定義出加強功能(方法)
第三步:在spring的xml 配置文件中來配置
<aop:config>下的<aop:aspect>是aspectJ框架用來聲明切面的。
前置通知
後置通知
環繞通知
異常拋出
注意:目標行爲只有拋出了異常後纔會執行這個加強方法
最終通知
不管是否有異常,最終通知都會執行.
關於通知上的參數
1. 在前置通知上能夠添加JoinPoint參數
經過它能夠獲取目標相關的信息
使用前置通知能夠完成日誌記錄,權限控制
2. 在後置通知上添加的參數
第二個參數val它能夠獲取目標方法的返回值
注意:須要在配置文件中配置
3. 環繞通知上的參數
它是咱們開發中應用最多的,能夠完成日誌操做,權限操做,性能監控,事務管理
4. 拋出異常通知上的參數
第二個參數Throwable它是用於接收拋出的異常
注意:須要在配置文件中聲明
5. 最終通知上的參數
可使用最終通知完成資源釋放
關於代理方式選擇
在spring的aop開發中,它使用的是代理方案,代理實現有兩種:
1. jdk的proxy
2. cglib
spring框架默認狀況下,會對有接口的類使用proxy代理。沒有接口的類使用cglib代理
Proxy-target-class的值默認是false,它表明有接口使用proxy代理
問題:若是如今對目標要使用cglib代理(不考慮是否有接口)?
只須要將proxy-target-class設置爲true.
基於annotation方案
第一步:編寫目標
在spring的配置文件中配置掃描註解
第二步:編寫加強(advice)
使用@Aspect來聲明切面
使用@Before來聲明前置通知
注意:必須在spring的配置文件中開啓aspectJ註解自動代理功能。
第三步:測試
其它通知類型及參數
後置通知
環繞通知
異常拋出通知
最終通知
使用@Pointcut註解定義切點
在每個通知中定義切點,工做量大,不方便維護,咱們可使用@Pointcut來聲明切點
切點容許邏輯運算例如mypointcut()||mypointcut1
關於代理方式選擇
Proxy-target-class默認值是false,表明的是若是目標是有接口的使用proxy代理,若是沒有接口使用cglib.
若是將proxy-target-class=true,無論目標是否有接口,都會使用cglib進行代理。
Spring jdbc Template
Spring提供了一個jdbc模板,它相似於dbutils工具。
問題:如何使用spring jdbc template?
第一:要導入相關的jar包
在這個基礎上咱們還須要導入
還須要導入相關的數據庫驅動jar包。
第二:spring jdbc template快速入門
快速入門
第一步:導入相關jar包,建立了一個JdbcTemplateTest1測試類
第二步:建立庫與表
CREATEDATABASE springtest;
USEspringtest;
CREATETABLE t_user(
id INT PRIMARY KEY AUTO_INCREMENT,
NAME VARCHAR(20),
age INT,
sex VARCHAR(20)
)
INSERTINTO t_user VALUES(NULL,'tom',20,'男');
INSERTINTO t_user VALUES(NULL,'fox',30,'男');
INSERTINTO t_user VALUES(NULL,'tony',40,'男');
SELECT *FROM t_user;
第三步:編碼
配置spring內置的鏈接池DriverManagerDataSource
C3P0開源鏈接池配置
1. 導入c3p0相關的jar包
2. 建立一個ComboPoolDataSource對象,設置相關的屬性
引入外部屬性文件
Spring支持將常常修改屬性,在properties文件中聲明,在xml配置文件中引入外部的properties文件的信息。
在applicationContext.xml文件中引入
在本身配置中須要從properties文件中引入的信息可使用${name}方式來獲取
JdbcTemplate CRUD
執行insert update delete操做
只須要使用JdbcTemplate的update方法就能夠執行insert update delete操做
執行select操做
簡單數據返回
複雜數據返回
注意:若是隻返回一個domain對象,可使用queryForObject方法,若是返回的是List<?>對象,可使用query方法,可是都須要使用RowMapper來對ResultSet進行處理。
RowMapper它有一個實現類叫BeanPropertyRowMapper
若是使用BeanPropertyRowmapper,實體類必須提供一個無參數的public構造方法,類中的bean屬性名稱與表中的列要對應
注意:這個類是在spring2.5後提供。
Spring 事務管理
案例—轉帳操做
建立一個關於賬戶表
CREATETABLE account(
id INT PRIMARY KEY AUTO_INCREMENT,
NAME VARCHAR(20),
money DOUBLE
)
INSERTINTO account VALUES(NULL,'tom',1000);
INSERTINTO account VALUES(NULL,'fox',1000);
建立service與dao
對於數據的操做使用spring jdbc template
關於service與dao的配置
咱們讓dao去extends JdbcDaoSupport類,這個類中它建立了JdbcTempate,前提是咱們須要注入一個dataSource.
在dao中在獲取JdbcTemplate可使用父類提供的getJdbcTemplate方法來獲取。
轉帳操做的問題
若是在轉帳操做過程當中出現問題,那麼轉帳會出現問題,結果以下
也就是咱們程序須要事務控制。
Spring事務管理機制
Spring事務管理的四個優勢:
1. 提供一致的對於不一樣的事務管理的API
2. 支持聲明式事務管理(重點)
3. 編程事務管理(在開發中應用比較少)
4. 優秀的整合與Spring的數據訪問
咱們重點講解spring的事務管理的相關的API,還有聲明式事務管理
Spring事務管理主要提供了三個接口來完成
1. org.springframework.transaction.PlatformTransactionManager
這是一個事務管理器,能夠來選擇相關的平臺(jdbc hibernate jpa…)
2. TransactionDefinition
它定義事務的一些相關信息 例如 隔離 傳播 超時只讀
3. TransactionStatus
它主要描述事務具體的運行狀態
PlatformTransactionManager
平臺事務管理器
在不一樣的持久化層解決技術它的事務代碼不同。
JDBC開發
Connection con=……;
con.setAutoCommit(false);//開啓事務
con.rollback();
con.commit();
Hibernate開發
Session session=….;
Transactiont=session.beginTransaction();
t.commit();
t.rollback();
PlatformTransactionManager接口API
DataSourceTransactionManager 主要針對於JdbcTemplate開發 MyBatis開發
HibernateTransactionManasger主要針對於Hibernate開發
JpaTransactionManager 主要針對於JPA開發。
TransactionDefinition
它描述的是事務的定義信息。
在TransactionDefinition中定義了大量的常量
隔離
如下是關於隔離性相關信息
事務的四個特性 ACID 原子性 一致性 隔離性 持久性。
不考慮事務隔離性有什麼問題?
髒讀,不可重複讀 虛讀。
ISOLATION_DEFUALT 它使用後端數據庫的默認隔離級別(spring中選項)
ISOLATION_READ_UNCOMMITTED 不能解決問題,會發生髒讀 不可重複讀 虛讀
ISOLATION_READ_COMMITTED 能夠解決髒讀 會產生不可重複讀與虛讀。
ISOLATION_REPEATABLE_READ能夠解決髒讀,不可重複讀解決不了虛讀
ISOLATION_SERIALIZABLE串行化,能夠解決全部問題
對於不現的數據庫,它的底層默認事務隔離級別不同。
Oracle數據庫它默認的是read_committed
Mysql數據庫它默認的是repeatable_read.
超時
默認值是-1 它使用的是數據庫默認的超時時間。
只讀
它的值有兩個true/false,若是選擇true通常是在select操做時
傳播
它解決的是兩個被事務管理的方法互相調用問題。它與數據庫不要緊,是程序內部維護的問題。
如下定義了事務的傳播行爲
以上操做中最經常使用的三種:
PROPAGATION_REQUIRED 默認值 兩個操做處於同一個事務,若是以前沒有事務,新建一個事務
兩個操做處於不一樣的事務
PROPAGATION_NESTED 它是一種嵌套事務,它是使用SavePoint來實現的。事務回滾時能夠回滾到指定的savepoint,注意:它只對DataSourceTransactionManager有做用
如下了解
PROPAGATION_SUPPORTS 支持當前事務,若是不存在,就不使用事務
PROPAGATION_MANDATORY 支持當前事務,若是不存在,拋出異常
PROPAGATION_NOT_SUPPORTED 以非事務運行,若是有事務存在,掛起當前事務
PROPAGATION_NEVER 以非事務運行,若是有事務存在,拋出異常
TransactionStatus
它定義了事務狀態信息,在事務運行過程當中,獲得某個時間點的狀態
聲明式事務管理
事務管理方式
1. 編碼方案不建議使用,它具備侵入性。在原有的業務代碼基礎上去添加事務管理代碼
2. 聲明式事務控制,基於AOP對目標進行代理,添加around環繞通知。
這種方案,它不具備侵入性,不須要修改原來的業務代碼
基於xml配置聲明式事務管理方案
第一步:在applicationContext.xml文件中添加aop與tx的名稱空間
第二步:在applicationContext.xml文件中配置
Spring提供的advice是傳統的springadvice
1. 聲明事務管理器
2. 配置通知
Spring爲咱們提供了一個TransactionInterceptor來完成加強
對於這個加強,咱們可使用spring爲咱們提供的一個標籤<tx:advice>來完成操做
3. 配置切面
由於使用的是傳統的spring的advice,須要使用<aop:advisor>
基於annotation聲明式事務管理方案
可使用@Transaction來在類或方法上添加聲明式事務管理
注意:須要在applicationContext.xml文件中使用
至關於開啓註解事務控制
問題:關於xml方式與annotation方式的優缺點?
從簡單上來講,使用註解更方便。
使用配置的方案,能夠對事務配置進行集中維護。
SSH框架整合
SSh=struts2+spring+hibernate
struts2 2.3.24
spring 4.2.4
hibernate 5.0.7
關於xml配置文件的整合方式
SSH整合jar包
Struts2框架須要jar包
Asm 是關於字節碼操做
Commons-fileupload 關於文件上傳
Commons-io 關於io流操做工具
Commons-lang 也是一個工具,包含了關於數據與字符串操做
Freemaker 標籤庫模板文件
Javassist 它也是關於字節碼操做,動態代理可使用它實現(相似於cglib)
Log4j關於日誌
Ognl 關於ognl表達式
Struts2-core xwork-cor struts2框架底層是使用xwork
Struts2與spring整合還須要這個包
若是須要使用struts2提供的json處理
注意:若是使用註解方案,咱們還須要導入一個jar包
Hibernate框架須要的jar包
Antlr 語法解析包
Dom4j 解析xml
Geronimo-jta apache geronimo它是一個開源javaEE服務器 Geronimo-jta是這個開源項目提供jar包,在hibernate中是關於jta事務相關
Hibernate-commoins-annotations
這個包是咱們在hibernate下來使用jpa相關的註解,這樣它不依賴於hibernate
Hibernate-core 開發hibernate必須
Hibernate-jpa 它是關於hibernate對jpa的支持
Jandex 用於索引annotation
Javassist 關於字節碼操做(注意:strtus2中也引入這個jar包了)
Jboss-logging 它是關於jboss統一日誌處理
若是使用關於jpa相關操做須要導入jpa依賴jar包
C3p0鏈接池
還須要數據庫相關的驅動jar包
還須要靜態日誌處理
Spring框架須要的jar包
Spring最基本jar包
AOP開發
Spring jdbc
Spring 事務管理須要tx
Spring整合hibernate
Spring整合web開發
若是使用到junit測試
還須要commons-loggin jar包
建立工程完成整合前期準備
須要的配置文件:
Strtsu2框架 src/strtus.xml
Hibernate框架 src/hibernate.cfg.xml 在domain有 Xxx.hbm.xml
Spring框架 src/applicationContext.xml
關於日誌 log4j.properties
關於數據庫鏈接 db.properties
Spring整合hibernate
基本原理:就是由spring來管理hibernate的SessionFactory
方式一:零障礙整合(瞭解)
咱們只須要使用spring中提供的一個LocalSessionFacotry來加載Hibernate的配置文件。
Ssh-xml工程加載到服務器後,若是能夠自動建立表,就表明spring整合hibernate ok.
注意:咱們必須配置spring的ContextLoaderListener
方式二(spring管理hibernate配置)
不在須要hibernate.cfg.xml文件,全部關於hibernate.cfg.xml文件中的配置都在spring的配置文件中來配置。
首先要配置數據源
接下來引入properties文件
建立LocalSessionFactoryBean來完成spring管理hibernate中的SessionFactory
上述的props能夠簡化成下面方案
加載hbm.xml配置文件
mappingResources它相似於咱們以前<mappingresource=」」>
mappingLocations它加載時是根據類路徑加載classpath:路徑
mappingJarLocations它會加載jar文件中的hbm.xml文件
mappingDirectoryLocations 它加載的目錄
spring整合hibernate後的DAO
spring整合hiberante後,咱們的dao只須要繼承HibernateDaoSupport類
在HibernateDaoSupport中只須要注入SessionFactory就能夠得到到HibernateTemplate,它是對hibernate操做的一個簡單封裝,可讓咱們方便使用原來hibernate的操做.
編寫service及測試
測試
事務管理
HibernateTemplate API介紹
保存操做 session.save()
修改操做 session.update()
刪除操做 session.delete()
相似於session.saveOrUpdate()根據持久化對象的狀態來判斷執行save或update
獲取操做 get() load()
Find操做 相似於session.createQuery().setParameter().list()
相似於hibernate中的QBC查詢,徹底的面向對象方案
下面這個能夠執行命名查詢
能夠在User.hbm.xml文件中定義hql或sql
Spring整合struts2框架
前期準備
建立一個addUser.jsp頁面
建立UserAction類
Struts.xml文件中配置
Spring整合struts2原理分析
1. spring整合struts2框架必須導入一個jar包
struts2-spring-plugin.jar
2. struts2框架配置文件加載順序
a. default.properties
b. struts-default.xml
c. strtus-plugin.xml
3. 在struts2框架中全部的action interceptor result全是bean,在struts2框架中默認是使用strtus2本身bean初化操做.
4. 當咱們在工程中導入struts2-spring-plugin.jar文件
就會加載這個包下的strtus-plugin.xml
這時bean的建立由spring來管理。
5. 這時在建立Action時它執行的代碼
上述代碼,在執行時,首先會從spring容器中來獲取,若是獲取不到,會buildBean
經過上述分析,spring整合struts2框架它的方式有兩種
1. spring管理action(簡單說就是在applicationContext.xml文件中來聲明action)
2. action自動裝配service
spring整合struts2框架方式一(掌握)
這種方案是基於spring管理action
1. 在applicationContext.xml文件中配置
2. 在action類中
3. 在struts.xml文件
Class的值就是bean的id值
注意:必須在web.xml文件中配置struts2框架的Filter
Spring整合struts2框架方式二(action中自動注入service)
Struts.xml文件中
Class仍是類的全名
這時就會將action類中須要的注入servcie自動注入
在default.properties中有一段配置
這時就會根據名稱進行autoWires
咱們能夠修改注入的方式
咱們在struts.xml文件中修改了注入的方式,根據type進行注入
Spring整合struts2框架總結
1. 若是在struts.xml文件中<action class=」cn.itheima.action.UserAction」>若是寫的是全類名,咱們使用action自動裝配service方案
2. 若是在struts.xml文件中<action class=」userAction」>這時,在applicationContext.xml文件中要配置<beanid=」userAction」 class=」 cn.itheima.action.UserAction」>
3. 以上操做的前提是必須導入struts2-spring-plugin.xml文件
在這個文件中它改變struts2的bean工廠
4. 默認狀況下若是採用action自動裝配service方案,這時每一次請求都會新建立一個action,而且service的裝配類型是by name
5. 若是咱們採用的是spring管理action這種方案咱們必須在<bean>聲明中添加scope=prototype」,緣由是struts2框架的action每一次請求都應該是一個新的action
關於annotation整合方式
Jar包導入
在原來的xml基礎上在多導入一個jar包
只有導入這個jar包後,咱們才能使用struts2框架的註解 @Namespace @Action
配置文件
Web.xml文件中要配置
Spring的配置文件applicationContext.xml
Struts2的配置文件 struts.xml
使用JPA註解來定義PO類
@Entity 定義實體類
@Table 定義表
@Id 主鍵
@GeneratedValue 生成主鍵策略
@Column 定義列
Spring整合hibernate
Dao編寫
如何在dao中獲得HibernateTemplate對象,原來是在applicationContext.xml文件中經過配置方案注入了一個SessionFactory對象,UserDao的父類HibernateDaoSupport,會幫助咱們根據SessionFactory來獲得HibernateTemplate
Service編寫
問題:service須要事務管理,怎樣處理?
Action編寫
使用@Controller @Scope
以上註解的做用是由spring管理action,它是一個多例的。
問題:如何完成struts2框架的流程?
基於annotation的ssh整合總結
在ssh的annotation整合時,必需要多導入的一個包
對於dao,service,action咱們使用
@Repository @Service @Controller來完成bean註冊。
在dao中咱們使用如下方案將SessionFactory注入,在dao中就可使用HibernateTemplate
在service及action中使用@Autowire來注入dao及service
必定要在applicationContext.xml文件中開啓註解掃描
對於PO類咱們使用JPA的註解 @Entiry @Table @Id @GeneratedValue @Column
要在applicationContext.xml文件中配置SessionFactory時來肯定掃描包
對於Struts2框架,咱們須要@Namespace @Action @ParentPakcage @Result來定義struts2流程
要求action類必須是在action actions struts struts2這樣的包中才會掃描struts2相關注解
SSH整合延遲加載問題解決
1. 修改UserDao中的findById
2. 添加一個user.jsp頁面
3. 在UserAction中處理user_findById請求
以上程序在執行後,報錯
解決no session問題:
1. 不使用延遲加載
2. 手動將延遲加載初始化 Hibernate.initialize(延遲對象)
3. 使用spring提供的一個OpenSessionInViewFilter來解決
基本的原理就是將session的關閉操做不在service層完成,而是在web層才關閉session.
注意:openSessionInViewFilter必定要在Struts2 Filter前配置.