Spring學習筆記

本文爲博主原創,允許轉載,但請聲明原文地址:http://www.coselding.cn/blog/8/8-145.html

1、 AOP(AbstractOrientedProgramming):面向抽象編程,面向接口編程,更靈活,代碼可維護性高;
2、 IoC(Inversion of Control):控制反轉,把原來需要自己new來提供的對象改成容器來提供,通過配置文件配置,自動依賴注入,增強了程序的靈活性和可維護性,靈活裝配;
  特點:在容器創建對象的時候也把對象中的屬性根據配置文件注入了,並且可以根據配置文件直接配置對象中屬性的具體哪個實現,從而形成AOP的目的;
3、 IoC容器配置:
  <!-- 定義Dao -->
  <bean id="ud" class="com.silence.spring.dao.impl.UserDaoImpl"></bean>
  <!-- 定義UserService,自動注入userDao屬性 -->
  <bean id="userService"
     class="com.silence.spring.service.UserService">
     <property name="userDao" ref="ud"></property>
  </bean>
  注:ref屬性表示參考前面定義的bean拿來用,如果改成<bean/>標籤表示當前new一個對象用來注入。
      Id和name屬性用處完全一樣,只是name能放特殊字符(無用);
      <property/>的value屬性用來給bean的簡單屬性賦值;
4、 IoC容器中對象獲取:
  //獲取配置文件對象
  ApplicationContext context = new ClassPathXmlApplicationContext("applicationContext.xml");
  //根據id值獲取容器中相應的對象
  UserService service = (UserService) context.getBean("userService");
5、 Spring注入方式:
  A. setter注入(重要);
  B. 構造方法注入(不重要),<constructor-arg>進行裝配,可設置索引和類型進行多參數定位;
  C. 接口注入(不用);
6、 bean的生存範圍:
  <bean/>的scope屬性:常用singleton(單例)和prototype(原型)兩種設計屬性。
7、 集合裝配:
  <property/>可以有<list/><set/><map/><props/>等子標籤,用來實現集合裝配。
8、 自動裝配:
  <bean/>的autowire屬性:一般設置byName或byType,實現不用裝配<property/>就自動裝配,用的不多,特定場合使用。
9、 惰性加載:(調試程序加快啓動使用)
  <bean/>的lazy-init設置;
  <beans/>的default-lazy-init設置默認所有bean的延遲加載方案。
10、 bean的生命週期:
  <bean/>的init-method屬性和destroy-method屬性執行該bean在初始化和銷燬的時候需要執行的方法名,如果scope是prototype的話,destroy-method不會執行。
11、 註解:
  開啓spring註解支持<context:annotation-config/>
  A.@Autowired:set方法上,默認byType查找;
  B.@Qualifier:在參數上,指定查找容器中對象的name或id,定向查找,相當於<qualifier/>標籤;
  C.@Required:set方法上,初始化必須裝配,否則報錯;

以下的是JPA標準的,需要j2ee包支持:
  D.@Resource:JPA標準,set方法上,先找name再找type,value屬性設置name,和Qualifier類似,代替@Autowired;
  E.@Component:標記一個組件,代替在xml文件中的<bean/>標籤聲明,配合@Resource,value屬性指定組件key,xml文件中要寫:
   //設定要掃描@Component的包
   <context:component-scan base-package="com.silence.spring.dao.impl"/>
  F.@Repository,@Service,@Controller目前和@Component一樣;
  G.@Scope:指定bean的生存週期;
  H.@PostConstruct:指定bean初始化的方法,相當於init-method屬性;
  I.@PreDestroy:指定bean銷燬要調用的方法,相當於destroy-method屬性;
12、 AOP(Aspect-Oriented-Programming):面向切面編程
原來是程序流程一條線執行下去,現在在這條線上橫切一個切面,在該切面上的執行語句,可以爲它執行前和執行後添加其他邏輯代碼,實現對原來業務邏輯的功能拓展,比如權限攔截,日誌輸出等,好處是可以很方便的控制這些額外代碼是否執行,避免了增刪這些邏輯產生的龐大的工作量。
注:Servlet的Filter和Struts2的攔截器都是AOP編程的例子。
(1)註解實現:
   A.//設置動態代理類庫支持,註解
    <aop:aspectj-autoproxy />
   B.編寫織入切面類:例:LogInterceptor日誌攔截
   C.標註組件:@Component
   D.標註切面:@Aspect
   E.標註織入建議@Before,例如:
     "execution(public void com.UserDaoImpl.addUser(com.User))"
    表示在addUser方法執行前執行該織入方法(此註解標記的方法)
    類似還有After(finally),AfterReturning,AfterThrowing,Around
    標記字符串寫法參考spring文檔
    樣例:同一個方法註解全部使用的執行結果:
     
   好處:對一個業務邏輯劃分切面織入其他業務邏輯時,完全不需要修改任何原邏輯代碼,只需要在需要切入的方法處標記相應的註解即可。
 (2)XML實現:
   <!-- xml配置aop切面織入 -->
   <!-- 配置一個切面處理類bean -->
   <bean id="loginterceptor2" class="com.silence.spring.aop.LogInterceptor2"></bean>
   <!-- 配置切面織入代理 -->
   <aop:config>
       <!-- 配置一個全局的切面,指定好該切面的匹配條件 -->
      <aop:pointcut id="mypointcut" expression="execution(public void          com.silence.spring.dao.impl.UserDaoImpl.addUser(com.silence.spring.domain.User))"/>
      <!-- 配置切面執行策略,引用切面處理類bean -->
      <aop:aspect id="myaspect" ref="loginterceptor2">
         <!-- 引用切面,在該切面執行loginterceptor2的before方法,策略爲 aop:before-->
         <aop:before method="before" pointcut-ref="mypointcut"/>
      </aop:aspect>
    </aop:config>
 注:其他注意事項和註解一致。
