Spring-1-(簡介及HelloWord)

一:Spring簡介java

  Spring 框架宗旨:不從新發明技術,讓原有技術使用起來更加方便.mysql

  Spring核心功能:程序員

    1.AOP:面向切面編程web

    2.Ioc/Di:控制反轉/依賴注入spring

    3.聲明式事務sql

  Spring框架RunTime(運行時環境)數據庫

    

    Spring中的容器(Container):express

       Spring 框架中重要概念編程

         容器(Container): Spring 看成一個大容器.數組

         BeanFactory 接口.老版本. 

         ApplicationContext 接口,新版本,是 BeanFactory 子接口

      BeanFactory 的功能在 ApplicationContext 中都有

    Spring拆分jar包:

      Spring3 開始把 Spring 框架的功能拆分紅多個 jar. 7.1 Spring2 及之前就一個 jar(優勢:可根據不一樣的需求導入不一樣的jar,而不需將Spring中的60多個jar都加載進去)

    解析框架:

      test: spring 提供測試功能

      Core Container:核心容器.Spring 啓動最基本的條件. (將spring跑起來至少有這些東西)

        Beans : Spring 負責建立類對象並管理對象

        

        Core: 核心類(類庫)

        

        Context: 上下文參數.獲取外部資源或這管理註解等

        

        SpEl: expression.jar

        

      AOP: 實現 aop 功能須要依賴

      Aspects: 切面 AOP 依賴的包

      Data Access/Integration : spring 封裝數據訪問層相關內容

        JDBC : Spring 對 JDBC 封裝後的代碼. 5.5.2 ORM: 封裝了持久層框架的代碼.例如 Hibernate

        Transactions:對應 spring-tx.jar,聲明式事務使用. 5.6 WEB:須要 spring 完成 web 相關功能時須要. 5.6.1 例如:由 tomcat 加載 spring 配置文件時須要有 spring-web包

   注意:Spring運行並不依賴與Web容器(tomcat等等),jar包依舊能夠運行,可是spring提供了web的jar包,因此也可使用web容器來運行

二:核心功能

   一)IoC

  1 中文名稱:控制反轉

  2.英文名稱:(Inversion of Control)

  3.IoC 是什麼?
    3.1 IoC 完成的事情原先由程序員主動經過 new 實例化對象事情,轉交給 Spring 負責.

    3.2 控制反轉中控制的是誰:

      控制類的對象.

    3.3 控制反轉中反轉指的是:

      原來有程序員管理的類的對象轉交給 Spring 負責管理.

    3.4 IoC 最大的做用:解耦.

      3.4.1 程序員不須要管理對象.解除了對象管理和程序員之間的耦合.

//以往咱們須要本身手動的建立對象,並進行使用
 User user = new User();
 String address = user.getAddress();
 

//如今咱們只須要將spring容器中的對象拿出來使用就行了       
 @Autowired
 User user;
 String address1 = user.getAddress();

  IoC容器有兩種:
    BeanFactory:
      簡介:
        基礎類型的IoC容器,由org.springframework.beans.factory.BeanFactory接口定義,並提供了完整的IoC服務支持;
        BeanFactory是一個管理Bean的工程,負責初始化各類Bean並調用他們的生命週期方法。
      實現:
        org.springframework.beans.factory.xml.XmlBeanFactory,根據xml配置文件中的定義來裝配Bean

     ApplicationContext:(也就是咱們配置的ApplicationContext.xml)
      簡介:
        是BeanFactory的子接口,也被稱爲應用上下文,由org.springframework.context.ApplicationContext提供,
        他提供BeanFactory全部的功能,而且增強了BeanFactory的功能,體如今Context包使用分層和有繼承關係的上下文類:
          1.MessageSource,提供對i18n消息的訪問;
          2.資源訪問,例如URL和文件
          3.事件傳遞給實現了ApplicationListener接口的Bean;
          4.載入多個有集成關係的上下文類,使每個上下文類都專一於一個特定的層次,

        幾乎全部的場合都是用ApplicationContext而非底層的BeanFactory
        建立ApplicationContext接口實例(建立IoC容器):
          方式一:(從類路徑中的xml文件載入上下文定義信息)
            ApplicatonContext applicationcontext=new ClassPathXmlApplicationContext("applicationContext.xml")
          方式二:(從文件路徑中的xml文件載入上下文定義信息)
            ApplicatonContext applicationcontext=new FileSystemXmlApplicationContext("F:\\workspace\\applicationContext.xml")

  這裏建立的是一個web工程可是使用的main方法執行也能夠放進tomcat中運行)

  所依賴的jar包(核心包以外還要加一個日誌包commons-logging.jar):

  

