国产xxxx99真实实拍_久久不雅视频_高清韩国a级特黄毛片_嗯老师别我我受不了了小说

資訊專欄INFORMATION COLUMN

Spring【DAO模塊】就是這么簡(jiǎn)單

NSFish / 1154人閱讀

摘要:連接對(duì)象執(zhí)行命令對(duì)象執(zhí)行關(guān)閉值得注意的是,對(duì)數(shù)據(jù)庫(kù)連接池是有很好的支持的。給我們提供了事務(wù)的管理器類,事務(wù)管理器類又分為兩種,因?yàn)榈氖聞?wù)和的事務(wù)是不一樣的。

前言

上一篇Spring博文主要講解了如何使用Spring來(lái)實(shí)現(xiàn)AOP編程,本博文主要講解Spring的DAO模塊對(duì)JDBC的支持,以及Spring對(duì)事務(wù)的控制...

對(duì)于JDBC而言,我們肯定不會(huì)陌生,我們在初學(xué)的時(shí)候肯定寫(xiě)過(guò)非常非常多的JDBC模板代碼!

回顧對(duì)模版代碼優(yōu)化過(guò)程

我們來(lái)回憶一下我們?cè)趺磳?duì)模板代碼進(jìn)行優(yōu)化的!

首先來(lái)看一下我們原生的JDBC:需要手動(dòng)去數(shù)據(jù)庫(kù)的驅(qū)動(dòng)從而拿到對(duì)應(yīng)的連接..

        try {
            String sql = "insert into t_dept(deptName) values("test");";
            Connection con = null;
            Statement stmt = null;
            Class.forName("com.mysql.jdbc.Driver");
            // 連接對(duì)象
            con = DriverManager.getConnection("jdbc:mysql:///hib_demo", "root", "root");
            // 執(zhí)行命令對(duì)象
            stmt =  con.createStatement();
            // 執(zhí)行
            stmt.execute(sql);
            
            // 關(guān)閉
            stmt.close();
            con.close();
        } catch (Exception e) {
            e.printStackTrace();
        }

因?yàn)镴DBC是面向接口編程的,因此數(shù)據(jù)庫(kù)的驅(qū)動(dòng)都是由數(shù)據(jù)庫(kù)的廠商給做到好了,我們只要加載對(duì)應(yīng)的數(shù)據(jù)庫(kù)驅(qū)動(dòng),便可以獲取對(duì)應(yīng)的數(shù)據(jù)庫(kù)連接....因此,我們寫(xiě)了一個(gè)工具類,專門來(lái)獲取與數(shù)據(jù)庫(kù)的連接(Connection),當(dāng)然啦,為了更加靈活,我們的工具類是讀取配置文件的方式來(lái)做的。


    /*
    * 連接數(shù)據(jù)庫(kù)的driver,url,username,password通過(guò)配置文件來(lái)配置,可以增加靈活性
    * 當(dāng)我們需要切換數(shù)據(jù)庫(kù)的時(shí)候,只需要在配置文件中改以上的信息即可
    *
    * */

    private static String  driver = null;
    private static String  url = null;
    private static String  username = null;
    private static String password = null;

    static {
        try {

            //獲取配置文件的讀入流
            InputStream inputStream = UtilsDemo.class.getClassLoader().getResourceAsStream("db.properties");

            Properties properties = new Properties();
            properties.load(inputStream);

            //獲取配置文件的信息
            driver = properties.getProperty("driver");
            url = properties.getProperty("url");
            username = properties.getProperty("username");
            password = properties.getProperty("password");

            //加載驅(qū)動(dòng)類
            Class.forName(driver);


        } catch (IOException e) {
            e.printStackTrace();
        } catch (ClassNotFoundException e) {
            e.printStackTrace();
        }

    }

    public static Connection getConnection() throws SQLException {
        return DriverManager.getConnection(url,username,password);
    }
    public static void release(Connection connection, Statement statement, ResultSet resultSet) {

        if (resultSet != null) {
            try {
                resultSet.close();
            } catch (SQLException e) {
                e.printStackTrace();
            }
        }
        if (statement != null) {
            try {
                statement.close();
            } catch (SQLException e) {
                e.printStackTrace();
            }
        }
        if (connection != null) {
            try {
                connection.close();
            } catch (SQLException e) {
                e.printStackTrace();
            }
        }
    }

