实际上,这不是一个问题,但实际上我需要您的意见…我把他的帖子放在这里是因为我知道您一直都很活跃,所以请不要认为这是一个坏问题并与我分享您的意见。
我已经使用Java动态代理来集中化在独立模式下使用的JPA代码,这是动态代理代码:
package com.forat.service;
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;
import java.util.logging.Level;
import java.util.logging.Logger;
import javax.persistence.EntityManager;
import javax.persistence.EntityManagerFactory;
import javax.persistence.EntityTransaction;
import javax.persistence.Persistence;
import com.forat.service.exceptions.DAOException;
/**
* Example of usage :
* <pre>
* OnlineFromService onfromService =
* (OnlineFromService) DAOProxy.newInstance(new OnlineFormServiceImpl());
* try {
* Student s = new Student();
* s.setName("Mohammed");
* s.setNationalNumber("123456");
* onfromService.addStudent(s);
* }catch (Exception ex) {
* System.out.println(ex.getMessage());
* }
*</pre>
* @author mohammed hewedy
*
*/
public class DAOProxy implements InvocationHandler{
private Object object;
private Logger logger = Logger.getLogger(this.getClass().getSimpleName());
private DAOProxy(Object object) {
this.object = object;
}
public static Object newInstance(Object object) {
return Proxy.newProxyInstance(object.getClass().getClassLoader(),
object.getClass().getInterfaces(), new DAOProxy(object));
}
@Override
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
EntityManagerFactory emf = null;
EntityManager em = null;
EntityTransaction et = null;
Object result = null;
try {
emf = Persistence.createEntityManagerFactory(Constants.UNIT_NAME);
em = emf.createEntityManager();;
Method entityManagerSetter = object.getClass().
getDeclaredMethod(Constants.ENTITY_MANAGER_SETTER_METHOD, EntityManager.class);
entityManagerSetter.invoke(object, em);
et = em.getTransaction();
et.begin();
result = method.invoke(object, args);
et.commit();
return result;
}catch (Exception ex) {
et.rollback();
Throwable cause = ex.getCause();
logger.log(Level.SEVERE, cause.getMessage());
if (cause instanceof DAOException)
throw new DAOException(cause.getMessage(), cause);
else
throw new RuntimeException(cause.getMessage(), cause);
}finally {
em.close();
emf.close();
}
}
}
这是包含更多信息的链接(http://m-hewedy.blogspot.com/2010/04/using-dynamic-proxies-to-
centralize-jpa.html
)
所以,请给我您的意见。
谢谢。
因此,您已经将事务划分逻辑封装在一个地方,并使用动态代理通过事务管理来增强现有服务并减少样板代码,对吗?
听起来对我来说还算不错。实际上,当我们谈到
声明式事务划分
时,诸如Spring或EJB之类的容器所做的事情非常相似。在实现方面,您可以使用动态代理或字节码检测来实现,甚至可以使用AspectJ。我曾经为一个很小的测试框架做过非常相似的事情。这是关于它的博客文章。
我看到的棘手的部分是:
1) 仅回滚 。根据JPA规范,实体事务可以标记为“
仅回滚
”。这样的交易永远无法提交。因此,我觉得您应该在这两行之间进行检查:
result = method.invoke(object, args);
et.commit();
2) 重新进入
。大多数具有声明式事务的系统都实现一种语义,即只有在没有事务处于活动状态时才启动事务(请参阅此EJB批注列表中的“ Required” )。看来您应该isActive
按照逻辑检查一下。
3) 异常处理 。注意动态代理中的异常传播。代理应该对客户端尽可能透明。如果DAOException
DAO
以外的其他异常泄漏出去,则代理会将其转换为RuntimeException
。对我来说听起来并不理想。同样不要混淆异常,因为invoke
失败了,并且调用包装了异常,我认为您应该照原样重新抛出:
catch ( InvocationTargetException e )
{
Throwable nested = e.getTargetException();
throw nested;
}
结论
:在这种情况下使用动态代理的想法对我来说是可以的。但是我怀疑您需要仔细检查代码中的一些内容(我不记得JPA规范的所有细节以及动态代理的异常处理,但是有些棘手的情况)。这种代码可以隐藏细微的错误,因此值得花些时间使其防弹。
本文向大家介绍浅谈Java代理(jdk静态代理、动态代理和cglib动态代理),包括了浅谈Java代理(jdk静态代理、动态代理和cglib动态代理)的使用技巧和注意事项,需要的朋友参考一下 一、代理是Java常用的设计模式,代理类通过调用被代理类的相关方法,并对相关方法进行增强。加入一些非业务性代码,比如事务、日志、报警发邮件等操作。 二、jdk静态代理 1、业务接口 2、业务实现类 3、代理类
本文向大家介绍Java静态代理和动态代理总结,包括了Java静态代理和动态代理总结的使用技巧和注意事项,需要的朋友参考一下 静态代理 第一种实现(基于接口): 1》接口 2》目标类,至少实现一个接口 3》代理类(与目标类实现相同接口,从而保证功能一致) 3》测试 第二种实现(基于目标类): 1>目标类 2>代理类(通过继承目标类,保证功能一致) 3>测试 动态代理 动态代理的代理类是在程序运行期间
本文向大家介绍Java动态代理静态代理实例分析,包括了Java动态代理静态代理实例分析的使用技巧和注意事项,需要的朋友参考一下 代理模式:为其他对象提供一种代理以控制某个对象的访问。用在:在某些情况下,一个客户不想或者不能直接访问另一个对象,而代理对象可以在客户端和目标对象之前起到中介的作用,代理对象还可以完成它附加的操作。 例子:就像房东、租客、中介的关系。中介(代理对象)为房东(真实对象)出租
Proxy 动态代理是 jfinal AOP 的底层实现机制。jfinal 4.0 版本新增了 com.jfinal.proxy 模块用于消除对 cglib/asm 的依赖来实现动态代理。 proxy 模块需要运行在 JDK 环境之下,如果需要运行在 JRE 之下,可以添加如下配置来支持: public void configConstant(Constants me) { // 4.6 之
是的,我见过类似的问题,但没有一个答案能真正引导我找到解决方案。我没有在任何地方使用这个线程,同样的代码在另一个jhipster应用程序中也可以使用,所以我不明白为什么这个提升转换会导致Hibernate问题。 例外: JPA地产: 编辑-这解决了我的问题:
本文向大家介绍java中动态代理的实现,包括了java中动态代理的实现的使用技巧和注意事项,需要的朋友参考一下 动态代理的实现 使用的模式:代理模式。 代理模式的作用是:为其他对象提供一种代理以控制对这个对象的访问。类似租房的中介。 两种动态代理: (1)jdk动态代理,jdk动态代理是由Java内部的反射机制来实现的,目标类基于统一的接口(InvocationHandler) (2)cglib动