栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > Java

Spring整合JDBC实现转账业务-动态代理模式

Java 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

Spring整合JDBC实现转账业务-动态代理模式

1,概述

        在前面的文章中,我使用了JDBC实现转账业务的事务管理及Spring整合JDBC实现转账业务

在这里我们我们对其Spring整合JDBC实现转账业务进行优化更新,使其业务层完全脱离我们的事务书写,我们采用的时候动态代理模式

2.项目结构

 3, 项目所需要的依赖
    
        
            org.springframework
            spring-context
            5.2.3.RELEASE
        
        
            org.springframework
            spring-test
            5.2.3.RELEASE
        
        
            junit
            junit
            4.12
            test
        
        
            mysql
            mysql-connector-java
            5.1.47
        
        
            com.alibaba
            druid
            1.1.10
        
        
            org.springframework
            spring-jdbc
            5.2.3.RELEASE
        
        
            commons-dbutils
            commons-dbutils
            1.7
        
        
            com.mchange
            c3p0
            0.9.5.5
        
    

4, 实体类Account

package com.offcn.bean;

import java.io.Serializable;

public class Account implements Serializable {
    private Integer id;
    private String name;
    private double money;

    public Integer getId() {
        return id;
    }

    public void setId(Integer id) {
        this.id = id;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public double getMoney() {
        return money;
    }

    public void setMoney(double money) {
        this.money = money;
    }

    @Override
    public String toString() {
        return "Account{" +
                "id=" + id +
                ", name='" + name + ''' +
                ", money=" + money +
                '}';
    }
}
5, 创建工具类

        工具类依次创建首先是ConnectionUtils--->TxManager--->BeanFactory

        1) ConnectionUtils

package com.offcn.utils;

import javax.sql.DataSource;
import java.sql.Connection;
import java.sql.SQLException;

public class ConnectionUtils {
    //这里我们获取Connection对象,对其进行操作
    private DataSource dataSource;
    // 创建ThreadLocal对象
    ThreadLocal tl = new ThreadLocal();

    public void setDataSource(DataSource dataSource) {
        this.dataSource = dataSource;
    }

    public Connection getConnection() {
        // 去获取Connection对象,看是否存在
        Connection connection = tl.get();
        try {
            // 如果不存在,则获取一个新的Connection对象
            if (connection == null) {
                connection = dataSource.getConnection();
                //将其存入ThreadLocal中
                tl.set(connection);
            }
        } catch (SQLException e) {
            e.printStackTrace();
        }
        return connection;
    }

}

        2) TxManager

package com.offcn.utils;

public class TxManager {
    // 通过我们的ConnectionUtils获取我们的Connection对象
    private ConnectionUtils connectionUtils;

    public ConnectionUtils getConnectionUtils() {
        return connectionUtils;
    }

    public void setConnectionUtils(ConnectionUtils connectionUtils) {
        this.connectionUtils = connectionUtils;
    }

    // 开启事务
    public void beginTransaction() {
        try {
            //System.out.println(connectionUtils.getConnection());
            // 获取我们的连接对象
            connectionUtils.getConnection().setAutoCommit(false);
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
    // 提交事务
    public void commit() {
        try {
            // 提交事务
            connectionUtils.getConnection().commit();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
    // 回滚事务
    public void rollback() {
        try {
            connectionUtils.getConnection().rollback();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
    // 释放资源
    public void close() throws Exception {
        connectionUtils.getConnection().close();
    }
}

        3) BeanFactory

        在这里我们要说下,我们的BeanFactory就是通过我们的动态代理,来帮我们去完成AccountService层,所需要做的事情,在此期间,我们就可以把我们的事务添加进来,在执行我们service事务层代码的时候,直接对其进行事务的控制,这样好处我们可以看到其真实的事务层的代码,我们就可以不用考虑其事务,做到了分层解耦开发

package com.offcn.utils;

import com.offcn.service.AccountService;

import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;


public class BeanFactory {
    // 我们要对我们的AccountService进行事务管理
    private AccountService accountService;
    // 创建一个事务管理器
    private TxManager txManager;

    public AccountService getProxyInstance() {
        return (AccountService) Proxy.newProxyInstance(accountService.getClass().getClassLoader(), accountService.getClass().getInterfaces(), new InvocationHandler() {
            @Override
            public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
                Object obj = null;
                try {
                    txManager.beginTransaction();
                    obj = method.invoke(accountService, args);// 执行目标方法
                    txManager.commit();
                } catch (Exception e) {
                    e.printStackTrace();
                    // 回滚
                    txManager.rollback();
                } finally {
                    txManager.close();
                }
                return obj;
            }
        });

    }

    public AccountService getAccountService() {
        return accountService;
    }

    public void setAccountService(AccountService accountService) {
        this.accountService = accountService;
    }

    public TxManager getTxManager() {
        return txManager;
    }

    public void setTxManager(TxManager txManager) {
        this.txManager = txManager;
    }
}
6, 所需资源

        1) applicationContext.xml




    
    
        
        
        
        
    

    
    
        
    
    
        
        
    

    
        
    
    
        
    
    
        
        
    
    

        2) dbConfig.properties

jdbc.driver=com.mysql.jdbc.Driver
jdbc.url=jdbc:mysql://localhost:3306/mybatis002
jdbc.username=root
jdbc.password=root
7, 数据访问层

        1) AccountDao

import com.offcn.bean.Account;

public interface AccountDao {
    public Account findByName(String name);
    public void update(Account account);
}

        2) AccountDaoImpl

package com.offcn.dao.impl;

import com.offcn.bean.Account;
import com.offcn.dao.AccountDao;
import com.offcn.utils.ConnectionUtils;
import org.apache.commons.dbutils.QueryRunner;
import org.apache.commons.dbutils.handlers.BeanHandler;

import java.sql.Connection;
import java.sql.SQLException;

public class AccountDaoImpl implements AccountDao {
    private ConnectionUtils connectionUtils;
    private QueryRunner queryRunner;

    @Override
    public Account findByName(String name) {
        Connection connection = connectionUtils.getConnection();
        Account account = null;
        try {
            account = queryRunner.query(connection, "select * from account where name = ?", new BeanHandler(Account.class), name);
        } catch (SQLException e) {
            e.printStackTrace();
        }
        return account;
    }

    @Override
    public void update(Account account) {
        Connection connection = connectionUtils.getConnection();
        try {
            queryRunner.update(connection, "update account set money = ? where name = ?", account.getMoney(), account.getName());
        } catch (SQLException e) {
            e.printStackTrace();
        }
    }

    public ConnectionUtils getConnectionUtils() {
        return connectionUtils;
    }

    public void setConnectionUtils(ConnectionUtils connectionUtils) {
        this.connectionUtils = connectionUtils;
    }

    public QueryRunner getQueryRunner() {
        return queryRunner;
    }

    public void setQueryRunner(QueryRunner queryRunner) {
        this.queryRunner = queryRunner;
    }
}

 

8, 业务处理层

        1) AccountService

package com.offcn.service;

public interface AccountService {
    
    public void transfer(String outName, String inName, double money);
}

        2) AccountServiceImpl

        就是我们再上面使用了BeanFactory这个工具类,我们发现我们再业务层中的代码,在编写的过程中,可以不用考虑其事务的影响

package com.offcn.service.impl;

import com.offcn.bean.Account;
import com.offcn.dao.AccountDao;
import com.offcn.service.AccountService;

public class AccountServiceImpl implements AccountService {
    private AccountDao accountDao;

    @Override
    public void transfer(String outName, String inName, double money) {
        Account byName = accountDao.findByName(outName);// 转出的用户
        Account byName1 = accountDao.findByName(inName);// 转入的用户

        // 更改用户余额
        byName.setMoney(byName.getMoney() - money);
        byName1.setMoney(byName1.getMoney() + money);

        accountDao.update(byName); // 更新转出的用户
         //int i = 1 / 0;
        accountDao.update(byName1); // 更新转入的用户
    }

    public AccountDao getAccountDao() {
        return accountDao;
    }

    public void setAccountDao(AccountDao accountDao) {
        this.accountDao = accountDao;
    }
}

9,测试

package com.offcn.mytest;

import com.offcn.service.AccountService;
import com.offcn.utils.BeanFactory;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;

@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration("classpath:applicationContext.xml")
public class MyTest01 {

    @Autowired
    @Qualifier("proxy")
    private AccountService accountService;


    @Test
    public void test01() {
        accountService.transfer("aaa", "bbb", 100D);

    }
}

转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/945204.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号