频道直达 - 专题 - 新闻 - 技巧 - 组网 - 开发 - 安全 - web编程 - 图像 - 操作系统 - 数据库 - 教育 - 旅游 - 健康 - 时尚 - 驱动 - 软件 - 游戏 - 多媒体 - ERP - 讨论组

使用动态代理实现用AOP对数据库进行操作

来源:BlogJava 作者:LifeNote 出处:巧巧读书 2008-04-25 进入讨论组

【引自LifeNote的博客】要实现对数据库的操作,离不开数据源(DataSource)或者连接(Connection),但是通常来说对数据库的操作都应该放在DAO中,而DAO又不应该与应用服务器相关联,所以一般都使用连接(Connection)。现在我们这里就有一个问题了,怎么在拦截器中获得连接。我想可以通过两种方式获得:

在分别讨论这两种方法之前,我们需要先讨论一下在处理数据库的时候的异常的处理。我这里做了一个TransactionException继承至RuntimeException然后在拦截器里面抛出,再又应用框架处理这个异常。下面试这个类的代码:

public class TransactionException extends RuntimeException {
private Throwable superException;
private String myMessage;

public TransactionException(Throwable throwable){
super(throwable);
this.superException = throwable;
}

public TransactionException(Throwable throwable,String message){
super(message,throwable);
this.superException = throwable;
this.myMessage = message;
}

/**
* @return Returns the myMessage.
*/
public String getMessage() {
return myMessage;
}

/**
* @return Returns the superException.
*/
public Throwable getSuperException() {
return superException;
}

/**
* @param myMessage The myMessage to set.
*/
public void setMyMessage(String message) {
this.myMessage = message;
}

/**
* @param superException The superException to set.
*/
public void setSuperException(Throwable superException) {
this.superException = superException;
}

}

1)通过方法的第一个参数传进去

l    DAO
import java.sql.Connection;

public class TestDao {
public void insertA(Connection con,String a,String b,……){
…………………………………………
一系列操作
…………………………………………
}

public String queryA(Connection con,…….){
…………………………………………
一系列操作
…………………………………………
}

public void updateA(Connection con,…….){
…………………………………………
一系列操作
…………………………………………
}
}

l    拦截器
import java.sql.Connection;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;

public class TransactionInterceptor implements Interceptor {

public void before(InvokeJniInfo invInfo) {
if(isNeedTransactions(invInfo)){
Connection conn = (Connection) invInfo.getArgs()[0];
try {
conn.setAutoCommit(false);
} catch (SQLException e) {
throw new TransactionException(e);
}
}
}

public void after(InvokeJniInfo invInfo) {
if(isNeedTransactions(invInfo)){
Connection conn = (Connection) invInfo.getArgs()[0];
try {
conn.commit();
} catch (SQLException e) {
throw new TransactionException(e);
}finally{
if(conn != null){
try {
conn.close();
} catch (SQLException e) {
throw new TransactionException(e,"Close Connection is failure!");
}
}
}
}
}

public void exceptionThrow(InvokeJniInfo invInfo) {
if(isNeedTransactions(invInfo)){
Connection conn = (Connection) invInfo.getArgs()[0];
try {
conn.rollback();
} catch (SQLException e) {
throw new TransactionException(e);
}finally{
if(conn != null){
try {
conn.close();
} catch (SQLException e) {
throw new TransactionException(e,"Close Connection is failure!");
}
}
}
}
}

private List getNeedTransaction(){
List needTransactions = new ArrayList();
needTransactions.add("insert");
needTransactions.add("update");
return needTransactions;
}

private boolean isNeedTransactions(InvokeJniInfo invInfo){
String needTransaction = "";
List needTransactions = getNeedTransaction();
for(int i = 0;i             needTransaction = (String)needTransactions.get(i);
if(invInfo.getMethod().getName().startsWith(needTransaction)){
return true;
}
}
return false;
}
}