經(jīng)過(guò)上面一層的封裝,我們可以在使用的地方直接使用工具類來(lái)得到與數(shù)據(jù)庫(kù)的連接...那么比原來(lái)就方便很多了!但是呢,每次還是需要使用Connection去創(chuàng)建一個(gè)Statement對(duì)象。并且無(wú)論是什么方法,其實(shí)就是SQL語(yǔ)句和傳遞進(jìn)來(lái)的參數(shù)不同!

于是,我們就自定義了一個(gè)JDBC的工具類,詳情可以看http://blog.csdn.net/hon_3y/article/details/53760782#t6

我們自定義的工具類其實(shí)就是以DbUtils組件為模板來(lái)寫(xiě)的,因此我們?cè)陂_(kāi)發(fā)的時(shí)候就一直使用DbUtils組件了。

使用Spring的JDBC

上面已經(jīng)回顧了一下以前我們的JDBC開(kāi)發(fā)了,那么看看Spring對(duì)JDBC又是怎么優(yōu)化的

首先,想要使用Spring的JDBC模塊,就必須引入兩個(gè)jar文件:

引入jar文件

spring-jdbc-3.2.5.RELEASE.jar

spring-tx-3.2.5.RELEASE.jar

首先還是看一下我們?cè)腏DBC代碼:獲取Connection是可以抽取出來(lái)的,直接使用dataSource來(lái)得到Connection就行了。

    public void save() {
        try {
            String sql = "insert into t_dept(deptName) values("test");";
            Connection con = null;
            Statement stmt = null;
            Class.forName("com.mysql.jdbc.Driver");
            // 連接對(duì)象
            con = DriverManager.getConnection("jdbc:mysql:///hib_demo", "root", "root");
            // 執(zhí)行命令對(duì)象
            stmt =  con.createStatement();
            // 執(zhí)行
            stmt.execute(sql);
            
            // 關(guān)閉
            stmt.close();
            con.close();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

值得注意的是,JDBC對(duì)C3P0數(shù)據(jù)庫(kù)連接池是有很好的支持的。因此我們直接可以使用Spring的依賴注入,在配置文件中配置dataSource就行了


    
        
        
        
        
        
        
        
        
    
    // IOC容器注入
    private DataSource dataSource;
    public void setDataSource(DataSource dataSource) {
        this.dataSource = dataSource;
    }

    
    public void save() {
        try {
            String sql = "insert into t_dept(deptName) values("test");";
            Connection con = null;
            Statement stmt = null;
            // 連接對(duì)象
            con = dataSource.getConnection();
            // 執(zhí)行命令對(duì)象
            stmt =  con.createStatement();
            // 執(zhí)行
            stmt.execute(sql);
            
            // 關(guān)閉
            stmt.close();
            con.close();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

Spring來(lái)提供了JdbcTemplate這么一個(gè)類給我們使用!它封裝了DataSource,也就是說(shuō)我們可以在Dao中使用JdbcTemplate就行了。

創(chuàng)建dataSource,創(chuàng)建jdbcTemplate對(duì)象




    
        
        
        
        
        
        
        
        
    

    
    

    
    
        
    
    

userDao

package bb;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.stereotype.Component;

/**
 * Created by ozc on 2017/5/10.
 */


@Component
public class UserDao implements IUser {

    //使用Spring的自動(dòng)裝配
    @Autowired
    private JdbcTemplate template;

    @Override
    public void save() {
        String sql = "insert into user(name,password) values("zhoggucheng","123")";
        template.update(sql);
    }

}

測(cè)試:

    @Test
    public void test33() {
        ApplicationContext ac = new ClassPathXmlApplicationContext("bb/bean.xml");

        UserDao userDao = (UserDao) ac.getBean("userDao");
        userDao.save();
    }

JdbcTemplate查詢

我們要是使用JdbcTemplate查詢會(huì)發(fā)現(xiàn)有很多重載了query()方法

一般地,如果我們使用queryForMap(),那么只能封裝一行的數(shù)據(jù),如果封裝多行的數(shù)據(jù)、那么就會(huì)報(bào)錯(cuò)!并且,Spring是不知道我們想把一行數(shù)據(jù)封裝成是什么樣的,因此返回值是Map集合...我們得到Map集合的話還需要我們自己去轉(zhuǎn)換成自己需要的類型。

我們一般使用下面這個(gè)方法:

我們可以實(shí)現(xiàn)RowMapper,告訴Spriing我們將每行記錄封裝成怎么樣的。

    public void query(String id) {
        String sql = "select * from USER where password=?";

        List query = template.query(sql, new RowMapper() {


            //將每行記錄封裝成User對(duì)象
            @Override
            public User mapRow(ResultSet resultSet, int i) throws SQLException {
                User user = new User();
                user.setName(resultSet.getString("name"));
                user.setPassword(resultSet.getString("password"));

                return user;
            }

        },id);


        System.out.println(query);
    }

當(dāng)然了,一般我們都是將每行記錄封裝成一個(gè)JavaBean對(duì)象的,因此直接實(shí)現(xiàn)RowMapper,在使用的時(shí)候創(chuàng)建就好了

    class MyResult implements RowMapper{

        // 如何封裝一行記錄
        @Override
        public Dept mapRow(ResultSet rs, int index) throws SQLException {
            Dept dept = new Dept();
            dept.setDeptId(rs.getInt("deptId"));
            dept.setDeptName(rs.getString("deptName"));
            return dept;
        }
        
    }
事務(wù)控制概述

下面主要講解Spring的事務(wù)控制,如何使用Spring來(lái)對(duì)程序進(jìn)行事務(wù)控制....

Spring的事務(wù)控制是屬于Spring Dao模塊的。

一般地,我們事務(wù)控制都是在service層做的。。為什么是在service層而不是在dao層呢??有沒(méi)有這樣的疑問(wèn)...

service層是業(yè)務(wù)邏輯層,service的方法一旦執(zhí)行成功,那么說(shuō)明該功能沒(méi)有出錯(cuò)

一個(gè)service方法可能要調(diào)用dao層的多個(gè)方法...如果在dao層做事務(wù)控制的話,一個(gè)dao方法出錯(cuò)了,僅僅把事務(wù)回滾到當(dāng)前dao的功能,這樣是不合適的[因?yàn)槲覀兊臉I(yè)務(wù)由多個(gè)dao方法組成]。如果沒(méi)有出錯(cuò),調(diào)用完dao方法就commit了事務(wù),這也是不合適的[導(dǎo)致太多的commit操作]。

事務(wù)控制分為兩種:

編程式事務(wù)控制

聲明式事務(wù)控制

編程式事務(wù)控制

自己手動(dòng)控制事務(wù),就叫做編程式事務(wù)控制。

Jdbc代碼:

Conn.setAutoCommite(false); // 設(shè)置手動(dòng)控制事務(wù)

Hibernate代碼:

Session.beginTransaction(); // 開(kāi)啟一個(gè)事務(wù)

【細(xì)粒度的事務(wù)控制: 可以對(duì)指定的方法、指定的方法的某幾行添加事務(wù)控制】

(比較靈活,但開(kāi)發(fā)起來(lái)比較繁瑣: 每次都要開(kāi)啟、提交、回滾.)

聲明式事務(wù)控制

Spring提供對(duì)事務(wù)的控制管理就叫做聲明式事務(wù)控制

Spring提供了對(duì)事務(wù)控制的實(shí)現(xiàn)。

如果用戶想要使用Spring的事務(wù)控制,只需要配置就行了

當(dāng)不用Spring事務(wù)的時(shí)候,直接移除就行了。

Spring的事務(wù)控制是基于AOP實(shí)現(xiàn)的。因此它的耦合度是非常低的。

【粗粒度的事務(wù)控制: 只能給整個(gè)方法應(yīng)用事務(wù),不可以對(duì)方法的某幾行應(yīng)用事務(wù)。

(因?yàn)閍op攔截的是方法。)

Spring給我們提供了事務(wù)的管理器類,事務(wù)管理器類又分為兩種,因?yàn)?strong>JDBC的事務(wù)和Hibernate的事務(wù)是不一樣的。

Spring聲明式事務(wù)管理器類:

Jdbc技術(shù):DataSourceTransactionManager

Hibernate技術(shù):HibernateTransactionManager

聲明式事務(wù)控制

我們基于Spring的JDBC來(lái)做例子吧

引入相關(guān)jar包

AOP相關(guān)的jar包【因?yàn)镾pring的聲明式事務(wù)控制是基于AOP的,那么就需要引入AOP的jar包?!?/strong>

