大家好,我是落雨尘,今天我们来聊一聊银行前置系统,还是随便聊点儿。
作为曾经银行前置系统的全栈型工程师,有一段时间沉浸甚至是沉迷在写“交易”的快乐中。由于受系统和眼界所限,这里所写的银行前置系统,更多的是基于中小型商业银行的系统架构。
我们今天聊的金融前置系统,更多是依托银行的业务背景下进行描述。
前置系统是什么
所谓前置系统,顾名思义,置于前面的平台系统都可以称为前置系统。
今天老李为了周转资金,要去找银行贷款,来到银行大厅被告知先要进行征信查询,在大厅找到一台征信查询机,输入个人信息点击查询,几秒后老李就在屏幕上看到了自己所有的征信内容。
这个查询机,就是一种前置机,TA部署在各个银行大厅,后台通过专线连接着征信中心的后台系统。指令信息通过银行系统的处理再经过这个前置系统进行数据传输,最终拿到征信中心的数据并展示在屏幕上。
快过年了,骗子们也要张罗年货。这不刘大妈刚被电信诈骗了,她赶紧给自己开户的银行打电话,银行客服进行了快速止付的操作后,刘大妈的钱得以被冻结,没有汇入到骗子的账户内。
针对电信诈骗,公安部和人民银行联合部署了一套防控系统,这套系统同样拥有前置机,TA部署在各银行网点,通过金融城域网接入公安部后台系统。
每天银行可通过这台前置机查询客户的身份信息是否在电信诈骗的黑名单中;同时公安部每天也会将涉及该银行的电信诈骗相关信息推送在这台前置机上,供银行查阅处理。
公司会计小张每天都要统计公司账户出入账情况,每天下班前,他都会打开银行专用的软件,选择要查询的公司账户,点击查询后,几秒后就能看到今天该账户的进出资金明细。
小张使用的其实就是银行针对企业的银企直联的前置接口软件,这种软件往往部署在各公司的电脑上,需要u-key的认证,通过互联网或者专线接入到银行前置系统。每次公司客户在软件操作后,数据通过前置接口软件传输到银行前置系统,最终拿到业务数据返回到企业客户的电脑上。
以上三种场景下,前置系统可以是一台机器搭载着接口软件,也可以仅仅是一款软件安装在任何一台电脑上。TA更多的工作是用来连接两边系统,身份验证、接收指令、传输数据...
银行为什么需要前置系统
传统银行系统更像是手动记账的延续,在系统设计也是点对点的处理模式,即前台(柜台)输入,后台(核心系统)记账。如果需要有外联系统的,由后台直接联动外联系统的一个软件或前置机,将请求发出去。这种系统框架安装实施方便、部署快捷,供规模较小的银行使用,足以满足其需要。
但随着银行规模的扩大,现有的系统模式越发的满足不了区域性业务的差异性复杂性。尤其是客户端种类的创新,各种自助终端、移动端接入层出不穷,以往的银行架构牵一发而动全身,升级优化都造成了很大的不便。
于是,渐渐的我们把系统中用来与外部通讯的、身份校验的、加密验签的等等功能都剥离出来,让原本的后台(核心系统)更专注于银行业务的本质工作(记账)。
这些剥离出来的功能,组合在一起就形成了前置系统。
银行前置系统在什么位置、能做什么
就如之前所说的,银行的前置系统是连接两边系统,期间进行身份验证、接收指令、传输数据、后台调度等工作。
前置系统独立出来之后,慢慢的,银行的架构变成“前端(柜台、ATM、网银等)-前置-后台”,前端发起的交易指令,由前置统一接入,并进行报文格式校验、解密验签等工作,之后将业务信息组成银行核心系统需要的报文格式,统一调度核心系统交易接口完成交易处理。
同时前置还负责与外联的渠道(银联、网联、二付支付、征信中心等等)接入,所有外联系统只需要跟前置做接口,包括消息报文接口、文件传输接口,简化了后台业务处理接口。
对于全国性银行系统架构主要体现在区域的前置分级和后台的业务系统化上,一般采用“前台-市级渠道前置-省级渠道前置(-地方性业务系统)-综合大前置-各个业务系统”,省市级渠道前置除了分担庞大的交易连接压力外,还担任了级联架构中地方独有业务的大前置角色,对于它来说,地方性业务系统就是本级的后台。
综合大前置包容了前置的交易统一调度功能,还把后台的一些公共的业务逻辑处理移过来,一方面以减少与后台的交互环节,另一方面也达到基础数据统一管理。
前置系统功能模式
这里需要将前置系统分成两个功能部分来说,一部分是渠道功能,一部分是大前置的业务处理、流程调试功能。
渠道功能
这部分主要实现了通讯接入和渠道报文转换的功能。面对各种各样的通讯方式和报文格式,前置系统既要“海纳百川”又要“杂而不乱”,需要具有一定的灵活性和扩展性。
通讯方面,传统银行以及与外联单位间使用的协议和中间件主要是TCP、IBM MQ、CICS、Tuxedo、SNA等。由于银行间大部分的数据是流转于金融城域网的(各运营商的金融专线),所以对于通讯安全这块儿有了一定的保障。
其中TCP就是简单的建立一个Socket,点对点的连接互发消息;IBM MQ更是央妈推的产品,所以大家也都在用;剩下的几个用的相对较少了,我当时就一直在使用Tuxedo,不过也就停留在建好通道消息能通的基础使用程度,维护上实在不敢造次,更别提改造和开发了。
随着技术框架的发展和革新,一些开源的中间件Rabbit MQ、Kafka等也渐渐的在对老的体系进行着替换,有些技术服务商的成熟产品比如金证的kcxp、先进数通的Starring平台等等也有着不俗的表现。
报文方面,主要使用的是固定长度格式、分隔符格式、8583格式、XML格式等等。
固定长度格式报文,优点在于简单,打包解包速度快;缺点是可能会浪费存储空间,一般用于重视处理效率的场景。
分隔符格式报文,节约存储空间,但是打包解包速度稍慢于固定长度格式,还要注意双字节引起的解包错位问题,而且还要考虑分隔符转义,一般用于字符取值空间比较单纯,数据域长度差异性比较大的场景。
8583格式报文,银联卡交易报文接口标准,和银联打交道离不开这个。8583报文的TLV模式可以扩展成通用交易报文格式来使用,其中T=Tag,L=Lenth,V=Value,其实就是数据字典和固定长度格式的结合体。我觉得这是一种最直观的最原始的标记报文,每个Tag域都代表了不同的业务含义,按照业务流程的需要,对相关域信息进行解析即可得到需要的业务内容。
XML格式报文,现在十分普遍了,最近几年新的项目和接口大多会使用XML报文,这种报文可以附带前面几种报文格式所不能包含的大量完备信息,具有自描述性、人可读性。但它的缺点也是比较明显的,就是“体积”偏大,打包解包速度慢,同时编码难度和繁复度也比以上几种格式都要大一些。
最后再说一种,JSON报文,准确的说应该是key-value格式报文,这种报文体量小、结构简单清晰、便于解析,尤其是在各技术框架的大力支持下,越来越多的系统间交互都采用了这种格式进行数据传输。特别是在webservice、restful接口以及微服务调用的“风靡”下,大有可为。
业务调度功能
业务调度,或者说是交易路由更形象一些。
核心思想就是根据接收到的报文中交易码以及其他业务信息,判断需要调用后台的哪一个交易进行处理。
交易路由的控制可以是多种形式的,最省事儿的甚至可以将处理逻辑写到代码里,也可以通过配置文件、数据库表等方式进行。交易路由控制中应尽量少的掺入业务逻辑的内容,保证简洁、可复用的完成一个“路由”的功能。
在进行业务调度的同时,由于前端接收到的报文信息以及格式是五花八门的,前置系统在这儿还会将接收到的报文内容进行整理和转换。将后台处理需要的信息进行筛选和整理,并按照内部约定好的报文格式进行转换输出。
这样的模式,前置系统相当于一个水龙头,进水管可以是各种管道来水,而出水口的大小、孔径都规整成了一种规格。前置渠道和后台只能考虑将N种外部报文转化成一种内部报文即可,避免了多对多转换的组合复杂度。
前置交易设计基本原则
交易的表现形式千千万万种,体现在后台的处理上除了各业务流程的特殊约定外,无外乎就落在“增删改查”四个字上。
结合上面对前置系统的功能理解,我们针对这四处数据操作来聊一聊。
增
首先考虑的是增的内容,前置系统的新增操作,主要是将接收到的数据进行落地,所以新增的内容主要包括消息的通讯部分、交易明细部分以及流程标识状态等字段内容。
通讯部分内容,主要是消息头中的消息ID、版本信息、渠道类型等等内容。
交易明细内容,主要是看业务形式了,一般都会包括交易时间、本方信息、对手方信息、业务信息等等。
流程标识状态,由于前置系统本身主要是渠道和交易路由的功能作用,所以对每一笔交易我们既要记录接收进来的信息,还要记录在整个业务周期内这笔数据的状态变化。从接收进来时的“初始化”、“待处理”,到分发给后台处理时的“处理中”、“已发送”,再到接收到返回信息后的“交易成功/失败”、“已接收”等等状态信息,都需要在前置系统中记录。
再者考虑的是增的地方,包括使用的数据库是Oracle、DB2还是MySQL,主要是考虑对金额字段总长度和保留位数的处理、某些库对字符集是否要特殊处理、时间格式是否要进行转换等等。
最后考虑的是增的方式,一是接数据是文件还是消息的,对文件的解析落库还是直接处理文件数据落库,消息的要考虑是哪种模式的报文以便采用对应的解析方式进行数据落地;再者是针对数据量比较大时,对系统的处理效率又有要求的情况下,就要考虑落库的方式是sql语句的insert到表里,还是import进行数据导入。在落库的过程还要结合业务的整体性和系统效率,设定每个事务提交多少条数据。
删
金融系统里大多数情况下不会对数据进行真正的删除,也就是我们说的物理删除。
所谓删的动作,在前置系统中,更多的是将数据状态修改为“注销”、“失效”等。
当然还是有些业务场景需要真正删除数据的,特别是一些业务处理流程中的中间表,还有就是一些业务允许重做多次的情况下,一般在业务进行到这一步时,都会将当天相关的数据先进行删除操作,再将新的数据落地,以避免数据的混乱导致处理错误。
改
前置系统中改的功能,我觉得大都体现在对流程的异常处理上。客户从前端发起的交易重发是业务的异常处理;运维人员在后台管理柜台上选择的交易状态修改也可以看作是业务流程的异常处理;对于由于网络拥塞等因素造成的数据丢失,相关的业务流程无法继续运转下去了,我们同样能技术层面可以将相关的数据状态改成一个结束的终态。
我们还是从几个方面来聊一聊改这个行为。
首先是改这个动作的发起方。客户算是发起方之一,客户的修改动作更多的是对业务数据的修改,比如刚做了一笔申购交易,状态已经是提交成功了,现在又发起了一笔撤单,如果前置系统里记录了这一单的状态,就需要找到原交易成功的交易记录,将其状态撤销掉。技术人员和业务人员也是发起方之一,通过后台管理柜面,对交易记录进行修改,这种修改更多的就是对业务流程的控制了,将无法完成的交易修改为终态,对错误的业务数据进行修改以便后续流程可以进行下去。
再者是改的内容,哪些内容是可以修改的,这其实是一个权限问题,比如金额方面的内容,对金额修改一定是由一个单独的交易流程中进行的,存款、撤单等等交易都对应了金额字段的增减,这种修改不可能也不可以由运维人员在后台管理界面上就执行了。再比如一些交易状态的修改,特别是一些异步交易的状态,由状态A能修改为状态B,能不能修改成状态CDEF...这都是和业务流程息息相关的,不能说是修改了状态成“交易完成”了,结果客户端又没办法收到正常正确的信息。
在设计和编写修改类交易时,我们更多的是要注意到修改的动作是否会影响到原交易的进行。尤其是正在进行中,非终态的交易数据,是否在修改时有“锁”或者“互斥”的机制。
查
对于有一定体量的金融系统,前置系统所承受的最大的数据压力一定是查询功能。
由于对客户需要提供全方位多样式的服务,导致查询后台数据的条件也是各种组合各种形式。对于某些重要的业务数据表(比如客户信息表、交易明细表等等)压力巨大,同时由于这些数据还在频繁的进行着新增、修改等操作,导致查询交易设计不好,有可能直接影响正常的交易。
目前对查询交易设计我觉得可以分成事前分析和事后优化两部分进行。
事前分析主要集中以下几个方面:
- 根据以往的业务经验,对数据量有一定的预估,采用现有类似的查询模式进行复用。
- 根据设定的查询条件,做好表索引的规划。
- 压力测试很重要,压力测试很重要,压力测试很重要。
事后优化的手段就各显神通了,业务不同,数据量不同,可以操作的空间也不尽相同,主要体现在以下几个方面:
- 对数据库表索引的优化。
- 对交易流程中耗时瓶颈的优化。
- 分库分表,减少单张表的数据量。
- 复制出一个查询库,与主数据库间做数据同步,将主业务与查询业务分别处理。
- 对整批数据采用export导出,以文件等形式进行传输。
当然现在还有各种把数据往内存里放的,甚至还会将一些固定数据暂存到客户端本地,以方便快速查询并减少服务器的压力。
观其本质,在设计和开发查询交易时,除开数据的准确性之外,最需要考虑的就是效率问题。基于效率这个基本上,利用现有的技术架构,根据业务的频度进行数据分离,从而达到高效的处理查询业务。
随便聊点儿
整体看下来,大家是不是有一种莫名的熟悉感。
其实前置系统的演变和功能划分,很像是现在被讲来讲去的微服务概念。
伴随着业务区域的划分以及系统边界的设定,将更多的渠道工作交给前置来做,让核心系统更专注于会计相关事务的处理。
同时在前置系统内部,又可以依据业务线的不同和技术框架的不同,对前置系统进行拆份、集群化、微服务化。
但万变不离其宗,不管中间穿透了几层系统,使用的多少中间件,走过了多少队列通道,我们都要用前置系统的本质作用来衡量这些动作的意义。
作为技术人员,我依然倡导的是要以不变应万变,抽丝剥茧出适合自己的精准模型来设计交易、设计系统。
好了,今天就聊到这里~
网友评论