需要注意的是:getNeedTransaction就是需要进行事务处理的方法的开头,这个方法可以写成一个从配置文件里面去读,这里我就写死在里面了。只是对insert和update开头的方法进行事务控制。

2)    将Connection对象放在ThreadLocal中

l    ConnectionUtil类:

import java.sql.Connection;

public final class ConnectionUtil {
private static ThreadLocal connections = new ThreadLocal();
public static Connection getConnection(){
Connection conn = null;
conn = (Connection) connections.get();
if(conn == null){
conn = getRealConnection();
connections.set(conn);
}
return conn;
}
public static void realseConnection(Connection conn){
connections.set(null);
}
private static Connection getRealConnection() {
实现自己获取连接的代码
return null;
}
}
l    DAO类
public class TestDao {
public void insertA(String a,String b){
Connection conn = getConnection();
…………………………………………
一系列操作
…………………………………………
}
public String queryA(Connection con,…….){
Connection conn = getConnection();
…………………………………………
一系列操作
…………………………………………
}

public void updateA(Connection con,…….){
Connection conn = getConnection();
…………………………………………
一系列操作
…………………………………………
}

private Connection getConnection(){
return ConnectionUtil.getConnection();
}

}
l    拦截器
import java.sql.Connection;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;

public class TransactionInterceptor implements Interceptor {

public void before(InvokeJniInfo invInfo) {
if(isNeedTransactions(invInfo)){
Connection conn = getConnection();
try {
conn.setAutoCommit(false);
} catch (SQLException e) {
throw new TransactionException(e);
}
}
}

public void after(InvokeJniInfo invInfo) {
if(isNeedTransactions(invInfo)){
Connection conn = getConnection();
try {
conn.commit();
} catch (SQLException e) {
throw new TransactionException(e);
}finally{
if(conn != null){
try {
conn.close();
releaseConnection(conn);
} catch (SQLException e) {
throw new TransactionException(e,"Close Connection is failure!");
}
}
}
}
}

public void exceptionThrow(InvokeJniInfo invInfo) {
if(isNeedTransactions(invInfo)){
Connection conn = getConnection();
try {
conn.rollback();
} catch (SQLException e) {
throw new TransactionException(e);
}finally{
if(conn != null){
try {
conn.close();
releaseConnection(conn);
} catch (SQLException e) {
throw new TransactionException(e,"Close Connection is failure!");
}
}
}
}
}

private Connection getConnection(){
return ConnectionUtil.getConnection();
}

private void releaseConnection(Connection conn){
ConnectionUtil.releaseConnection(conn);
}
private List getNeedTransaction(){
List needTransactions = new ArrayList();
needTransactions.add("insert");
needTransactions.add("update");
return needTransactions;
}

private boolean isNeedTransactions(InvokeJniInfo invInfo){
String needTransaction = "";
List needTransactions = getNeedTransaction();
for(int i = 0;i             needTransaction = (String)needTransactions.get(i);
if(invInfo.getMethod().getName().startsWith(needTransaction)){
return true;
}
}
return false;
}
}

  

最后将这个拦截器添加到AOP拦截框架中去,InterceptorHandler类中的getIntercetors方法中添加一个:

private synchronized List getIntercetors(){
if(null == interceptors){
interceptors = new ArrayList();
……………………………………
interceptors.add(new TransactionInterceptor ());
……………………………………
}
return interceptors;
}

更多文章 更多内容请看数据库专栏数据库处理专题城域网专题专题,或进入讨论组讨论。
收藏此文】【 】【打印】【关闭
相关图文阅读
频道图文推荐
健 康 咨 询
时 尚 咨 询
巧巧读书宗旨
相关专题
讨论组问题推荐
站内各频道最新更新文档
站内最新制作专题
热门关键字导读
Photoshop教 程照片处理 照片制作 PS快捷键 抠图
计 算 机 故 障XP系统修复
艺 术 与 设 计设计 流媒体 设计欣赏 边框
计 算 机 安 全ARP
站内频道文章精选
巧巧电脑频道编辑信箱  告诉我们您想看的专题或文章