引入tx名稱空間

引入AOP名稱空間

引入jdbcjar包【jdbc.jar包和tx.jar包】

搭建配置環(huán)境

編寫(xiě)一個(gè)接口

public interface IUser {
    void save();
}

UserDao實(shí)現(xiàn)類,使用JdbcTemplate對(duì)數(shù)據(jù)庫(kù)進(jìn)行操作!

@Repository
public class UserDao implements IUser {

    //使用Spring的自動(dòng)裝配
    @Autowired
    private JdbcTemplate template;

    @Override
    public void save() {
        String sql = "insert into user(name,password) values("zhong","222")";
        template.update(sql);
    }

}

userService

@Service
public class UserService {

    @Autowired
    private UserDao userDao;
    public void save() {

        userDao.save();
    }
}

bean.xml配置:配置數(shù)據(jù)庫(kù)連接池、jdbcTemplate對(duì)象、掃描注解





    
    
        
        
        
        
        
        
        
        
    

    
    

    
    
        
    

前面搭建環(huán)境的的時(shí)候,是沒(méi)有任何的事務(wù)控制的。

也就是說(shuō),當(dāng)我在service中調(diào)用兩次userDao.save(),即時(shí)在中途中有異常拋出,還是可以在數(shù)據(jù)庫(kù)插入一條記錄的。

