如何与第三方接口保持数据一致性

大家经常遇到这样的需求,尤其是支付中心接口的时候:

查询满足某种条件的订单,调用第三方接口成功,更改订单状态。

常见实现示例

task1:

orders = queyrOrder(...); //查询已离店的订单

        for (Map<String, Object> order : orders) {

            try {

                con.setAutoCommit(false);

                String orderNo = (String) order.get("order_no");

                // 调用支付中心返现接口

                callCommission(order);  //无论是网络异常还是返回结果失败,都抛异常

                // 更改订单状态

                cashedOrder(con, order); //更改订单状态

                con.commit();

        }

  

task 2

orders = queyrOrder(...);//查询“返现中”的订单

 for (Map<String, Object> order : orders) {

        con.setAutoCommit(false);

        // 调用返现任务

        callCommission(order);

        // 更改订单状态

        cashedOrder(con, order);

        con.commit();           

 }

  

示例的问题
  1. 在事务中存在远程调用,容易导致事务时间过长
  2. 在callCommission 和 cashedOrder之间,是否有其他操作能改变该订单状态? 如果有,是否会出现多次调用第三方的问题?
  3. 第三方接口特性未知
设计方案

往两个方面思考

  1. 自己系统本身数据一致性
  2. 如果调用第三方接口 和 更新自己系统数据 之间任何一个环节 出异常了。比如:应用重启,机房网络问题等。如何保证第三方接口和自己系统的数据一致性?

方案

  1. 加锁,方案有:版本号乐观锁、select for update 悲观锁。
    延伸问题:在原表上执行task,还是队列表?
  2. 第三方接口需要什么特性才能保证数据一致性? 要考虑网络超时问题、应用发布重启、并发等问题。
  • 回调
  • 提供结果查询
  • 幂等性
重构后的示例1:

(幂等接口的方案)


queueOrders = queryQueueOrders();

for(QueueOrder order : queueOrders){

   callApi()

   startTransaction();

   lock(order);  

   updateStatus()

   commitTransaction();

}


(提供结果查询的API接口的方案)


queueOrders = queryQueueOrders();

for(QueueOrder order : queueOrders){

   try{

      startTransaction();

      if(isBeingProcess(order)){

          Result r = queryAPIResult();

          if(r.success()){

            return;

          }

      }

      lock(order);

      callApi()

      updateStatus();

   }finally{

   commitTransaction();

   }

}


注意:该示例依然有“在事务中调用远程接口的问题”

http://www.cnblogs.com/NanguoCoffee/archive/2013/03/30/2990918.html

时间: 2024-10-13 14:40:42

如何与第三方接口保持数据一致性的相关文章

asp.net后台集成QQ第三方接口含发送微博、带图片微博(有源码)

最近在做项目的时候用到了QQ第三方接口,腾讯提供了JS.安卓.IOS.php的SDK,但是没有C#的SDK.一开始我是在前台直接用JS的SDK做登陆验证,但是做完自己就感觉这样很可笑,JS是暴露给客户端的,那么客户完全可以直接绕过去,进入到你的后台. 所以我在通过登陆验证后回调后台页面,在后台进行合法性验证,防止非法登陆. 原理就是后台通过httpwebrequest操作第三方接口 /// <summary> /// HTTP POST方式请求数据 /// </summary> /

Java Web系统经常使用的第三方接口

1. Web Service 接口 1.1 接口方式说明和长处 在笔者的开发生涯中,当作为接口提供商给第三方提供接口时,以及作为client去调用第三方提供的接口时,大部分时候都是使用 Web  Service接口, Web Service作为接口使用广泛的原因,与它的特点息息相关. Web Service的主要目标是跨平台的可互操作性,为了实现这一目标, Web Service 全然基于 XML(可扩展标记语言). XSD( XML Schema)等独立于平台.独立于软件供应商的标准,是创建可

采用http请求第三方接口实现Demo

我们在调用第三方接口的时候,有的时候需要采用http协议进行通信,这里简单介绍一下http请求的执行过程. 写在前面: 你需要找到一个能访问的接口url,知道需要传递什么参数,请求的编码格式. 下面是我写的一个示例. package cn.sccl.lijianbo; import java.io.IOException; import java.util.ArrayList; import java.util.List; import org.apache.http.HttpEntity; i

快速对接第三方接口--短信接口

1,账号注册.获取key及secret 在第三方接口站点注册账户,进而获取账户的key和secret 2,浏览所需接口,复制示例代码 对需求接口文档大致快速浏览,找到示例代码复制到本地,详细阅读文档,一一对照,编辑代码. 对调试屡次出错的情况: A,如允许get提交,直接超链接方式传值,访问浏览器,确定错误范围 B,整体认真查看文档后,再示例代码,分别对比,确认本地代码与其差距,找出错误

关于 第三方接口支付的时候 采用post提交的方式,有两种 一种是通过 curl来进行,一种是通过js当页面加载完后跳转

这是第一种.通过javascript页面加载完后,对表单采用 post方式提交给 第三方接口----- echo <<<_END<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"><html xmlns="http://www.w3.

第三方接口调用封装

1.背景 基于公司项目情况,几乎每个项目都有大量的调用第三方数据接口的情况,因此急需一个公共的调用第三方接口的组件.同时也需要在调用过程中对于缓存.出错日志.重试等公共操作的封装. 2.组件设计说明 1.代码简洁.清晰 2.面向接口编程,支持扩展 3.职责单一原则 4.组件架构如下图: 3.代码说明 1.代码库地址: http://git.bbdops.com/dafei/components 2.采用技术包括 mybatis.jpa.swagger2.springboot

SpringMVC 结合HttpClient调用第三方接口实现

使用HttpClient 需要依赖jar包 1:commons-httpclient-3.0.jar 2:commons-logging-1.1.1.jar 3:commons-codec-1.6.jar 本地调用测试===>>>>>>>>>>>> package com.me.cn.siteTrans.test; import java.util.HashMap; import java.util.Map; import org.a

某航空项目第三方接口测试总结及接口测试技术的探讨

XX项目第三方接口测试总结及接口测试技术的探讨 1. 了解第三方接口 1.1 第三方接口的概念 XX项目第三方接口也就是电子客票网站扩展接口,主要功能是为了满足用户通过对接口的调用来替代原来用户必须进入网站才能进行相关操作的需求,方便代理人(大客户)提高自有系统流程的自动化程度.常见的第三方接口为商旅网接口包括携程.去哪儿等OTA及一些较大的代理人网站等. 1.2 网站与第三方接口的关系 接口的业务功能与现有网站功能必须一致,用户使用接口生成的订单,也可以通过登录网站来进行处理,如用户可以在第三

PHP通过XML报文方式,已第三方接口交互(发送xml,获取XML,并解析xml步骤)

开发者端:发送请求,并接收结果 <?php // 下面的demo,实现的功能如下: // 1-开发者需要判断一个用户是否存在,去请求第三方接口. // 2-与第三方接口的通信,是以xml格式传送数据.开发者把用户信息以xml格式发送给第三方接口 // 3-第三方接口获取开发者的xml数据,通过数据的查询,把结果再以xml的格式发送给开发者. //首先检测是否支持curl if (!extension_loaded("curl")) { trigger_error("对不