【问题标题】:Transaction Rollback in Controller if exception occurred in any service如果任何服务发生异常,控制器中的事务回滚
【发布时间】:2014-10-26 14:32:32
【问题描述】:

我是 spring 的新手,在 Transaction 中遇到问题。

我创建了两个模型如下:

UserDto - Stored user information
RoleDto - Stored user's role information

两种模型的服务如下(都用@Transactional注释):

UserService - void saveUser(UserDto userDto) throws Exception;
RoleService - void saveRole(RoleDto roleDto) throws Exception;

现在当用户在应用程序中创建帐户时,我调用了控制器的“add”方法,其代码如下:sn-p:

userService.saveUser(userDto);
roleService.saveRole(roleDto);

现在在此代码中,如果 Roleservice 中发生异常,它仍会将用户数据插入数据库表中。但是如果 roleService 抛出任何异常,我也想回滚。我试图找到解决方案,但找不到任何好的教程。任何帮助将不胜感激。

【问题讨论】:

    标签: java spring spring-transactions


    【解决方案1】:

    您调用该方法的方式使每个方法都有自己的事务。你的代码可以这样理解:

    Transaction t1 = Spring.createTransaction();
    t1.begin();
    try {
        //your first service method marked as @Transactional
        userService.saveUser(userDto);
        t1.commit();
    } catch (Throwable t) {
        t1.rollback();
    } finally {
        t1.close();
    }
    Transaction t2 = Spring.createTransaction();
    t2.begin();
    try {
        //your second service method marked as @Transactional
        roleService.saveRole(roleDto);
        t2.commit();
    } catch (Throwable t) {
        t2.rollback();
    } finally {
        t2.close();
    }
    

    解决此问题的一种方法是创建另一个服务类,在该服务类的实现中注入了RoleServiceUserService,标记为@Transactional 并调用这两个方法。这样,两个方法将共享该类中使用的相同事务:

    public interface UserRoleService {
        void saveUser(UserDto userDto, RoleDto roleDto);
    }
    
    @Service
    @Transactional
    public class UserRoleServiceImpl implements UserRoleService {
        @Autowired
        UserService userService;
        @Autowired
        RoleService roleService;
    
        @Override
        public void saveUser(UserDto userDto, RoleDto roleDto) {
            userService.saveUser(userDto);
            roleService.saveRole(roleDto);
        }
    }
    

    更好的设计是使RoleDto 成为USerDto 的字段,并且USerService 的实现注入了RoleService 字段并执行必要的调用来保存每个字段。请注意,服务类必须提供包含业务逻辑的方法,这也意味着业务逻辑规则。服务类不仅仅是 Dao 类的包装器。

    这可能是上述解释的一个实现:

    @Service
    public class UserServiceImpl implements UserService {
        @Autowired
        RoleService roleService;
    
        public void saveUSer(UserDto userDto) {
            //code to save your userDto...
            roleService.saveRole(userDto.getRoleDto());
        }
    }
    

    【讨论】:

    • 感谢您的精彩解释,我会按照它来解决我的问题。非常感谢
    猜你喜欢
    • 2017-03-17
    • 2013-11-23
    • 1970-01-01
    • 2021-01-15
    • 2015-12-08
    • 2013-10-16
    • 2012-12-28
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多