Service代碼:

@Service
public class UserService {

    @Autowired
    private UserDao userDao;
    public void save() {

        userDao.save();

        int i = 1 / 0;
        userDao.save();
    }
}

測(cè)試代碼:

public class Test2 {

    @Test
    public void test33() {
        ApplicationContext ac = new ClassPathXmlApplicationContext("bb/bean.xml");

        UserService userService = (UserService) ac.getBean("userService");
        userService.save();
    }
}

XML方式實(shí)現(xiàn)聲明式事務(wù)控制

首先,我們要配置事務(wù)的管理器類:因?yàn)镴DBC和Hibernate的事務(wù)控制是不同的。

    
    

        
        
    

再而,配置事務(wù)管理器類如何管理事務(wù)

    
    
        
        
        
            
            
        
    
    

最后,配置攔截哪些方法,

    
    
        
        
    

配置完成之后,service中的方法都應(yīng)該被Spring的聲明式事務(wù)控制了。因此我們?cè)俅螠y(cè)試一下:

    @Test
    public void test33() {
        ApplicationContext ac = new ClassPathXmlApplicationContext("bb/bean.xml");

        UserService userService = (UserService) ac.getBean("userService");
        userService.save();
    }

使用注解的方法實(shí)現(xiàn)事務(wù)控制

當(dāng)然了,有的人可能覺(jué)得到XML文件上配置太多東西了。Spring也提供了使用注解的方式來(lái)實(shí)現(xiàn)對(duì)事務(wù)控制

第一步和XML的是一樣的,必須配置事務(wù)管理器類:

    
    

        
        
    
    

第二步:開(kāi)啟以注解的方式來(lái)實(shí)現(xiàn)事務(wù)控制

    
    
    

最后,想要控制哪個(gè)方法事務(wù),在其前面添加@Transactional這個(gè)注解就行了!如果想要控制整個(gè)類的事務(wù),那么在類上面添加就行了。

    @Transactional
    public void save() {

        userDao.save();

        int i = 1 / 0;
        userDao.save();
    }

事務(wù)屬性

其實(shí)我們在XML配置管理器類如何管理事務(wù),就是在指定事務(wù)的屬性!我們來(lái)看一下事務(wù)的屬性有什么:

