
高并多进程在银行业务处理中的应用方案.doc
21页随着计算机在银行业中的深入应用,许多银行业务,尤其核心业务的开展都以数据库为依托数据库技术与银行业发展的联系越来越密切目前大多数银行采用C/S系统架构,后端数据库服务器响应前端发起的各种交易,前端交易的信息最终以数据形式集中存放在后台数据库中后台数据库服务器是银行日常联机交易的核心,其稳定可靠的运行、迅速的响应速度、较高的吞吐量以及24小时不间断运行,是为客户提供优质服务的前提,是银行业务正常发展的保证,也是提高自身竞争力的基础由于业务需要,经常要对数据库关键表进行全表更新处理,如银行年度结息、批量扣收卡年费等,还要在效率、可靠性、并发及硬件资源之间权衡在保证可靠性的前提下,充分利用硬件资源,尽可能不影响其他业务的正常运行,即最大化并发、高效率地完成更新操作这就需要软件开发人员熟悉银行业务,充分应用数据库技术及编程技巧,开发出优质高效的应用软件,保证业务稳定持续发展 本文结合常见实例,分析探讨在银行联机事务中批量业务的不同实现方法比较不同方法的利弊,从而确定适合联机事务环境批量处理的最佳方案,并对重点实施给出代码一、实例及要求 某银行批量扣收银行卡年费业务,银行卡信息约有1000万条记录(下称“card_info表”)。
1.对card_info表记录的处理 (1)对符合扣收条件且余额充足的记录进行扣收,将扣收成功的信息写入扣收清单card_succ表中,扣收失败的信息写入欠收清单card_fail表中,用于以后统计,同时更新card_info表信息 (2)不符合扣收条件的不做处理 (3)符合扣收条件但余额不足的写入欠收清单card_fail表中,同时更新card_info表 (4)符合扣收条件的记录占80%以上 假设实例所用的应用服务器为HP-V260小型机,该机配置有8个CPU,8G内存,操作系统为HP Unix,数据库采用目前许多大行业广泛应用的Informix Dynamic Server Version 9.30.FC1 2.要求 在扣收处理过程中不停业,即系统不停止对其他联机交易业务的处理二、实例分析 1.扣收时间的确定 首先,要确定批量扣收处理是在白天还是在夜间进行 随着银行业的竞争日益激烈,各银行为吸引并方便客户,提供了各种服务渠道以满足客户的不同需求,有正常营业时间的网点柜面交易,还有ATM、POS、网上银行、银行、银行等24小时不间断营业的自助服务 由于白天为银行营业高峰时间,计算机数据库系统为典型的联机事务处理,要求系统有较高的吞吐率及快速的响应时间。
银行卡表为关键表,日间访问频繁,如对其进行大量的更新操作,势必影响其他业务的正常运行毫无疑问,应当选择交易量较少的夜间进行批量扣收处理 2.单进程与多进程的确定 要确定启用单进程还是多进程进行批量扣收处理为了提高运行性能,应采用多进程并发处理,其原因有以下几点 (1)时间因素银行后台系统在夜间一项重要的工作是日终结账为保证账务的完整一致,其他批处理一般在日结前或日结后进行,即与日终结账串行处理一般情况下,日终结账会耗时数小时,在保证日结正常处理结束后,用于其他批处理的时间将会有限所以有限的扣收处理时间是一个重要因素 (2)系统资源因素夜间客户自助发起的交易较少,在正常批处理完成后,CPU的空闲率通常在98%以上,内存也大量闲置如果采用单进程对实例进行批量处理,必然存在着主机资源闲置和应用程序执行缓慢的状况为此应采用多进程并发模式进行批量扣收处理,充分利用系统资源,提高程序的执行速度,减少运行时间 (3)应用处理对象因素如果应用需要数据库系统进行大量的数据库操作,如批量数据装载、海量数据的查询统计等,其主要瓶颈为I/O,启用多进程无助于性能改善相反,如果应用存在大量计算处理,则采用多个进程并行处理可提高性能。
本例中对每条记录的处理,均存在条件判断、余额积数计算、校验码运算等大量计算,故应采用多进程并行处理,以提高性能 (4)开发环境因素本实例采用HP Unix操作系统该系统是一个多用户、多任务、交互式的分时操作系统,其开发环境支持子进程的创建,而且实现较为容易 3.进程个数的确定 确定同时启动的子进程数目启动多少个子进程,依赖于所运行主机的物理CPU个数、内存大小、系统已有负载及进程做什么类型的操作等因素 如果存在主机系统负载已很重、物理CPU少、内存小等情况,启动过多的进程将会造成进程间较多的上下文切换、内存的换出换进,无助于性能的改善,反而降低性能反之,可启用相对多的进程以提高性能 对于本例,由于系统有数个物理CPU,同时夜间业务较少,系统的负载小,闲置内存多,故确定同时启动子进程数为物理CPU数减1 4.启动进程次数的确定 即确定进程的生命周期进程由操作系统负责管理和调度,创建一个子进程较为耗时,代价较大,如果频繁创建、释放子进程会造成系统性能的下降在本实例中,由于采用小事务,事务的数目远远大于子进程个数,如果采用每个子进程处理单个事务,势必造成频繁创建、释放子进程为解决这一问题,我们采用创建子进程个数不变,每个子进程循环处理分配给其上的多个小事务,即最大化每个子进程的生命周期,以提高性能。
5.并发控制 开发数据库应用软件,首先应该保证数据的可靠性、容错性及一致性,其他因素,诸如性能等,在与其产生冲突时,必须要保证前者 采用多进程,事务间必定存在着并发,为保证数据的可靠性与一致性,就要使用有故障恢复功能的数据库及事务事务的“原子性”保证了每个事务中的更新操作要么全部成功,要么全部回滚,避免在更新操作中因锁碰撞或其他异常情况,造成数据的不一致Informix使用锁来控制并发,实现事务之间的隔离采用锁进行并发控制,应考虑并确定锁的以下几个特性 (1)锁粒度的确定 锁粒度是指被封锁的对象范围大小,从小到大分为五级:键级、行级、页级、表级、数据库级,并发性依次降低,其中对整个数据库上锁使得并发性降为零提高并发性是开发数据库应用软件应遵循的原则,尤其是银行应用软件保证客户业务的顺畅运行,是银行业向客户的基本承诺 针对本实例,为提高各进程间并发操作,最大化降低扣收处理对其他业务的影响,应选择页锁或行锁页锁封锁了整个页,该级锁定提供了一次封锁若干条记录的有效手段,但其他用户就不能访问已封锁页面上的所有数据了页级锁降低了并发或数据对其他用户的可用性,但按表的物理顺序处理时,页级锁能用很少的锁完成对大量记录的变更。
行锁在任意时刻只封锁一条记录,它提供了最高的并发,但当封锁记录数目很大时,有可能耗尽锁资源,且锁管理的额外开销也会变得十分显著 权衡页锁与行锁的利弊,考虑锁定要持续到事务结束才能解除,为尽量减少扣收处理期间对客户交易的影响,即保证最大并发性,本实例使用行级锁同时为有效减少锁管理的额外开销,采用小事务(建议将数据库锁参数的配置尽量调大,Informix每个锁仅占44字节的内存空间,锁的物理资源开销很小,由于锁资源不够而引起事务回滚是得不偿失的) (2)事务大小的确定 事务的大小是很重要的,它直接影响性能的优劣,同时也是较难精确确定的,依赖于用户的不同需求及所运行的环境一般来说,太大的事务性能较差,原因如下 ①事务越大执行时间越长,被其阻塞的事务等待时间可能越长,并发事务锁碰撞错误返回的可能性越大;需要等待其他事务释放某个锁的可能性也越大,造成锁溢出的可能性也越大 ②Informix的数据库日志为所有事务所共享,如果多个事务存在大量更新操作,日志将被迅速填充,大的事务在结束前将长时间地占有使用过的日志,不能释放,从而引起长事务的可能性增大所以太大的事务性能较差,一般情况下,需要将大的事务划分为较小的事务,以提高性能。
当然也不能把事务划分得太小,太小的事务无助于性能的提高当事务太小,如将实例的每个事务按单条或很少的记录处理,会造成频繁的I/O及其他重复开销这是因为启动成本高,运行成本低数据库系统中最昂贵的操作是磁盘I/O,数据库服务器进行大块磁盘操作比只处理数条记录要快,因为磁盘开始一个读操作是很耗时的,但是一旦开始,磁盘就能高速地传输数据 因此,本实例划分事务大少的原则是,在与夜间交易发生碰撞冲突概率很低的情况下使用适当小的事务 6.表的访问方式 即采用顺序扫描还是索引扫描方式访问表使用索引,根本目的就是为了提高查询效率索引扫描在以下情况下将会提高查询效率:大表的查询,且满足查询条件的记录数占全表的比例不超过30%,查询的数据仅为索引数据等相反,对记录数很小的表,或从一个表选择几乎所有的行且包含有非索引字段,使用索引反而会降低效率这是因为数据库服务器将不得不反复地参照索引来读取数据尤其对于大表而言是致命的,因为I/O是很昂贵的操作从一个磁道连续读64KB的数据,很可能比从该磁道两次读取512字节数据所花费的时间还短因此,对读取同等数据量的数据,顺序扫描是最经济的 在本实例中,由于扣收处理的表为大表,且满足处理条件的记录占绝大多数,采用顺序扫描,将最小化I/O操作,提高性能。
各子进程均采用顺序扫描的方式,每个子进程处理的数据按物理存储空间严格区分开,这样保证了各子进程间事务的完全隔离子进程间碰撞的概率降为零,极大地方便了各子进程间的并发控制,提高了整体性能同时采用顺序扫描,还可用到数据库服务器的预读功能,即在顺序扫描期间提前将数据页从磁盘读入内存,可进一步提高性能子进程、事务及相应记录如图1所示图中记录顺序为物理顺序;k为进程个数,n为每个进程处理的事务个数,m为每个事务处理的记录数 从图1中可清楚地看到每个事务处理的记录从物理上严格分开,虽然每个进程的第一个事务与其前一个进程的最后一个事务所处理的记录可能存在于同一个磁盘页面上,但由于每个进程顺序处理其上的多个事务,从而使每个进程的第一个事务与前一进程的最后一个事务存在着时间差,故此实现了每个事务间的完全隔离 7.其他方面 (1)建立日志跟踪机制 事务的并发控制是本例的难点,也是保证数据一致性、可靠性的关键本例扣收批处理的各事务由于从数据物理空间上完全隔离,从而保证了批处理事务间无碰撞,简化了事务的并发控制,但仍存在着扣收批处理子进程的事务与夜间客户交易事务的并发,虽然碰撞概率很小,但仍存在可能为了对子进程处理结果进行有效跟踪及控制,我们将每个子进程的所有事务处理结果记录下来,为操作人员提供了实时监控处理结果的有效手段,实现友好的人机接口,同时方便开发人员对出错信息进行分析及优化,也为出错(如锁碰撞)后的断点再继提供依据。
实现这一功能,需要用到多进程间的通信,其方法有多种,如共享内存、共享文件、信号量、消息队列、数据库表等方法本例中我们采用数据库表的方法,该方法容易实现,安全可靠,同时以数据库表的形式可长期存放,方便日后查询、分析 (2)父进程对子进程的控制 由于进程是由操作系统管理及调度,当子进程出现异常,如僵死时,父进程需要迅速捕获该信息,同时中止并清理重置子进程为此,采用父进程创建子进程后,将子进程号记录下来,父进程在等待子进程正常结束的时候,定时扫描子进程是否正常三、实例实施 总结上节分析,我们得出对本例采用:多进程、小事务、顺序扫描银行卡表 在具体实施中,为使得程序流程清楚,易于维护,我们采用一些编程方面的技巧以下对该实例的重点及实施难点做详细的论述 1.采用公共变量定义参数 为使程序易于调试、维护及调优,并具有通用性,我们将一些关键参数定义为全局变量,并为日后移植打下基础关键参数包括子进程个数、事务个数、每个事务处理的记录条数等 #define PROCESS_。












