`
jinnianshilongnian
  • 浏览: 21441516 次
  • 性别: Icon_minigender_1
博客专栏
5c8dac6a-21dc-3466-8abb-057664ab39c7
跟我学spring3
浏览量:2406614
D659df3e-4ad7-3b12-8b9a-1e94abd75ac3
Spring杂谈
浏览量:2998819
43989fe4-8b6b-3109-aaec-379d27dd4090
跟开涛学SpringMVC...
浏览量:5632396
1df97887-a9e1-3328-b6da-091f51f886a1
Servlet3.1规范翻...
浏览量:257846
4f347843-a078-36c1-977f-797c7fc123fc
springmvc杂谈
浏览量:1593564
22722232-95c1-34f2-b8e1-d059493d3d98
hibernate杂谈
浏览量:249105
45b32b6f-7468-3077-be40-00a5853c9a48
跟我学Shiro
浏览量:5848536
Group-logo
跟我学Nginx+Lua开...
浏览量:698464
5041f67a-12b2-30ba-814d-b55f466529d5
亿级流量网站架构核心技术
浏览量:780943
社区版块
存档分类
最新评论

【第九章】 Spring的事务 之 9.4 声明式事务 ——跟我学spring3

阅读更多

9.4  声明式事务

9.4.1  声明式事务概述

       从上节编程式实现事务管理可以深刻体会到编程式事务的痛苦,即使通过代理配置方式也是不小的工作量。

       本节将介绍声明式事务支持,使用该方式后最大的获益是简单,事务管理不再是令人痛苦的,而且此方式属于无侵入式,对业务逻辑实现无影响。

       接下来先来看看声明式事务如何实现吧。

9.4.2  声明式实现事务管理

1、定义业务逻辑实现,此处使用ConfigUserServiceImpl和ConfigAddressServiceImpl

2、定义配置文件(chapter9/service/ applicationContext-service-declare.xml):

2.1、XML命名空间定义,定义用于事务支持的tx命名空间和AOP支持的aop命名空间:

 

java代码:
<beans xmlns="http://www.springframework.org/schema/beans"
      xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xmlns:tx="http://www.springframework.org/schema/tx"
      xmlns:aop="http://www.springframework.org/schema/aop"
      xsi:schemaLocation="
          http://www.springframework.org/schema/beans
          http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
       http://www.springframework.org/schema/tx
       http://www.springframework.org/schema/tx/spring-tx-3.0.xsd
          http://www.springframework.org/schema/aop
          http://www.springframework.org/schema/aop/spring-aop-3.0.xsd">

 

2.2、业务实现配置,非常简单,使用以前定义的非侵入式业务实现:

 

java代码:
<bean id="userService" class="cn.javass.spring.chapter9.service.impl.ConfigUserServiceImpl">
    <property name="userDao" ref="userDao"/>
    <property name="addressService" ref="addressService"/>
</bean>
<bean id="addressService" class="cn.javass.spring.chapter9.service.impl.ConfigAddressServiceImpl">
    <property name="addressDao" ref="addressDao"/>
</bean>

 

2.3、事务相关配置:

 

java代码:
<tx:advice id="txAdvice" transaction-manager="txManager">
    <tx:attributes>
        <tx:method name="save*" propagation="REQUIRED" isolation="READ_COMMITTED"/>
        <tx:method name="*" propagation="REQUIRED" isolation="READ_COMMITTED" read-only="true"/>
    </tx:attributes>
</tx:advice>

 

 

 

java代码:
<aop:config>
    <aop:pointcut id="serviceMethod" expression="execution(* cn..chapter9.service..*.*(..))"/>
    <aop:advisor pointcut-ref="serviceMethod" advice-ref="txAdvice"/>
</aop:config>
  • <tx:advice>:事务通知定义,用于指定事务属性,其中“transaction-manager”属性指定事务管理器,并通过< tx:attributes >指定具体需要拦截的方法;
  •  <tx:method name="save*">:表示将拦截以save开头的方法,被拦截的方法将应用配置的事务属性:propagation="REQUIRED"表示传播行为是Required,isolation="READ_COMMITTED"表示隔离级别是提交读;
  • <tx:method name="*">:表示将拦截其他所有方法,被拦截的方法将应用配置的事务属性:propagation="REQUIRED"表示传播行为是Required,isolation="READ_COMMITTED"表示隔离级别是提交读,read-only="true"表示事务只读;
  • <aop:config>:AOP相关配置:
  • <aop:pointcut/>:切入点定义,定义名为"serviceMethod"的aspectj切入点,切入点表达式为"execution(* cn..chapter9.service..*.*(..))"表示拦截cn包及子包下的chapter9. service包及子包下的任何类的任何方法;
  • <aop:advisor>:Advisor定义,其中切入点为serviceMethod,通知为txAdvice。

从配置中可以看出,将对cn包及子包下的chapter9. service包及子包下的任何类的任何方法应用“txAdvice”通知指定的事务属性。

 

 

3、修改测试方法并测试该配置方式是否好用:

将TransactionTest 类的testServiceTransaction测试方法拷贝一份命名为testDeclareTransaction:

并在testDeclareTransaction测试方法内将:

 

java代码:
classpath:chapter9/service/applicationContext-service.xml"

 

替换为:

 

java代码:
classpath:chapter9/service/applicationContext-service-declare.xml"

 

4、执行测试,测试正常通过,说明该方式能正常工作,当调用save方法时将匹配到事务通知中定义的“<tx:method name="save*">”中指定的事务属性,而调用countAll方法时将匹配到事务通知中定义的“<tx:method name="*">”中指定的事务属性。

 

 

声明式事务是如何实现事务管理的呢?还记不记得TransactionProxyFactoryBean实现配置式事务管理,配置式事务管理是通过代理方式实现,而声明式事务管理同样是通过AOP代理方式实现。

 

 

声明式事务通过AOP代理方式实现事务管理,利用环绕通知TransactionInterceptor实现事务的开启及关闭,而TransactionProxyFactoryBean内部也是通过该环绕通知实现的,因此可以认为是<tx:tags/>帮你定义了TransactionProxyFactoryBean,从而简化事务管理。

 

 

了解了实现方式后,接下来详细学习一下配置吧:

 

9.4.4  <tx:advice/>配置详解

       声明式事务管理通过配置<tx:advice/>来定义事务属性,配置方式如下所示:

 

java代码:
<tx:advice id="……" transaction-manager="……">
<tx:attributes>
        <tx:method name="……"
                           propagation=" REQUIRED"
                           isolation="READ_COMMITTED"
                           timeout="-1"
                           read-only="false"
                           no-rollback-for="" 
                           rollback-for=""/>
        ……
    </tx:attributes>
</tx:advice>

 

  • <tx:advice>id用于指定此通知的名字, transaction-manager用于指定事务管理器,默认的事务管理器名字为“transactionManager”;
  • <tx:method>:用于定义事务属性即相关联的方法名;

         name定义与事务属性相关联的方法名,将对匹配的方法应用定义的事务属性,可以使用“*”通配符来匹配一组或所有方法,如“save*”将匹配以save开头的方法,而“*”将匹配所有方法;

         propagation:事务传播行为定义,默认为“REQUIRED”,表示Required,其值可以通过TransactionDefinition的静态传播行为变量的“PROPAGATION_”后边部分指定,如“TransactionDefinition.PROPAGATION_REQUIRED”可以使用“REQUIRED”指定;

         isolation:事务隔离级别定义;默认为“DEFAULT”,其值可以通过TransactionDefinition的静态隔离级别变量的“ISOLATION_”后边部分指定,如“TransactionDefinition. ISOLATION_DEFAULT”可以使用“DEFAULT”指定:

         timeout事务超时时间设置,单位为秒,默认-1,表示事务超时将依赖于底层事务系统;

         read-only事务只读设置,默认为false,表示不是只读;

         rollback-for需要触发回滚的异常定义,以“,”分割,默认任何RuntimeException 将导致事务回滚,而任何Checked Exception 将不导致事务回滚;异常名字定义和TransactionProxyFactoryBean中含义一样

         no-rollback-for不被触发进行回滚的 Exception(s);以“,”分割;异常名字定义和TransactionProxyFactoryBean中含义一样;

 

记不记得在配置方式中为了解决“自我调用”而导致的不能设置正确的事务属性问题,使用“((IUserService)AopContext.currentProxy()).otherTransactionMethod()方式解决,在声明式事务要得到支持需要使用<aop:config expose-proxy="true">来开启。

 

9.4.5  多事务语义配置及最佳实践

       什么是多事务语义?说白了就是为不同的Bean配置不同的事务属性,因为我们项目中不可能就几个Bean,而可能很多,这可能需要为Bean分组,为不同组的Bean配置不同的事务语义。在Spring中,可以通过配置多切入点和多事务通知并通过不同方式组合使用即可。

 

       1、首先看下声明式事务配置的最佳实践吧:

 

 

java代码:
<tx:advice id="txAdvice" transaction-manager="txManager">
<tx:attributes>
           <tx:method name="save*" propagation="REQUIRED" />
           <tx:method name="add*" propagation="REQUIRED" />
           <tx:method name="create*" propagation="REQUIRED" />
           <tx:method name="insert*" propagation="REQUIRED" />
           <tx:method name="update*" propagation="REQUIRED" />
           <tx:method name="merge*" propagation="REQUIRED" />
           <tx:method name="del*" propagation="REQUIRED" />
           <tx:method name="remove*" propagation="REQUIRED" />
           <tx:method name="put*" propagation="REQUIRED" />
           <tx:method name="get*" propagation="SUPPORTS" read-only="true" />
           <tx:method name="count*" propagation="SUPPORTS" read-only="true" />
          <tx:method name="find*" propagation="SUPPORTS" read-only="true" />
          <tx:method name="list*" propagation="SUPPORTS" read-only="true" />
          <tx:method name="*" propagation="SUPPORTS" read-only="true" />
       </tx:attributes>
</tx:advice>
<aop:config>
       <aop:pointcut id="txPointcut" expression="execution(* cn.javass..service.*.*(..))" />
       <aop:advisor advice-ref="txAdvice" pointcut-ref="txPointcut" />
</aop:config>

该声明式事务配置可以应付常见的CRUD接口定义,并实现事务管理,我们只需修改切入点表达式来拦截我们的业务实现从而对其应用事务属性就可以了,如果还有更复杂的事务属性直接添加即可,即

如果我们有一个batchSaveOrUpdate方法需要“REQUIRES_NEW”事务传播行为,则直接添加如下配置即可:

 

 

java代码:
<tx:method name="batchSaveOrUpdate" propagation="REQUIRES_NEW" />

 

 

2、接下来看一下多事务语义配置吧,声明式事务最佳实践中已经配置了通用事务属性,因此可以针对需要其他事务属性的业务方法进行特例化配置:

 

java代码:
<tx:advice id="noTxAdvice" transaction-manager="txManager">
    <tx:attributes>
           <tx:method name="*" propagation="NEVER" />
    </tx:attributes>
</tx:advice>
<aop:config>
       <aop:pointcut id="noTxPointcut" expression="execution(* cn.javass..util.*.*())" />
       <aop:advisor advice-ref="noTxPointcut" pointcut-ref="noTxAdvice" />
</aop:config>

 

       该声明将对切入点匹配的方法所在事务应用“Never”传播行为。

 

       多事务语义配置时,切入点一定不要叠加,否则将应用两次事务属性,造成不必要的错误及麻烦。

 

9.4.6  @Transactional实现事务管理

对声明式事务管理,Spring提供基于@Transactional注解方式来实现,但需要Java 5+。

 

注解方式是最简单的事务配置方式,可以直接在Java源代码中声明事务属性,且对于每一个业务类或方法如果需要事务都必须使用此注解。

 

接下来学习一下注解事务的使用吧:

 

 

1、定义业务逻辑实现:

 

java代码:
package cn.javass.spring.chapter9.service.impl;
//省略import
public class AnnotationUserServiceImpl implements IUserService {
    private IUserDao userDao;
    private IAddressService addressService;
    public void setUserDao(IUserDao userDao) {
        this.userDao = userDao;
    }
    public void setAddressService(IAddressService addressService) {
        this.addressService = addressService;
    }
    @Transactional(propagation=Propagation.REQUIRED, isolation=Isolation.READ_COMMITTED)
    @Override
    public void save(final UserModel user) {
        userDao.save(user);
        user.getAddress().setUserId(user.getId());
        addressService.save(user.getAddress());
    }
    @Transactional(propagation=Propagation.REQUIRED, isolation=Isolation.READ_COMMITTED, readOnly=true)
    @Override
    public int countAll() {
        return userDao.countAll();
    }
}

 

 

 

2、定义配置文件(chapter9/service/ applicationContext-service-annotation.xml):

 

2.1、XML命名空间定义,定义用于事务支持的tx命名空间和AOP支持的aop命名空间:

 

java代码:
<beans xmlns="http://www.springframework.org/schema/beans"
      xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xmlns:tx="http://www.springframework.org/schema/tx"
      xmlns:aop="http://www.springframework.org/schema/aop"
      xsi:schemaLocation="
          http://www.springframework.org/schema/beans
          http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
       http://www.springframework.org/schema/tx
       http://www.springframework.org/schema/tx/spring-tx-3.0.xsd
          http://www.springframework.org/schema/aop
          http://www.springframework.org/schema/aop/spring-aop-3.0.xsd">

 

2.2、业务实现配置,非常简单,使用以前定义的非侵入式业务实现:

 

java代码:
<bean id="userService" class="cn.javass.spring.chapter9.service.impl.ConfigUserServiceImpl">
    <property name="userDao" ref="userDao"/>
    <property name="addressService" ref="addressService"/>
</bean>
<bean id="addressService" class="cn.javass.spring.chapter9.service.impl.ConfigAddressServiceImpl">
    <property name="addressDao" ref="addressDao"/>
</bean>
 

 

2.3、事务相关配置:

 

java代码:
<tx:annotation-driven transaction-manager="txManager"/> 

使用如上配置已支持声明式事务。

 

 

3、修改测试方法并测试该配置方式是否好用:

将TransactionTest 类的testServiceTransaction测试方法拷贝一份命名为testAnntationTransactionTest:

将测试代码片段:

 

java代码:
classpath:chapter9/service/applicationContext-service.xml"

 

替换为:

 

java代码:
classpath:chapter9/service/applicationContext-service-annotation.xml"

 

 

将测试代码段


java代码:
userService.save(user);

 

替换为:


java代码:
try {
    userService.save(user);
    Assert.fail();
} catch (RuntimeException e) {
}
Assert.assertEquals(0, userService.countAll());
Assert.assertEquals(0, addressService.countAll());
 

 

4、执行测试,测试正常通过,说明该方式能正常工作,因为在AnnotationAddressServiceImpl类的save方法中抛出异常,因此事务需要回滚,所以两个countAll操作都返回0。

 

9.4.7  @Transactional配置详解

       Spring提供的<tx:annotation-driven/>用于开启对注解事务管理的支持,从而能识别Bean类上的@Transactional注解元数据,其具有以下属性:

  • transaction-manager:指定事务管理器名字,默认为transactionManager,当使用其他名字时需要明确指定;
  • proxy-target-class:表示将使用的代码机制,默认false表示使用JDK代理,如果为true将使用CGLIB代理
  • order:定义事务通知顺序,默认Ordered.LOWEST_PRECEDENCE,表示将顺序决定权交给AOP来处理。

Spring使用@Transaction来指定事务属性,可以在接口、类或方法上指定,如果类和方法上都指定了@Transaction,则方法上的事务属性被优先使用,具体属性如下:

  • value:指定事务管理器名字,默认使用<tx:annotation-driven/>指定的事务管理器,用于支持多事务管理器环境;
  • propagation:指定事务传播行为,默认为Required,使用Propagation.REQUIRED指定;
  • isolation:指定事务隔离级别,默认为“DEFAULT”,使用Isolation.DEFAULT指定;
  • readOnly:指定事务是否只读,默认false表示事务非只读;
  • timeout:指定事务超时时间,以秒为单位,默认-1表示事务超时将依赖于底层事务系统;
  • rollbackFor:指定一组异常类,遇到该类异常将回滚事务;
  • rollbackForClassname:指定一组异常类名字,其含义与<tx:method>中的rollback-for属性语义完全一样;
  • noRollbackFor:指定一组异常类,即使遇到该类异常也将提交事务,即不回滚事务;
  • noRollbackForClassname:指定一组异常类名字,其含义与<tx:method>中的no-rollback-for属性语义完全一样;

 

Spring提供的@Transaction注解事务管理内部同样利用环绕通知TransactionInterceptor实现事务的开启及关闭。

使用@Transactional注解事务管理需要特别注意以下几点:

  • 如果在接口、实现类或方法上都指定了@Transactional 注解,则优先级顺序为方法>实现类>接口;
  • 建议只在实现类或实现类的方法上使用@Transactional,而不要在接口上使用,这是因为如果使用JDK代理机制是没问题,因为其使用基于接口的代理;而使用使用CGLIB代理机制时就会遇到问题,因为其使用基于类的代理而不是接口,这是因为接口上的@Transactional注解是“不能继承的”
  • 在Spring代理机制下(不管是JDK动态代理还是CGLIB代理),“自我调用”同样不会应用相应的事务属性,其语义和<tx:tags>中一样;
  • 默认只对RuntimeException异常回滚;
  • 在使用Spring代理时,默认只有在public可见度的方法的@Transactional 注解才是有效的,其它可见度(protected、private、包可见)的方法上即使有@Transactional 注解也不会应用这些事务属性的,Spring也不会报错,如果你非要使用非公共方法注解事务管理的话,可考虑使用AspectJ。

9.4.9  与其他AOP通知协作

       Spring声明式事务实现其实就是Spring AOP+线程绑定实现,利用AOP实现开启和关闭事务,利用线程绑定(ThreadLocal)实现跨越多个方法实现事务传播。

       由于我们不可能只使用一个事务通知,可能还有其他类型事务通知,而且如果这些通知中需要事务支持怎么办?这就牵扯到通知执行顺序的问题上了,因此如果可能与其他AOP通知协作的话,而且这些通知中需要使用声明式事务管理支持,事务通知应该具有最高优先级。

9.4.10  声明式or编程式

       编程式事务时不推荐的,即使有很少事务操作,Spring发展到现在,没有理由使用编程式事务,只有在为了深入理解Spring事务管理才需要学习编程式事务使用。

       推荐使用声明式事务,而且强烈推荐使用<tx:tags>方式的声明式事务,因为其是无侵入代码的,可以配置模板化的事务属性并运用到多个项目中。

       而@Transaction注解事务,可以使用,不过作者更倾向于使用<tx:tags>声明式事务。

       能保证项目正常工作的事务配置就是最好的。

9.4.11  混合事务管理

所谓混合事务管理就是混合多种数据访问技术使用,如混合使用Spring JDBC + Hibernate,接下来让我们学习一下常见混合事务管理:

 

1、  Hibernate + Spring JDBC/iBATIS:使用HibernateTransactionManager即可支持;

2、  JPA + Spring JDBC/iBATIS:使用JpaTransactionManager即可支持;

3、  JDO + Spring JDBC/iBATIS:使用JtaTransactionManager即可支持;

 

混合事务管理最大问题在于如果我们使用第三方ORM框架,如Hibernate,会遇到一级及二级缓存问题,尤其是二级缓存可能造成如使用Spring JDBC和Hibernate查询出来的数据不一致等。

因此不建议使用这种混合使用和混合事务管理。

 

 

原创内容,转载请注明出处【http://sishuok.com/forum/blogPost/list/0/2508.html

 

38
7
分享到:
评论
22 楼 Dead_knight 2013-07-11  
jinnianshilongnian 写道
Dead_knight 写道
有几个注意点,你这里似乎没有提到。
1.事务的隔离级别。oracle只支持serialize、read-commit。mysql需要修改二进制日志的格式(mixed、statement、row),否则默认的statement也不是都支持这四种隔离级别。所以说,如果不确定数据库所支持的事务隔离级别,贸然的在事务配置中指定,会抛出数据库驱动的异常。当然,一般默认的配置是不存在这个问题的。

2.jta是否支持spring的事务传播特性?我之前测试的结果是不支持,也没深入研究。不知道大哥你有没测试这样的场景。我基于jotm、atomikos两种都测试过的。
1)、如果在action中,直接这样调用:service1.save();service2.save()。如果第二个操作失败,第一个操作没有回滚,事务传播都使用require。
2)、如果在action中,这样调用:service.save();save方法里面的调用顺序为:dao1.save();dao2.save();如果第二个dao的操作失败,第一个操作成功回滚。
由此,我觉得应该是事务传播特性在jta场景下不支持。

1、是的,oracle还有一个readonly隔离级别

2、我测试的是atomikos,忘记当时是否测试了传播性了,回头我看下 再回复

事务传播特性在jta场景下不支持,这个按理说肯定不会的,晚上我研究下



嗯,先谢过。我就是担心我测试的结论是错误的,才跟你交流一下。下周我把spring的事务管理的源码分析一下,应该能得出结论。
21 楼 jinnianshilongnian 2013-07-11  
Dead_knight 写道
有几个注意点,你这里似乎没有提到。
1.事务的隔离级别。oracle只支持serialize、read-commit。mysql需要修改二进制日志的格式(mixed、statement、row),否则默认的statement也不是都支持这四种隔离级别。所以说,如果不确定数据库所支持的事务隔离级别,贸然的在事务配置中指定,会抛出数据库驱动的异常。当然,一般默认的配置是不存在这个问题的。

2.jta是否支持spring的事务传播特性?我之前测试的结果是不支持,也没深入研究。不知道大哥你有没测试这样的场景。我基于jotm、atomikos两种都测试过的。
1)、如果在action中,直接这样调用:service1.save();service2.save()。如果第二个操作失败,第一个操作没有回滚,事务传播都使用require。
2)、如果在action中,这样调用:service.save();save方法里面的调用顺序为:dao1.save();dao2.save();如果第二个dao的操作失败,第一个操作成功回滚。
由此,我觉得应该是事务传播特性在jta场景下不支持。

1、是的,oracle还有一个readonly隔离级别

2、我测试的是atomikos,忘记当时是否测试了传播性了,回头我看下 再回复

事务传播特性在jta场景下不支持,这个按理说肯定不会的,晚上我研究下


20 楼 Dead_knight 2013-07-11  
有几个注意点,你这里似乎没有提到。
1.事务的隔离级别。oracle只支持serialize、read-commit。mysql需要修改二进制日志的格式(mixed、statement、row),否则默认的statement也不是都支持这四种隔离级别。所以说,如果不确定数据库所支持的事务隔离级别,贸然的在事务配置中指定,会抛出数据库驱动的异常。当然,一般默认的配置是不存在这个问题的。

2.jta是否支持spring的事务传播特性?我之前测试的结果是不支持,也没深入研究。不知道大哥你有没测试这样的场景。我基于jotm、atomikos两种都测试过的。
1)、如果在action中,直接这样调用:service1.save();service2.save()。如果第二个操作失败,第一个操作没有回滚,事务传播都使用require。
2)、如果在action中,这样调用:service.save();save方法里面的调用顺序为:dao1.save();dao2.save();如果第二个dao的操作失败,第一个操作成功回滚。
由此,我觉得应该是事务传播特性在jta场景下不支持。
19 楼 jinnianshilongnian 2013-01-14  
at1943 写道
确实是shiro的DefaultAdvisorAutoProxyCreator配置问题,去掉就不抱错。但那个是shiro权限注解用的吧
引用
用AOP控制方法时,把DefaultAdvisorAutoProxyCreator的proxyTargetClass属性设为true,与事务AOP一起使用cglib。
这句不太对啊,没有proxyTargetClass这个属性。

估计版本问题,你看看最新版本是否有
18 楼 at1943 2013-01-13  
确实是shiro的DefaultAdvisorAutoProxyCreator配置问题,去掉就不抱错。但那个是shiro权限注解用的吧
引用
用AOP控制方法时,把DefaultAdvisorAutoProxyCreator的proxyTargetClass属性设为true,与事务AOP一起使用cglib。
这句不太对啊,没有proxyTargetClass这个属性。
17 楼 jinnianshilongnian 2013-01-12  
jinnianshilongnian 写道
at1943 写道
就在这里https://github.com/runcat/domain4cat


我记得是
<!-- 保证实现了Shiro内部lifecycle函数的bean执行 -->
<bean id="lifecycleBeanPostProcessor" class="org.apache.shiro.spring.LifecycleBeanPostProcessor"/>



<bean class="org.springframework.aop.framework.autoproxy.DefaultAdvisorAutoProxyCreator" depends-on="lifecycleBeanPostProcessor"/>
<bean class="org.apache.shiro.spring.security.interceptor.AuthorizationAttributeSourceAdvisor">
    <property name="securityManager" ref="securityManager"/>
</bean>

这个的问题了,之前给一朋友弄过,暂时记不清了 ,你看看文档这个


记得是这样的,你参考下
https://github.com/springside/springside4/wiki/ShiroSecurity

1. 各种Bean找不到的问题。

A. 与Spring Data JPA同时使用时,ShiroFilterFacotryBean的BeanPostProcessor报找不到XXDao类,可能是Spring Data JPA的BeanPostProcessor还没完成自己的任务吧。一个workaround方法是在shiroDbRealm的定义里加上depends-on="缺失Dao"的定义,强制Dao被初始化。 B. 用AOP控制方法时,把DefaultAdvisorAutoProxyCreator的proxyTargetClass属性设为true,与事务AOP一起使用cglib。
16 楼 jinnianshilongnian 2013-01-12  
at1943 写道
就在这里https://github.com/runcat/domain4cat


我记得是
<!-- 保证实现了Shiro内部lifecycle函数的bean执行 -->
<bean id="lifecycleBeanPostProcessor" class="org.apache.shiro.spring.LifecycleBeanPostProcessor"/>



<bean class="org.springframework.aop.framework.autoproxy.DefaultAdvisorAutoProxyCreator" depends-on="lifecycleBeanPostProcessor"/>
<bean class="org.apache.shiro.spring.security.interceptor.AuthorizationAttributeSourceAdvisor">
    <property name="securityManager" ref="securityManager"/>
</bean>

这个的问题了,之前给一朋友弄过,暂时记不清了 ,你看看文档这个
15 楼 at1943 2013-01-11  
就在这里https://github.com/runcat/domain4cat
14 楼 jinnianshilongnian 2013-01-11  
at1943 写道
jinnianshilongnian 写道
at1943 写道
No matching bean of type [net.noday.d4c.service.impl.DnsRecordServiceImpl] found for dependency: expected at least 1 bean which qualifies as autowire candidate for this dependency. Dependency annotations: {@org.springframework.beans.factory.annotation.Autowired(required=true)}
应该实例化了,因为我打断掉到DnsRecordServiceImpl的构造函数里发现其运行了两次。

怀疑springmvc 配置文件的问题

请参考
http://www.iteye.com/topic/1128522

我的应该没有这个问题吧,我都是分开扫的

那你发我下相关配置文件
13 楼 at1943 2013-01-11  
jinnianshilongnian 写道
at1943 写道
No matching bean of type [net.noday.d4c.service.impl.DnsRecordServiceImpl] found for dependency: expected at least 1 bean which qualifies as autowire candidate for this dependency. Dependency annotations: {@org.springframework.beans.factory.annotation.Autowired(required=true)}
应该实例化了,因为我打断掉到DnsRecordServiceImpl的构造函数里发现其运行了两次。

怀疑springmvc 配置文件的问题

请参考
http://www.iteye.com/topic/1128522

我的应该没有这个问题吧,我都是分开扫的
12 楼 jinnianshilongnian 2013-01-11  
at1943 写道
No matching bean of type [net.noday.d4c.service.impl.DnsRecordServiceImpl] found for dependency: expected at least 1 bean which qualifies as autowire candidate for this dependency. Dependency annotations: {@org.springframework.beans.factory.annotation.Autowired(required=true)}
应该实例化了,因为我打断掉到DnsRecordServiceImpl的构造函数里发现其运行了两次。

怀疑springmvc 配置文件的问题

请参考
http://www.iteye.com/topic/1128522
11 楼 at1943 2013-01-11  
https://github.com/runcat/domain4cat是这个,主要是加接口太麻烦了,实在不行加上接口就正常了
10 楼 at1943 2013-01-11  
No matching bean of type [net.noday.d4c.service.impl.DnsRecordServiceImpl] found for dependency: expected at least 1 bean which qualifies as autowire candidate for this dependency. Dependency annotations: {@org.springframework.beans.factory.annotation.Autowired(required=true)}
应该实例化了,因为我打断掉到DnsRecordServiceImpl的构造函数里发现其运行了两次。
9 楼 jinnianshilongnian 2013-01-11  
at1943 写道
找不到
No matching bean of type [net.noday.d4c.service.impl.DnsRecordServiceImpl] found for dependency: expected at least 1 bean which qualifies as autowire candidate for this dependency.

把相关配置文件(包括springmvc)的发我站内信 我帮你看下
8 楼 at1943 2013-01-11  
找不到
No matching bean of type [net.noday.d4c.service.impl.DnsRecordServiceImpl] found for dependency: expected at least 1 bean which qualifies as autowire candidate for this dependency.
7 楼 jinnianshilongnian 2013-01-11  
at1943 写道
求 助啊!service层不想用接口,但是用了下边的配置controller中总是注入不成功。
<bean id="txManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
<property name="dataSource" ref="dataSource" />
</bean>
<tx:advice id="txAdvice" transaction-manager="txManager">
<tx:attributes>
<tx:method name="save*" propagation="REQUIRED"/>
<tx:method name="*" read-only="true" />
</tx:attributes>
</tx:advice>
<aop:config proxy-target-class="true">
<aop:advisor advice-ref="txAdvice" pointcut="execution(* net.noday..service..*.*(..))" />
</aop:config>


抱什么错
6 楼 at1943 2013-01-11  
求 助啊!service层不想用接口,但是用了下边的配置controller中总是注入不成功。
<bean id="txManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
<property name="dataSource" ref="dataSource" />
</bean>
<tx:advice id="txAdvice" transaction-manager="txManager">
<tx:attributes>
<tx:method name="save*" propagation="REQUIRED"/>
<tx:method name="*" read-only="true" />
</tx:attributes>
</tx:advice>
<aop:config proxy-target-class="true">
<aop:advisor advice-ref="txAdvice" pointcut="execution(* net.noday..service..*.*(..))" />
</aop:config>
5 楼 pangyi 2012-12-12  

收获很大。知识的价值就是分享。非常感谢楼主的分享精神。
4 楼 jinnianshilongnian 2012-11-12  
縌流而上的魚 写道
老师,下面这句话:
“多事务语义配置时,切入点一定不要叠加,否则将应用两次事务属性,造成不必要的错误及麻烦。”
可以理解为,多种事务配置的时候,避免一个方法或者一个包下面的所有类的方法重复使用不同的事务配置,是吗?

对头
3 楼 縌流而上的魚 2012-11-12  
老师,下面这句话:
“多事务语义配置时,切入点一定不要叠加,否则将应用两次事务属性,造成不必要的错误及麻烦。”
可以理解为,多种事务配置的时候,避免一个方法或者一个包下面的所有类的方法重复使用不同的事务配置,是吗?

相关推荐

Global site tag (gtag.js) - Google Analytics