對(duì)于事務(wù)的隔離級(jí)別,不清楚的朋友可參考我之前的博文:http://blog.csdn.net/hon_3y/article/details/53760782

事務(wù)傳播行為:

看了上面的事務(wù)屬性,沒(méi)有接觸過(guò)的其實(shí)就這么一個(gè):propagation = Propagation.REQUIRED事務(wù)的傳播行為。

事務(wù)傳播行為的屬性有以下這么多個(gè),常用的就只有兩個(gè):

Propagation.REQUIRED【如果當(dāng)前方法已經(jīng)有事務(wù)了,加入當(dāng)前方法事務(wù)

Propagation.REQUIRED_NEW【如果當(dāng)前方法有事務(wù)了,當(dāng)前方法事務(wù)會(huì)掛起。始終開(kāi)啟一個(gè)新的事務(wù),直到新的事務(wù)執(zhí)行完、當(dāng)前方法的事務(wù)才開(kāi)始】

當(dāng)事務(wù)傳播行為是Propagation.REQUIRED

現(xiàn)在有一個(gè)日志類,它的事務(wù)傳播行為是Propagation.REQUIRED

    Class Log{
            Propagation.REQUIRED  
            insertLog();  
    }

現(xiàn)在,我要在保存之前記錄日志

    Propagation.REQUIRED
    Void  saveDept(){
        insertLog();   
        saveDept();
    }

saveDept()本身就存在著一個(gè)事務(wù),當(dāng)調(diào)用insertLog()的時(shí)候,insertLog()的事務(wù)會(huì)加入到saveDept()事務(wù)中

也就是說(shuō),saveDept()方法內(nèi)始終是一個(gè)事務(wù),如果在途中出現(xiàn)了異常,那么insertLog()的數(shù)據(jù)是會(huì)被回滾的【因?yàn)樵谕皇聞?wù)內(nèi)】

    Void  saveDept(){
        insertLog();    // 加入當(dāng)前事務(wù)
        .. 異常, 會(huì)回滾
        saveDept();
    }
當(dāng)事務(wù)傳播行為是Propagation.REQUIRED_NEW

現(xiàn)在有一個(gè)日志類,它的事務(wù)傳播行為是Propagation.REQUIRED_NEW

    Class Log{
            Propagation.REQUIRED  
            insertLog();  
    }

現(xiàn)在,我要在保存之前記錄日志

    Propagation.REQUIRED
    Void  saveDept(){
        insertLog();   
        saveDept();
    }

當(dāng)執(zhí)行到saveDept()中的insertLog()方法時(shí),insertLog()方法發(fā)現(xiàn) saveDept()已經(jīng)存在事務(wù)了,insertLog()會(huì)獨(dú)自新開(kāi)一個(gè)事務(wù),直到事務(wù)關(guān)閉之后,再執(zhí)行下面的方法

如果在中途中拋出了異常,insertLog()是不會(huì)回滾的,因?yàn)樗氖聞?wù)是自己的,已經(jīng)提交了

    Void  saveDept(){
        insertLog();    // 始終開(kāi)啟事務(wù)
        .. 異常, 日志不會(huì)回滾
        saveDept();
    }
如果文章有錯(cuò)的地方歡迎指正,大家互相交流。習(xí)慣在微信看技術(shù)文章,想要獲取更多的Java資源的同學(xué),可以關(guān)注微信公眾號(hào):Java3y

文章版權(quán)歸作者所有,未經(jīng)允許請(qǐng)勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。

轉(zhuǎn)載請(qǐng)注明本文地址:http://specialneedsforspecialkids.com/yun/68806.html

