我的支付总结(二) 系统设计
业务流程
上文提到由于支付处理的流程复杂性,为了避免因为冗长的流程阻塞降低了处理效率,支付系统中多使用异步机制,将整个支付业务流程拆分为多步处理。支付系统将流程划分为业务受理、支付前置和支付网关、终态获取、结果处理四个大部分,各部分之间以消息队列或系统之间的交互分隔。风控和路由属于支付前置服务,但由于其重要性和复杂性,将它们提出来分别介绍。
下面的图是两种典型的交易时序图:
业务受理
业务受理接口是与商户系统的交互处,主要功能为接受交易业务,响应给商户的是受理结果,而并非交易结果,交易结果会通过异步方式告知商户。
为了考虑接口的安全性,受理接口要依次验证支付请求报文的安全性、商户的权限、参数的合法性。为了保证保证交易入口的可用性,特殊接口还要限制商户的请求频率。
由于受理结果要同步响应给商户,很长的验证流程是不合适的。要尽量保证受理接口进行的是基础验证,对其他复杂的的验证流程,进行异步处理,验证无法通过的再置交易为失败为好。
受理接口还需要特别注意到的一点是要保证系统受理和接口响应的原子性,即要保证响应给商户的受理结果是真实的,可查询的。要保证受理结果响应给商户后,该笔交易要能查询到,这时候便需要数据落地和响应商户的顺序了。为了保证安全,要在数据落地后再将受理结果响应给商户,避免出现数据丢失的情况。
此时要开始异步流程的第一步了,受理成功待处理的交易应该在消息队列内。
风控
风控的概念上文已提过,这里说一下风控系统的简单实现。
首先是交易量风控,交易金额过大、交易频率过高的交易都是需要注意的,通过配置对不同交易分类的阈值限制,将可疑交易打上风控标签,再添加后续验证来确认。
然后是交易惯性风控,这就需要对比用户画像来确定了。通过分析用户的多次支付习惯,为用户“画”一张大概的“画像”,支付时对比是否符合其支付习惯,对异常的交易进行后续验证。(由于用户支付的量不大,无此功能,不再多提)
后续验证可以分交互性交易和非交互性交易来分别处理,对非交互性交易,如代收或代付,并不要求交易的实时性,可以采用接口审核或人工审核的方式。而交互性交易,如收银台交易,审核肯定不能达到要求的实时性,添加验证步骤,如手机验证码等二次验证则十分适用。
支付路由
支付路由,简单的说就是选择一条支付通道。支付通道要有一定维度上的优先级,这里提到优先级,是因为支付通道偶尔会因为系统维护、银行维护等原因关闭,那么在可选通道之间要有优先级来调控优先通道不可用时的替代通道。单纯的通道路由在技术上实现起来可能非常简单,可是通道路由要考虑的因素还有很多:
- 三方系统三方系统支持:最基本的要求了,一般三方系统对账户类型、卡类型、银行等有不同的支持范围。
- 便宜:很直观的要求,为了公司的开销考虑,能使用价格低的通道最好。虽然低价格在一定程度上代表着低质量,会埋下各种各样甚至不可思议的坑。
- 通道限流:由于各个系统对通道的限制不同,在达到通道上限后自然要限制交易频率。还有些三方系统比较傲娇,接了我们的支付通道却不用也不行,所以支付通道的流量还要有下限。
- 动态调节:动态调节是通道路由的完全态会有的功能,和分布式系统中对各个服务器的监控类似,实时监控通道的状态,在判断通道的失败率达到某个阈值后自动关闭通道,使用替换通道。并间隔一段试探通道的状态,在其交易恢复正常后再将通道打开。
支付网关
支付网关是支付系统与三方系统的交互接口,支付网关的设计要考虑的重点是报文的交互。除了普通系统要进行的参数验证、内外系统参数映射、各种请求类的包装外,支付系统要额外考虑的有:
- 报文签名和加密:这个各个支付系统会有不同的要求,见招拆招即可,这就需要掌握一些加密知识了,也是我之前花很多时间研究通信加密的原因(说起来还挺敬业 = =)。
- 日志:网关日志很重要!!!不光是作为与三方系统交互的凭证,也是排查错误的关键信息。一般会将原始(强调一下)报文记录下来,包括请求参数、响应参数、耗时等信息。
终态获取
支付系统的交易除了需求实时性较强的快捷支付外,其他交易类型一般都是异步,那么终态的获取就靠主动查询和异步回调通知。
异步回调通知:异步回调通知是最基本的获取三方终态的方式了,即支付系统在支付请求时提供一个通知地址,在三方系统处理完交易后请求此地址并附带交易结果信息。需要注意报文验签防止报文伪造。另外通知一般会多次通知以确保通知到达,还要给三方系统符合规则的响应,以在自己系统处理完交易后,告诉三方系统停止通知。
主动查询:主动查询是对异步回调通知的保证。在有的系统(呵呵)不提供回调通知或自己系统故障通知失败,或对交易的实时性要求很高,而三方系统的异步通知延迟严重时,主动查询就非常重要了。需要注意查询时机,一定要确认三方系统已完全受理了交易且可查询后再调用查询接口。
结果处理
获取到支付结果后,不光要及时更新自己系统内的支付状态,还要考虑对交易的后续处理:
- 结果通知:同三方系统通知支付系统,支付系统要将支付结果及时通知商户。为了确保通知成功,重试机制是必不可少的,这里考虑三方系统通知支付系统的逻辑。
- 推送账务系统:由于支付系统的账务由账务和资金管理系统负责,支付系统只负责交易结果的推送。单独的账务和资金管理系统功能介绍见下;
- 触发统计:为了保证交易统计的实时性,在支付成功后尽快统计支付结果。
支付结果在确认后正常流程内不再变动,为了减少支付结果的处理对交易表的侵入性,可以使用另一张 交易终态表 来承担交易结果处理的记录。至于两张表的数据同步,使用数据库的事务即可。
账务和资金管理
账务和资金管理系统是为了在资金流上确保交易的正确。
支付系统之间一般在第二日进行前一日交易的资金结算。账务负责维护各个商户与支付通道的对应银行账户,并根据当日的交易结果汇总出资金的应收应付,第二日财务人员根据应收应付和实收实付进行转账和核销。
附属服务
附属服务不属于交易流程的一部分,但它们也是必不可少的部分,对异常交易的排查、修复有着重要意义。
对账
对账是对前一日交易在全局上的对照,不同于账务和资金管理系统,对账是在数据流上确定交易的正确性,一般的对账流程如下:
- 下载对账文件 针对各三方系统的下载方式:FTP/HTTP 获取到对账文件
- 标准化处理:将格式为 txt/xml/cvs/zip 的三方系统对账文件处理成一种选用格式;
- 本地对账准备:可以根据数据量的大小,从源库/从库/nosql/文件方式准备与三方系统对账文件的对比
- 两个账务数据对比。
- 差异数据修复(人工/后续)
监控
监控在每个完备的系统都会存在,不过一般是运维层面上的,支付系统更多的是在业务层面上的监控。监控系统一般监控交易异常、通道异常等影响正常交易的状况,并及时报警告知运营或技术人员。
监控方式一般有:
- 统计法:定时对比统计数据与监控阈值,在统计数据的异常比例超出监控阈值时触发报警。
- 试探法:以测试交易来定时试探系统的稳定性和三方通道的稳定性。
- 埋点法:在支付关键节点埋点,并检验交易状态是否在期望状态。
统计
统计数据一般包括,交易总额,手续费,交易总笔数,成功率等,一般根据业务线、支付通道、银行等维度来分别统计。
对运营人员来说,统计数据可以帮助在全局上观察交易状况,作出决策;对于业务流程来说,统计数据可以作为通道路由的基础,如在支付通道交易异常率较高时降低其优先级等,也可以为监控系统提供数据;对技术人员来说,统计可以帮助有方向地优化系统。
小结
理清了支付的各个必备模块,系统设计应该就会很清晰了,完成了系统设计,后续的工作就剩下代码的堆砌和完善了。
支付服务中的每一块都有一定的“门道”,有机会和必要的话,会单独拿出来一块写。
感谢关注。