13、配置properties文件
 <!-- 配置property文件支持,佔位符提取 -->
 <bean
 class="org.springframework.beans.factory.config.PropertyPlaceholderConfigurer">
  <property name="locations">
   <value>classpath:jdbc.properties</value>
  </property>
 </bean>
配置完:可以引用配置文件中的屬性
 value="$ {jdbc.driverClassName}"
14、 動態代理實現:
被代理類有實現接口:JDK自帶Proxy;
被代理類沒實現接口:CDLIB通過修改二進制碼實現動態代理;
15、 Spring配置方式選擇:
 IoC容器中bean配置:註解適用;
 AOP面向切面設計:Xml配置適用。
16、Spring常用應用:
 (1)IoC容器配置DataSource數據庫連接池,再通過在Dao處自動注入dataSource,達成配置;
 (2)
17、集成Hibernate:
 (1)初步集成:
    A.加入Hibernate的jar包和相關的支持jar
    B.Spring配置sessionFactory的bean放入IoC容器,再在需要的位置拿出使用:
  主要配置Hibernate的主配置文件信息和對象映射文件的位置(或者加了註解的實體類全名),然後生成的sessionFactory交給IoC容器管理,自動注入Dao的Bean中。
 <!-- 集成Hibernate -->
 <bean id="sessionFactory"
  class="org.springframework.orm.hibernate3.annotation.AnnotationSessionFactoryBean">
  <!-- 配置連接池 -->
  <property name="dataSource" ref="dataSource" />
  <!-- 配置註解組件類 -->
  <property name="annotatedClasses">
   <list>
    <value>com.silence.spring.domain.User</value>
   </list>
  </property>
  <!-- Hibernate主配置文件內容 -->
  <property name="hibernateProperties">
   <props>
    <prop key="hibernate.dialect">org.hibernate.dialect.MySQLDialect</prop>
    <prop key="hibernate.show_sql">true</prop>
   </props>
  </property>
 </bean>
 (2)Spring事務管理:
  A.定義Hibernate事務管理器,切面類:
 <!-- Hibernate事務管理器 -->
 <bean id="txManager"
  class="org.springframework.orm.hibernate3.HibernateTransactionManager">
  <property name="sessionFactory" ref="sessionFactory" />
 </bean>
  B.使用事務管理器:
 <!-- 使用事務管理器 -->
 <tx:annotation-driven transaction-manager="txManager"/>
  C.在需要事務管理的業務處理方法上註解@Transactional
 注:
  A. 業務處理方法用getCurrentSession(),不需要close,不需要處理事務,抓到RunTimeException會自動回滾;
  B. @Transactional意味着註解的方法在前後調用事務管理器切面類,在方法調用前後自動維護好事務操作。
  C. 事務管理多使用xml配置,註解需要爲每個方法註解。

18、 @Transactional 的屬性
 (1)propagation:事務傳播機制設置
事務傳播行爲類型 說明
PROPAGATION_REQUIRED 如果當前沒有事務,就新建一個事務,如果已經存在一個事務中,加入到這個事務中。這是 最常見的選擇。
PROPAGATION_SUPPORTS 支持當前事務,如果當前沒有事務,就以非事務方式執行。
PROPAGATION_MANDATORY 使用當前的事務,如果當前沒有事務,就拋出異常。
PROPAGATION_REQUIRES_NEW 新建事務,如果當前存在事務,把當前事務掛起。
PROPAGATION_NOT_SUPPORTED 以非事務方式執行操作,如果當前存在事務,就把當前事務掛起。
PROPAGATION_NEVER 以非事務方式執行,如果當前存在事務,則拋出異常。
PROPAGATION_NESTED 如果當前存在事務,則在嵌套事務內執行。如果當前沒有事務,則執行與 PROPAGATION_REQUIRED 類似的操作。

 (2)isolation:事務隔離級別;
 (3)readOnly:只讀,進行優化,提高性能;
 (4)rollbackFor:回滾條件,默認運行時異常
19、HibernateDaoSupport:
 功能:封裝了HibernateTemplate和sessionFactory;
 繼承這個類去寫Dao方便,但是每個Dao都要xml配置bean-
 或者繼承HibernateDaoSupport寫一個BaseDao,並寫一個設置hibernateTemplate的方法,在裏面調用super.setHibernateTemplate()方法,再在上面用註解注入hibernateTemplate實例,就會把配置好的hibernateTemplate注入到此Dao中。