相關(guān)文章

  • Spring【依賴注入】就是這么簡(jiǎn)單

    摘要:前言在的第二篇中主要講解了模塊的使用容器創(chuàng)建對(duì)象的問(wèn)題,模塊主要是解決對(duì)象的創(chuàng)建和對(duì)象之間的依賴關(guān)系,因此本博文主要講解如何使用容器來(lái)解決對(duì)象之間的依賴關(guān)系回顧以前對(duì)象依賴我們來(lái)看一下我們以前關(guān)于對(duì)象依賴,是怎么的歷程直接對(duì)象在最開(kāi)始,我們 前言 在Spring的第二篇中主要講解了Spring Core模塊的使用IOC容器創(chuàng)建對(duì)象的問(wèn)題,Spring Core模塊主要是解決對(duì)象的創(chuàng)建和...

    Lyux 評(píng)論0 收藏0
  • 納稅服務(wù)系統(tǒng)【總結(jié)】

    摘要:要是使用到日歷的話,我們想到使用這個(gè)日歷類上面僅僅是我個(gè)人總結(jié)的要點(diǎn),如果有錯(cuò)誤的地方還請(qǐng)大家給我指正。 納稅服務(wù)系統(tǒng)總結(jié) 納稅服務(wù)系統(tǒng)是我第一個(gè)做得比較大的項(xiàng)目(不同于javaWeb小項(xiàng)目),該項(xiàng)目系統(tǒng)來(lái)源于傳智Java32期,十天的視頻課程(想要視頻的同學(xué)關(guān)注我的公眾號(hào)就可以直接獲取了) 我跟著練習(xí)一步一步完成需求,才發(fā)覺(jué)原來(lái)Java是這樣用來(lái)做網(wǎng)站的,Java有那么多的類庫(kù),頁(yè)面...

    ispring 評(píng)論0 收藏0
  • Spring入門看這一篇就夠了

    摘要:甲乙交易活動(dòng)不需要雙方見(jiàn)面,避免了雙方的互不信任造成交易失敗的問(wèn)題。這就是的核心思想。統(tǒng)一配置,便于修改。帶參數(shù)的構(gòu)造函數(shù)創(chuàng)建對(duì)象首先,就要提供帶參數(shù)的構(gòu)造函數(shù)接下來(lái),關(guān)鍵是怎么配置文件了。 前言 前面已經(jīng)學(xué)習(xí)了Struts2和Hibernate框架了。接下來(lái)學(xué)習(xí)的是Spring框架...本博文主要是引入Spring框架... Spring介紹 Spring誕生: 創(chuàng)建Spring的...

    superw 評(píng)論0 收藏0
  • Spring【AOP模塊就是這么簡(jiǎn)單

    摘要:可以通過(guò)切入點(diǎn)表達(dá)式,指定攔截哪些類的哪些方法給指定的類在運(yùn)行的時(shí)候植入切面類代碼。 前言 到目前為止,已經(jīng)簡(jiǎn)單學(xué)習(xí)了Spring的Core模塊、....于是我們就開(kāi)啟了Spring的AOP模塊了...在講解AOP模塊之前,首先我們來(lái)講解一下cglib代理、以及怎么手動(dòng)實(shí)現(xiàn)AOP編程 cglib代理 在講解cglib之前,首先我們來(lái)回顧一下靜態(tài)代理和動(dòng)態(tài)代理....我之前就寫(xiě)過(guò)了靜態(tài)代...

    whjin 評(píng)論0 收藏0
  • Springboot簡(jiǎn)單應(yīng)用

    摘要:第一步首先創(chuàng)建一個(gè)簡(jiǎn)單的工程,這里也可以用上的模版。第二步建立需要用到的數(shù)據(jù)庫(kù)表,及數(shù)據(jù)。第三步建立項(xiàng)目的各個(gè)模塊,實(shí)現(xiàn)相應(yīng)的邏輯。模塊就是一個(gè)簡(jiǎn)單的調(diào)用方法,代碼如下模塊代碼如下參數(shù)為必填項(xiàng)至此,整個(gè)項(xiàng)目創(chuàng)建完成,然后就是啟動(dòng)測(cè)試了。 一直用SpringMVC+Spring開(kāi)發(fā),雖然用了這么久,但對(duì)里面繁瑣的配置還是很頭疼,這種情況改用Springboot,無(wú)疑是個(gè)很好的選擇。廢話不...

    zhunjiee 評(píng)論0 收藏0

發(fā)表評(píng)論

0條評(píng)論

最新活動(dòng)
閱讀需要支付1元查看
<