支付核心系统设计:Airbnb的分布式事务方案简介

导读:微服务架构下的支付系统 , 由于其需要在性能和一致性之间做很多权衡 , 带来设计和实现的复杂性 。Airbnb的支付系统需要对接全球很多个国家的支付系统 , 因此带来很大的复杂性 。本文详细论述了Airbnb如何使用分布式事务的相关技术来保证支付系统的数据一致性和性能 , 十分值得一读 。
过去几年中 , Airbnb一直在将其基础架构迁移到SOA 。相比单体应用 , SOA提供了许多优势 , 例如支持开发人员专业化和加速迭代的能力 。然而 , 这也对计费和支付程序提出了挑战 , 因为SOA使维护数据完整性变得更加困难 。对服务API的调用 , 该服务对下游服务进行进一步的API调用 , 其中每个服务改变状态都可能具有副作用 , 等同于执行复杂的分布式事务 。
为了确保所有服务之间的数据一致性 , 可以使用两阶段提交之类的协议 。如果不用这样的协议 , 数据一致性就难以保证 。在分布式系统中请求不可避免地会失败(连接会在某些时候丢失并超时 , 尤其是对于包含多个网络请求的事务 。
分布式系统中使用三种不同的常用技术来实现最终的一致性:读修复 , 写修复和异步修复 。每种方法各有利弊 。三种方式在我们的支付系统中都有使用 。
异步修复通过服务器负责运行数据一致性检查来实现 , 例如表扫描 , lambda函数和cron job 。此外 , 从服务器到客户端的异步通知广泛用于支付行业 , 以保持客户端的一致性 。异步修复以及通知可以与读写修复技术结合使用 , 提供第二道防线 , 并在解决方案复杂性方面起到作用 。
本文中描述的解决方案使用了写修复 , 其中从客户端到服务器的每次写入调用都尝试修复不一致状态 。写修复要求客户端更加智能(稍后我们将对此进行扩展讨论) , 并允许重复发出相同的请求 , 而不必维护状态(除了重试) 。因此 , 客户端可以按自己的需求来达到最终的一致性 , 从而使他们能够控制用户体验 。在实现写修复时 , 幂等性是一个非常重要的属性 。
 
什么是幂等?API请求具有幂等性即客户端可以重复进行相同的调用 , 结果将是相同的 。换句话说 , 发出多个相同的请求应该与发出单个请求具有相同的效果 。
这种技术通常用于涉及资金流动的计费和支付系统 , 即支付请求必须完全处理一次(也称为“确切一次交付”) 。重要的是 , 如果多次调用移动资金操作 , 系统最多只能移动一次资金 。这对Airbnb Payments API至关重要 , 以避免多次支付 。
幂等性允许来自客户端的多个相同请求使用API的自动重试机制来达到最终一致性 。这种方式在具有幂等性的客户端 - 服务器中是常见的 , 并且在我们的系统中也是如此 。
下图说明了重复请求和理想幂等行为的简单场景 。无论收费多少 , 客户最多支付一次费用 。

支付核心系统设计:Airbnb的分布式事务方案简介

文章插图
 
问题描述保证我们的支付系统最终的一致性至关重要 。幂等性是在分布式系统中实现这一点的理想机制 。在SOA世界中 , 我们将不可避免地遇到问题 。例如 , 假如服务没有响应 , 客户端将如何恢复?如果Response丢失或客户超时怎么办?如果竞争条件导致用户点击“预订”两次呢?我们的需求包括:
  • 我们需要一个通用但可配置的幂等解决方案 , 而不是实现针对特定用例的自定义解决方案 , 以便在Airbnb的各种支付服务中使用 。
  • 虽然正在迭代基于SOA的支付产品 , 但我们无法在数据一致性上妥协 。
  • 我们需要超低延迟 , 因此构建单独的幂等服务不能满足延迟要求 。最重要的是 , 该服务将遇到上述问题 。
  • 随着Airbnb使用SOA扩展其工程组织 , 让每个开发人员专注于数据完整性和最终的一致性是非常低效的 。我们希望业务开发免受这些麻烦 , 保证他们能够专注于产品开发并更快地进行迭代 。
此外 , 代码可读性 , 可测试性和故障排除能力的相当大的权衡被认为是非主导因素 。


推荐阅读