<bean class="com.xpl.model.User" id="user">
public class Text {
    public static void main(String[] args) {
//        將applicationContext加載進去,初始化spring容器
//        spring初始化的時候就會將容器中的全部組件初始化,這個時候對象已將建立
//        他是經過類的無參構造進行初始化的
        ClassPathXmlApplicationContext cxt = new ClassPathXmlApplicationContext("applicationContext.xml");
//        獲取spring容器中的組件
//        方式有三種:
//            方式一:經過id獲取,可是要強轉
//        User user = (User) cxt.getBean("user");
//            方式二:經過id和類獲取
        User user = cxt.getBean("user4", User.class);
        System.out.println(user);
//            方式三:經過class類獲取,有個缺陷,加入spring中使用這個類建立了多個實例,就會衝突,找不到
        User bean = cxt.getBean(User.class);
        String[] beanDefinitionNames = cxt.getBeanDefinitionNames();
//        能夠看到spring容器中全部的組件名字
        for(int i=0;i<beanDefinitionNames.length;i++){
            System.out.println(beanDefinitionNames[i]);
        }
    }
}  

  Spring建立實例的三種方式:

  1).構造器建立

    1.1.無參構造器(默認)

    1.2.有參構造

          具體使用參照下邊的代碼註釋

          

          

  2).實例工廠

  3).靜態工廠.

<!--經過構造器注入bean-->
    <bean class="com.xpl.model.User" id="user">
        <constructor-arg index="0" value="張三"/>
        <constructor-arg index="1" value="27"/>
    </bean>
    <!--結果-->
    <!--有參構造String name, int age-->
    <!--User{name='張三', age=27}-->
    <bean class="com.xpl.model.User" id="user1">
        <constructor-arg name="name" value="李四"/>
        <constructor-arg name="age" value="27"/>
    </bean>
    <!--結果-->
    <!--有參構造int age,String name-->
    <!--User{name='李四', age=27}-->
    <!--發現:走的是後邊(有兩個有參構造,第二個有參構造)-->
    <!--是由於經過有參構造,name屬性賦值時候,執行參數相同的構造器的最後一個)-->
    <!--這個時候就須要使用參數中的index或者type來精準定位-->
    <!--注意不須要全都寫,配合使用只要能定位到某個構造器就能夠-->
    <bean class="com.xpl.model.User" id="user2">
        <constructor-arg name="name" index="0" value="王五"/>
        <constructor-arg name="age" value="27"/>
    </bean>
    <!--結果-->
    <!--有參構造String name, int age-->
    <!--User{name='王五', age=27}-->

<!--實例工廠建立--> <!--實例工廠須要實例化,因此先注入進來--> <bean class="com.xpl.model.UserFactory" id="userFactory"/> <!--指定實例工廠是哪個,在指定工廠方法是哪個--> <bean factory-bean="userFactory" factory-method="creatPeople" id="user3"/>

<!--靜態工廠建立--> <bean class="com.xpl.model.UserStaticFactory" factory-method="creatPeople" id="user4"/>

  對象屬性賦值:

   1).構造方法注入(上邊已經演示過了參考)

   2).經過set方法注入

       基本數據類型:

       複雜數據類型:

        