注:自己用包裝設計模式寫一個BaseDao,自行維護hibernateTemplate和sessionFactory對象並進行對象注入,再去繼承這個Dao寫具體的其他實現的Dao即可實現其子類的Dao的自動注入。
20、Hibernate的Session關閉後查詢的解決方式之一:
在web.xml設置過濾器org.springframework.orm.hibernate3.support.OpenSessionInViewFilter,對所有路徑進行過濾,可以控制Session在請求前打開,頁面請求結束後才關閉,避免了Session延遲操作的關閉後查詢問題。
注:該過濾器要在struts2的過濾器之前設置,設置時過濾器的順序問題可能引發異常。
21、整合Struts:(Spring作爲Struts的插件整合到Struts,Struts自己維護Action容器)
目的:配置好讓Struts向Spring容器請求業務處理類對象,並自動注入到Struts中。
(1) 設置服務器啓動自動裝載Spring容器並實例化對象:(web.xml)
   <listener>
      <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
    <!-- 默認是去找WEB-INF下的applicationContext.xml配置文件 -->
   </listener>
(2) 設置要裝載的Spring配置文件路徑:
  <!-- 這裏設置加載的applicationContext.xml路徑 -->
 <context-param>
  <param-name>contextConfigLocation</param-name>
  <param-value>classpath:applicationContext.xml</param-value>
  <!-- <param-value>/WEB-INF/applicationContext-*.xml,classpath*:applicationContext-*.xml</param-value> -->
 </context-param>
(3) 加入struts2-spring-plugin.jar包,此時Struts的Action的產生會放入專有的Action容器並把Action中的屬性從Spring中找到相應的對象注入;
整合運行流程:
在struts-config.xml的配置文件中,配置了Struts的Action,指明瞭Action的name屬性,Struts配置的所有Action會由struts2-spring-plugin維護在一個專有的Action的容器中,以name屬性作爲檢索條件,prototype方式產生給用戶的Action副本,用戶界面也是通過Action的name找到該Action的。因此Action中不需要配置任何註解即可正常運行。
Struts的Action在產生時,Action中的屬性的set方法會自動按照名稱name從Spring容器中注入相同name的對象,沒有配置xml或者註解也會自動注入,此處若在設計時使用了重名name的bean和Action屬性有時候會出現注入錯誤的情況發生。
總結:Struts-Spring整合後會有兩個容器,Action容器和Spring的IoC容器,Action容器負責維護Action,IoC負責維護業務處理層以上的所有bean對象,當用戶發送一個請求時,通過Action的name找到一個Action,並自動從Spring容器中找到Action對象中的相應屬性名稱的對象,注入到Action的屬性上(該屬性對象必須要有set方法),完成完整的Action的初始化,使Action中有了業務處理對象,可以執行相應的業務處理。即Action中的代碼相對於整合Spring前不需要改變。
Action中的屬性對象的注入是按照name,type,constructor順序進行檢索的,在設置對象的name屬性時一定注意屬性間重名可能導致的衝突問題。
Action中的屬性對象若需要人工自定義注入,在屬性的上面@Resource即可指定。
22、整合Struts:(Spring作爲Struts的插件整合到Struts,Spring容器維護Action)
(1) 設置服務器啓動自動裝載Spring容器並實例化對象:(web.xml)
   <listener>
     <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
     <!-- 默認是去找WEB-INF下的applicationContext.xml配置文件 -->
   </listener>
(2) 設置要裝載的Spring配置文件路徑:
  <!-- 這裏設置加載的applicationContext.xml路徑 -->
  <context-param>
     <param-name>contextConfigLocation</param-name>
     <param-value>classpath:applicationContext.xml</param-value>
  <!-- <param-value>/WEB-INF/applicationContext-*.xml,classpath*:applicationContext-*.xml</param-value> -->
  </context-param>
(3) 加入struts2-spring-plugin.jar包;
(4) struts-config.xml文件中的<action>標籤的class屬性用spring中的name填寫,這樣就不會有Action容器,把Action也交給Spring容器管理;
(5) Action中要用@Component指定Action的名稱,@Scope指定prototype類型,需要注入的屬性用@Resource指定注入,這樣該Action就和普通的Spring容器中對象一樣。
執行過程:
用戶請求通過struts-config.xml找到對應的action的名稱(@Component標明),根據名稱從Spring取出,並根據註解注入action需要的業務處理對象處理請求。
23、DTO(Data Transfer Object)或VO(Value Object):比如formbean的不是和數據庫對應的實體的JavaBean,只是用來存儲暫時數據值的對象實體。
24、中文亂碼:
org.springframework.web.filter.CharacterEncodingFilter過濾器配置到web.xml並設置初始化參數encoding指定編碼集即可解決表示層的亂碼問題。
25、Spring單元測試支持:
測試原則:不破壞數據庫現場。
AbstractTtransactionalJunit4SpringContextTests
26、OpenSessionInViewInterceptor、AbstractTtransactionalJunit4SpringContextTests

本文爲博主原創,允許轉載,但請聲明原文地址:http://www.coselding.cn/blog/8/8-145.html

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章