如何将多个方法调用作为一个事务进行管理

时间:2016-02-01 05:53:49

标签: java api rest transactions transactionscope

我在为我的REST API(JAVA)建立事务管理器/范围时遇到问题,我在API后端有以下函数,我想将所有以下函数作为一个事务执行,

  1. 致电第三方WS终点
  2. 解密回复
  3. 将响应保存到DB1
  4. 将响应保存到DB2
  5. 我想确保上述所有步骤都已完成或回滚,如果有任何一个失败,我有足够的信息来进行回滚,但我不知道实现正确的事务管理机制的最佳做法是什么,因为上面提到的每个API调用在3个单独的类中发生步骤,
    这是我的类结构的伪代码

    class CallWS {
    public People callThWS() {
      // functions related to call third party WS and decryption (step 1,2)
     }
    }
    
    class People peopleServices {  
       public People getPeopleData() {
            callThWS ppl= new callThWS();
            People pplObj = ppl.callThWS(); 
            // save to DB1, (step 3)
            return pplObj;
       }
    }
    
    class People peopleContr {
     public People getAllPeople() {
        peopleServices ppSer= new peopleServices();
        People pplObj2 =  ppSer.getPeopleData();
        // save to DB2, (Step 4)
        return  pplObj2; 
     }
    }
    

    请帮我这个,
    感谢

2 个答案:

答案 0 :(得分:0)

您需要的是分布式事务(XA)。检查支持XA的各种事务管理器的示例。查看this文章,了解如何在独立应用程序中使用XA提供程序(警告:旧文章)。

答案 1 :(得分:0)

如果您控制列出的所有类的来源,并且您可以按照单个入口点的方式重构代码,那么除了调用外部Web服务之外,您可以非常轻松地完成。伪代码如下。

在这里,我们应该同意您在方法中调用的所有资源都是事务性的。正如我之前提到的,对外部WS的调用不会属于该类别,因为对外部Web服务的调用本质上不是事务性的。再次,如果您不通过调用外部服务来更改数据,您可以考虑将其留在事务外部。你仍然有一点控制权。就像回滚交易一样,如果对外部服务的调用不成功,并且只要你没有改变另一方的任何东西,你可能不关心在那里回滚交易。

但是你仍然有一些选项可以调用外部WS调用,例如Web Services Atomic Transactions,但我敢打赌你需要控制源,甚至可能需要控制另一方的环境。在这种幸运的情况下,您宁愿通过避免WS调用来实现它。

class RestAPIEntryPointResource {
    @Inject
    CallWS callWS;

    @Inject
    PeopleServices peopleServices ;

    @Inject
    PeopleContr peopleContr;

 /*Put some transaction demarcation here. 
If your class is an EJB, it is already done for you. 
With Spring you have various options to mark the method transactional. 
You also may want to take a manual control, but it look redundant here. */
    public void entryPointMethod() {
        callWS.callThWS();
        peopleServices.getPeopleData();
        peopleContr.getAllPeople();
    }
}

class CallWS {
    public People callThWS() {
        // functions related to call third party WS and decryption (step 1,2)
    }
}

class PeopleServices {
    public People getPeopleData() {
        ..........
    }
}

class PeopleContr {
    public People getAllPeople() {
        .........
    }
}