<bean class="com.xpl.model.User" id="user">
        <!--基本數據類型-->
        <property name="name" value="趙六"/>
        <!--數組-->
        <property name="arr">
            <array>
                <value>1</value>
                <value>2</value>
                <value>3</value>
            </array>
        </property>
        <!--若是list中只有一個值也能夠這樣寫-->
        <!--<property name="arr" value="1"/>-->
        <!--引用數據類型,引用上邊的cat-->
        <property name="cat" ref="cat"/>
        <!--list-->
        <property name="list">
            <list>
                <value>5</value>
                <value>6</value>
                <value>7</value>
            </list>
        </property>
        <!--若是list中只有一個值也能夠這樣寫-->
        <!--<property name="list" value="1"/>-->
        <!--map-->
        <property name="map">
            <map>
                <entry key="1" value="2"/>
                <entry key="2" value="2"/>
                <entry key="3" value="2"/>
            </map>
        </property>
        <property name="set">
            <set>
                <value>1</value>
                <value>2</value>
                <value>3</value>
            </set>
        </property>
        <property name="properties">
            <props>
                <prop key="1">1</prop>
                <prop key="2">2</prop>
                <prop key="3">3</prop>
            </props>
        </property>
   </bean>

  二)DI

  1. DI:中文名稱:依賴注入

    2. 英文名稱((Dependency Injection)

    3. DI 是什麼?

      3.1 DI 和 IoC 是同樣的

      3.2 當一個類(A)中須要依賴另外一個類的對象時,把 B 賦值給 A 的過程就叫作依賴注入.(注入:就是給spring容器中的bean賦值的過程;當Bean中的某個屬性是另外一個Bean時,把這個Bean以屬性的方式注

      入進去就是依賴注入,廣義上描述他就是Aop,狹義上描述就是將一個Bean做爲了另一個Bean的屬性)

//首先有一個bean,這個Bean就是下邊Bean的一個屬性   
  <bean class="com.xpl.model.User" id="user">     
     <property name="cat" ref="cat"/>
   </bean>    
    <bean class="com.xpl.model.Cat" id="cat">
        //這個Bean中的屬性是一個Bean
       <property name="name" value="小白貓"/>
   </bean>
public class User {
      private Cat cat;
      private Properties properties;
  }

  public class Cat {
      private String name;
  }

  三)AOP  

    1.AOP:中文名稱面向切面編程

    2.英文名稱:(Aspect Oriented Programming)

    3.正常程序執行流程都是縱向執行流程

      3.1 又叫面向切面編程,在原有縱向執行流程中添加橫切面

      3.2 不須要修改原有程序代碼

        3.2.1 高擴展性

        3.2.2 原有功能至關於釋放了部分邏輯.讓職責更加明確.

    概念:(原理:動態代理)

    在程序原有縱向執行流程中,針對某一個或某一些方法添加通知,造成橫切面過程就叫作面向切面編程.

    主要體如今事務處理,日誌管理,權限控制,異常處理等方面,提升代碼的可維護性。

 

    原有功能: 鏈接點, pointcut(在某個方法前織入,這個方法就叫鏈接點)

    增長的部分叫作通知(加強Advice)

      前置通知: 在切點以前執行的功能. before advice

      後置通知: 在切點以後執行的功能,after advice

      異常通知.throws advice

      環繞通知:

    全部切點+通知叫作切面.

    織入: 把切面嵌入到原有功能的過程叫作織入

    重要:spring聲明式事務是基於aop實現的,事務通常是用在service上的,有了事務service中一旦出現異常就會回滾,

         因此不建議在service中使用try-catch,由於使用try-catch以後aop就捕獲不到異常,聲明式事務就失效了

  java原生動態代理:

public interface Calculate {  
    public int add(int a,int b);
    public int min(int a,int b);
}

public class Calculateimpl implements Calculate {
    @Override
    public int add(int a, int b) {
        return a+b;
    }

    @Override
    public int min(int a, int b) {
        return a-b;
    }
}

