当前位置: 首页 > 后端技术 > PHP

业务锁定应用程序

时间:2023-03-29 17:54:21 PHP

锁业务场景是一个补偿工单(底层第二个人发起)。当金额大于一定值时,会对这个工单进行层层审批(风控)。首先,YY一个审批流程“TL审批”-->“主管审批”--->“财务审批”。这里会有3种权限,“初审权限”、“复审权限”和“终审权限”。2.对应的TL创建审批任务,在主管界面可以看到对应的审批任务,主管可以点击Pass或Reject实现1.查询任务,判断当前角色是否有操作该任务的权限,等待任务完成。系列验证2.驱动状态机更新工单状态3.完成任务异常场景场景1操作:主管疯狂点击pass按钮3次(前提是点击一次按钮不会变灰,即使是灰色的,也可以通过模拟请求来实现)异常情况:三个点击线程都运行1,然后线程1驱动状态机(pass+当前状态:pendingTLapproval)和结果是要supervisor审核通过,然后线程2驱动状态机(pass+当前状态:等待supervisor审核)结果等待财务审核,然后线程3运行驱动状态机(passed+当前状态:Waitingforsupervisor'sapproval)等待财务审批),结果是账户支付成功(不考虑多任务完成时会出现的异常)异常分析:在这种场景下,只要角色有“初检”ionauthority”,可以通过漏洞直接对订单进行审计和记账解决方法:细化状态机中的各个审计操作1.查询任务,查询当前操作类型对应的任务(TLApprovalORSupervisorApprovalORFinancialApproval)---这不仅仅是一个“pass”操作,而是判断当前角色是否有对应的操作权限2.根据当前操作类型+当前状态驱动状态机3.查询任务前完成任务添加全局lock全局锁定此工作订单(更优雅)。场景二:一个角色同时拥有一审权限和二审权限。当他打开一个工单时,他需要进行初检,但其他主管已经执行了初检的动作,并更新了一些信息。因为角色页面没有刷新,无法获取更新信息,然后点击pass按钮异常情况:点击pass按钮相当于二试,会导致角色无法获取最新信息,导致错误判断方案:在场景一加全局锁的前提下,可以给页面传递一个工单modifyTime,判断modifyTime在全局锁中是否一致。如果不一致,说明工单更新了,可以给用户一个相应的提醒别人,业务中整个状态机的流向是确定的,所以为了保证状态流向正确,当更新数据库状态,需要在状态上带上乐观锁UPDATEXXXSETstatus=XXXWHEREid=XXXANDfrom_status=XXX如果使用全局锁,则需要为每个工单添加对应的全局锁