2011-01-16 44 views
2

创建我有一个POJO类与@Transactional春天开始一个事务由新

public class Pojo { 

    @Transactional 
    public void doInTransaction() { 
     ... 
    } 
} 

Spring声明式事务管理注释的方法目的是基于AOP的,但我没有与任何经验。我的问题是: 是否有可能在单独调用(new Pojo).doInTransaction()时,Spring将启动一个事务。

回答

3

Spring声明式事务管理 基于APO但我不 有那方面的经验。

我建议开始使用它,您将获得使用AOP使用交易通知的体验。一个好的起点是here

是否有可能调用 (新POJO)时.doInTransaction单独(), 春天将开始交易。

不,你不能指望Spring知道你手动调用的bean。但是,这听起来像是你想要避免声明式事务管理和编程式事务管理。有一种方法可以通过使用Transaction Template来实现。那是你在找什么?

0

Spring通过Annotation处理事务的方式正如您所说的那样使用AOP。 的AOP位使用动态代理实现(见doc

所以为了做到这一点,你会通过Spring容器需要检索您的类的实例(POJO这里),因为,使其工作,将春通过Pojo返回一个动态代理服务器,该服务器将自动包含任何带有交易管理代码的带注释的方法。

如果你只是做一个

Pojo p = new Pojo(); 
p.doInTransaction(); 

春天没有任何这方面发挥作用,你的方法调用不会在事务内。

,所以你需要做的就是这样的事情

ApplicationContext springContext = ...; 
Pojo p = (Pojo) springContext.getBean("your.pojo.id"); 
p.doInTransaction(); 

注:这是一个例子,你应该更喜欢的,而不是从上下文

手动检索你的bean这样依赖注入,并且使用正确配置的Spring Context,Spring应该了解您的类以扫描事务性注释并自动将您的bean包装为注释感知的动态代理实例。从你的观点来看,这并没有改变任何东西,你仍然会将你的对象投射到你自己的类,但是如果你试图打印出你的春天上下文Pojo bean的类名,你会得到一些代理$。 ..而不是你原来的班级名称。

看一看这个链接反正:link text

1

这是有点可能,但以一种麻烦的方式:您必须使用AutowireCapableBeanFactory机制。

这里是事务类为例

public interface FooBar{ 
    void fooIze(Object foo); 
} 

public class FooBarImpl implements FooBar{ 
    @Transactional 
    @Override 
    public void fooIze(final Object foo){ 
     // do stuff here 
    } 
} 

这里是我们如何使用它:

public class FooService implements ApplicationContextAware{ 

    private ApplicationContext applicationContext; 

    @Override 
    public void setApplicationContext(
    final ApplicationContext applicationContext){ 
     this.applicationContext = applicationContext; 
    } 

    public void serviceMethod(){ 

     //declare variable as interface, initialize to implementation 
     FooBar fooBar = new FooBarImpl(); 

     // try to use it, won't work, as it's not a proxy yet 
     Object target = new Object[0]; 
     fooBar.fooIze(target); // no transaction 

     // now let spring create the proxy and re-assign the variable 
     // to the proxy: 
     fooBar = // this is no longer an instance of FooBarImpl!!! 
      (FooBar) applicationContext 
       .getAutowireCapableBeanFactory() 
       .applyBeanPostProcessorsAfterInitialization(fooBar, 
        "someBeanName"); 
     fooBar.fooIze(fooBar); // this time it should work 

    } 

} 

这不是最好的做法。首先,它使您的应用程序高度意识到Spring Framework,并且违反了依赖注入原则。所以只有在没有其他方式的情况下才能使用它!