public class ProxyFactory {
    //建立代理對象
    public Object createMyCalculate(Object obj){
        //Proxy是java反射中的一個類  obj.getClass().getClassLoader()獲取類加載器  實現的接口
        return Proxy.newProxyInstance(obj.getClass().getClassLoader(), obj.getClass().getInterfaces(), new InvocationHandler() {
            @Override
            //代理的那個對象(傳入的) 要處理的方法  傳入的參數
            public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
                System.out.println("star");
                //調用方法並執行
                Object invoke = method.invoke(obj, args);
                System.out.println("end");
                return invoke;
            }
        });
    }
}
public class Text {
public static void main(String[] args) {
ProxyFactory proxyFactory=new ProxyFactory();
Calculateimpl calculateimpl=new Calculateimpl();
Calculate calculate=(Calculate)proxyFactory.createMyCalculate(calculateimpl));
calculate.add(1,3);
}
}

  Spring中aop實現:

  XML方式配置:

/**
 * 定義advice
 */
public class Advice {
    public void before(){
        System.out.println("前");
    }
    public void mythrow(Exception e){
//        還須要配置xml才能夠打印出異常信息
        System.out.println("異常"+e.getMessage());
    }
    public void  after(){
        System.out.println("後");
    }
    public void aftering(){
        System.out.println("aftering");
    }
    public Object around(ProceedingJoinPoint proceedingJoinPoint) throws Throwable {
        System.out.println("執行環繞通知");
        System.out.println("環繞-前置");
//        返回值
        Object proceed = proceedingJoinPoint.proceed();
        System.out.println(proceed);
        System.out.println("環繞-後置");
        return proceed;
    }
}
public class Demo {
    public int min(int i,int j){
        return i+j;
    }
}
public class Text {
    public static void main(String[] args) {

        ClassPathXmlApplicationContext cxt = new ClassPathXmlApplicationContext("applicationContext.xml");
        Demo demo = cxt.getBean("demo", Demo.class);
        demo.min(1,5);
    }
}
<!--將要被加強的對象注入進來-->
<bean class="com.xpl.test.Demo" id="demo"/>
<!--將advice注入進來-->
<bean class="com.xpl.advice.Advice" id="advice"/>
<aop:config>
    <!--定義切點:就是要在哪一個方法上加強-->
    <aop:pointcut id="min" expression="execution(int com.xpl.test.Demo.min(int ,int ))"/>
    <!--定義切面:切點+加強-->

    <!--引用的就是上邊注入進來的加強Bean-->
    <aop:aspect ref="advice">
        
        <!--這幾個加強是有順序的特別是異常aftering和after-->
        <!--通知類型    加強方法名(加強類中的)    被加強的方法(上邊定義的切點)-->
        
        <!--after和after-returning的區別:-->
                <!--after不管是否拋出異常都會執行-->
                <!--after-returning必須正確執行纔會執行-->
        <aop:after method="after" pointcut-ref="min"/>
        <aop:after-returning method="aftering" pointcut-ref="min"/>
        <aop:after method="before" pointcut-ref="min"/>
        <!--必須和加強類中異常方法中參數的異常名相同-->
        <aop:after-throwing method="mythrow" pointcut-ref="min" throwing="e"/>
       
        <aop:around method="around" pointcut-ref="min"/>
    </aop:aspect>
</aop:config>

    通配符*

    在定義切點的時候可使用*通配符精肯定位切點

    他支持一級包名

<aop:pointcut id="min" expression="execution(int com.xpl.test.Demo.min(int ,int ))"/>

表示com包下的全部包中的全部方法
<aop:pointcut id="min" expression="execution(* com.*.*.*.*(* ,* ))"/>

   四)自動注入

  前提:Spring全局配置文件中

   看代碼理解:

    兩個類A和B須要交給Spring管理

    B中有個屬性是對象A

    非自動注入:本身寫本身的property給屬性賦值,或使用ref

    自動注入:在bean標籤上使用autowire屬性

   原理:Byname去判斷我須要注入的屬性名在spring容器中是否存在id名稱同樣的,存在就直接注入給他,

      Bytype是去找class

      Constructor:須要實體類中有有參構造方法,而且參數名稱要和xml中的name同樣

public class B {
    private String name;
    private A a;

public class A {
    private String name;

 

沒有自動注入
<
bean class="com.xpl.model.A" id="a"> <property name="name" value="aaa"/> </bean>--> <bean class="com.xpl.model.B" id="b"> <property name="name" value="bbbbb"/> <property name="A" ref="a"/> </bean>

自動注入 <bean class="com.xpl.model.A" id="a"> <property name="name" value="aaa"/> </bean> <bean class="com.xpl.model.B" id="b" autowire="byName"> <property name="name" value="bbbbb"/> </bean>

 

 

    也能夠配置爲全局的

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xsi:schemaLocation="http://www.springframework.org/schema/beans
       http://www.springframework.org/schema/beans/spring-beans.xsd" default-autowire="byName">

 

五:加載配置文件

  注意:經過配置文件健在內容的時候要注意使用下邊高亮部分

  緣由是:實例化前後順序形成的,以避免在實例化完成以後加載配置文件就加載不進去了

db.driver=com.mysql.jdbc.Driver
db.username=root
db.password=root
db.url=jdbc:mysql:///test?useUnicode=true&characterEncoding=UTF-8

 

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns:context="http://www.springframework.org/schema/context"
       xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd">

    <context:property-placeholder location="classpath:db.properties"/>
    <!--配置數據源-->
    <bean class="org.springframework.jdbc.datasource.DriverManagerDataSource" id="dataSource">
        <property name="driverClassName" value="${db.driver}"/>
        <property name="username" value="${db.username}"/>
        <property name="password" value="${db.password}"/>
        <property name="url" value="${db.url}"/>
    </bean>
    <!--建立sqlSessionFactory-->
    <bean class="org.mybatis.spring.SqlSessionFactoryBean" id="factory">
        <!--建立sqlSession須要有數據庫鏈接,na那麼就引用上邊的數據源-->
        <property name="dataSource" ref="dataSource"/>
        <property name="typeAliasesPackage" value="com.xpl.model"/>
    </bean>
  //掃描配置mapper.xml文件
   <bean class="org.mybatis.spring.SqlSessionFactoryBean" id="sqlSessionFactory">      <property name="dataSource" ref="dataSource"/>      <property name="typeAliasesPackage" value="com.xpl.model"/>      <property name="mapperLocations">       <list>         <value>classpath*:com/xpl/mapper/*.xml</value>       </list>     </property>    </bean> <!--掃描器,加載mapper接口--> <bean class="org.mybatis.spring.mapper.MapperScannerConfigurer">       //配置這一句就能夠mapper接口和mapper.xml不寫在一個文件夾了 <property name="basePackage" value="com.xpl.mapper"/> <property name="sqlSessionFactoryBeanName" value="factory"/> <!--<property name="sqlSessionFactory" ref="factory"/>--> </bean> </beans>

 

六:從配置文件中取值

people.name=xupeilei
兩種方式,將bean交給Spring容器!!!這是關鍵,要想去spring容器中的全局的值,就必定要把這個Bean交給Spring管理!!!!!
方式一:直接配置進去

<
bean class="com.xpl.model.People" id="people"/>

方式二:經過包掃描
<context:component-scan base-package="com.xpl.model"/>

 

public class People {
  name這個屬性名和取值時的name名沒有必然關係,能夠不同 @Value(
"${people.name}") private String name;

 

七:Scope屬性

  默認單例

八:聲明式事務

  1.編程式事務:

    1.1 由程序員編程事務控制代碼. 1.2 OpenSessionInView 編程式事務

  2.聲明式事務:

    2.1 事務控制代碼已經由 spring 寫好.程序員只須要聲明出哪些方法須要進行事務控制和如何進行事務控制.

  3.聲明式事務都是針對於 Service 類下方法的.

  4.事務管理器基於通知(advice)的.

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns:context="http://www.springframework.org/schema/context" xmlns:tx="http://www.springframework.org/schema/tx"
       xmlns:aop="http://www.springframework.org/schema/aop"
       xsi:schemaLocation="http://www.springframework.org/schema/beans 
    http://www.springframework.org/schema/beans/spring-beans.xsd
    http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd
    http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx.xsd
    http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd"
>                  <!--配置數據庫連接--> <!--引入數據庫鏈接信息--> <context:property-placeholder location="classpath:db.properties"/> <!--配置數據庫裏鏈接池--> <bean class="com.alibaba.druid.pool.DruidDataSource" id="dataSource"> <property name="url" value="${db.url}"/> <property name="username" value="${db.username}"/> <property name="password" value="${db.password}"/> </bean>
                   <!--配置mybatis--> <!--配置mapper--> <bean class="org.mybatis.spring.SqlSessionFactoryBean" id="sqlSessionFactory"> <property name="dataSource" ref="dataSource"/> <property name="typeAliasesPackage" value="com.xpl.model"/> <property name="mapperLocations"> <list> <value>classpath*:com/xpl/mapper/*.xml</value> </list> </property> </bean> <!--自動獲取getXXX(mapper.xlass)--> <bean class="org.mybatis.spring.mapper.MapperScannerConfigurer"> <!--獲取那個接口 value就是上邊配的SqlSessionFactoryBean--> <property name="sqlSessionFactoryBeanName" value="sqlSessionFactory"/> <!--接口所在的文件夾 這裏配置完了就不須要將接口和mapper文件放一個文件夾了--> <property name="basePackage" value="com.xpl.mappering"/> </bean>                   <!--配置事務--> <bean class="org.springframework.jdbc.datasource.DataSourceTransactionManager" id="dataSourceTransactionManager"> <property name="dataSource" ref="dataSource"/> </bean> <tx:advice id="txAdvice" transaction-manager="dataSourceTransactionManager"> <tx:attributes> <tx:method name="add*"/> <tx:method name="upd*"/> <tx:method name="del*"/> <tx:method name="sel*"/>
       <tx:method name="*" read-only="true"/>  </tx:attributes> </tx:advice> <aop:config> <aop:pointcut id="pc1" expression="execution(* com.xpl.service.*.*(..))"/> <aop:advisor advice-ref="txAdvice" pointcut-ref="pc1"/> </aop:config> </beans>

 

九:事務傳播行爲

<tx:method name="add*" read-only="" propagation=""/>

 

  readonly=」boolean」 是不是隻讀事務.

     1 若是爲 true,告訴數據庫此事務爲只讀事務.數據化優化,會對性能有必定提高,因此只要是查詢的方法,建議使用此數據.

     2 若是爲 false(默認值),事務須要提交的事務.建議新增,刪除,修改.

  propagation 控制事務傳播行爲.

    1當一個具備事務控制的方法被另外一個有事務控制的方法調用後,須要如何管理事務(新建事務?在事務中執行?把事務掛起?報異常?)

      REQUIRED (默認值): 若是當前有事務,就在事務中執行,若是當前沒有事務,新建一個事務.

      SUPPORTS:若是當前有事務就在事務中執行,若是當前沒有事務,就在非事務狀態下執行.

      MANDATORY:必須在事務內部執行,若是當前有事務,就在事務中執行,若是沒有事務,報錯.

      REQUIRES_NEW:必須在事務中執行,若是當前沒有事務,新建事務,若是當前有事務,把當前事務掛起.

      NOT_SUPPORTED:必須在非事務下執行,若是當前沒有事務,正常執行,若是當前有事務,把當前事務掛起.

      NEVER:必須在非事務狀態下執行,若是當前沒有事務,正常執行, 若是當前有事務,報錯.

      NESTED:必須在事務狀態下執行.若是沒有事務,新建事務,常執行,若是當前有事務,把當前事務掛起.

十:事務隔離級別 

<tx:method name="add*" isolation="DEFAULT"/>

 

    髒讀:

      一個事務(A)讀取到另外一個事務(B)中未提交的數據,另外一個事務中數據可能進行了改變,此時 A事務讀取的數據可能和數據庫中數據是不一致的,此時認爲數據是髒數據,讀取髒數據過程叫作髒讀

      解釋:A從數據庫讀出一條數據(aaa),並修改成(bbb)沒有提交只是flush到內存中,這時B讀到了內存中的數據(bbb),可是數據庫中數據依舊是(aaa),B讀到的就是髒數據

.     不可重複讀:

      主要針對的是某行數據.(或行中某列)

      主要針對的操做是修改操做.

      兩次讀取在同一個事務內

      當事務 A 第一次讀取事務後,事務 B 對事務 A 讀取的淑君進行修改,事務 A 中再次讀取的數據和以前讀取的數據不一致,過程不可重複讀. 

      解釋:張三盤點了倉庫現存50噸大豆,而後他準備賣給特朗普,這時他老婆在他不知道的狀況賣給了金三胖,張三合同籤回來準備發貨發現大豆沒有了

    幻讀:

      主要針對的操做是新增或刪除

      兩次事務的結果.

      事務 A 按照特定條件查詢出結果,事務 B 新增了一條符合條件的數據.事務 A 中查詢的數據和數據庫中的數據不一致的,事務 A 好像出現了幻覺,這種狀況稱爲幻讀. 

  isolation=」」 事務隔離級別在多線程或併發訪問下如何保證訪問到的數據具備完整性的.

    DEFAULT:

      默認值,由底層數據庫自動判斷應該使用什麼隔離界別

    READ_UNCOMMITTED: 能夠讀取未提交數據,可能出現髒讀,不重複讀,幻讀.

       效率最高.

    READ_COMMITTED:只能讀取其餘事務已提交數據.能夠防止髒讀,可能出現不可重複讀和幻讀.

    REPEATABLE_READ: 讀取的數據被添加鎖,防止其餘事務修改此數據,能夠防止不可重複讀.髒讀,可能出現幻讀.

    SERIALIZABLE: 排隊操做,對整個表添加鎖.一個事務在操做數據時,另外一個事務等待事務操做完成後才能操做這個表.

      最安全的

      效率最低的.

十一:事務回滾

<tx:method name="add*"rollback-for="" no-rollback-for=""/>

 

   rollback-for=」異常類型全限定路徑」

      當出現什麼異常時須要進行回滾

      建議:給定該屬性值.

        手動拋異常必定要給該屬性值.

   no-rollback-for=」」

      當出現什麼異常時不滾回事務.

十二:註解

1. @Component 建立類對象,至關於配置<bean/>
2. @Service 與@Component 功能相同.

  2.1 寫在 ServiceImpl 類上.

3. @Repository 與@Component 功能相同.

  3.1 寫在數據訪問層類上.

4. @Controller 與@Component 功能相同.

  4.1 寫在控制器類上.

5. @Resource(不須要寫對象的 get/set)(其實至關於對自動注入的補充:由於使用註解的方式auto就不生效了,可是咱們還要在類中放入屬性,就將這個類放進去)
  5.1 java 中的註解
  5.2 默認按照 byName 注入,若是沒有名稱對象,按照 byType 注入
    5.2.1 建議把對象名稱和 spring 容器中對象名相同
6. @Autowired(不須要寫對象的 get/set)
  6.1 spring 的註解
  6.2 默認按照 byType 注入.

7. @Value() 獲取 properties 文件中內容
8. @Pointcut() 定義切點
9. @Aspect() 定義切面類
10. @Before() 前置通知
11. @After 後置通知
12. @AfterReturning 後置通知,必須切點正確執行
13. @AfterThrowing 異常通知
14. @Arround 環繞通知

十三:java配置類

  能夠不使用applicationContext.xml來配置屬性而是使用一個java類來替代

  @Configuration

  @Componentscan:默認掃描當前包及子包的子包。。

  @Componentscan(basePackages=「com.xpl.model」)設置掃描哪個包

  @Bean

十四:多數據源

相關文章
相關標籤/搜索