发明内容
本公开实施例提供一种故障恢复方法、装置、电子设备及计算机可读存储介质。
第一方面,本公开实施例中提供了一种故障恢复方法。
具体的,所述故障恢复方法,包括:
响应于故障节点的故障恢复事件,获取所述故障节点的最近一次快照数据;其中,所述快照数据至少包括最近一次快照时刻所述故障节点的状态、输入输出信息;
根据所述快照数据恢复所述故障节点最近一次快照时刻的状态,并按照所述故障节点故障之前的方式对输入数据进行处理后得到处理结果;其中,所述输入数据根据所述输入输出信息获得,且为所述故障节点在最近一次快照之后、故障之前所接收到的数据;
输出所述处理结果中的目标数据;其中,所述目标数据为所述故障节点的下游节点未获得过的数据。
进一步地,根据所述快照数据恢复所述故障节点最近一次快照时刻的状态,并按照所述故障节点故障之前的方式对输入数据进行处理后得到处理结果之前,还包括:
根据所述快照数据中的输入输出信息确定最近一次快照时刻所述故障节点从上游节点已获得的未处理数据的第一数据标识;其中,所述未处理数据的数据标识是由所述上游节点按照所述未处理数据的产出顺序分配的;
根据所述未处理数据的第一数据标识从所述上游节点的输出缓存中获得所述输入数据;其中,所述输入数据包括所述未处理数据以及所述上游节点在所述未处理数据之后产生的数据。
进一步地,按照所述故障节点故障之前的方式对输入数据进行处理后得到处理结果,包括:
根据所述输入数据的时间戳的顺序对所述输入数据进行处理,并得到处理结果;其中,所述输入数据的时间戳由产生所述输入数据的上游节点按照产生时间分配的,且对所述输入数据进行处理时所采用的处理机制与所述故障节点故障之前所采用的处理机制一致。
进一步地,按照所述故障节点故障之前的方式对输入数据进行处理后得到处理结果之后,所述方法还包括:
按照所述处理结果产生的顺序以及所述输入输出信息为所述处理结果分配具有顺序关系的第二数据标识。
进一步地,输出所述处理结果中的目标数据,包括:
确定所述故障节点失效前输出至下游节点的输出数据的第三数据标识;
将所述第二数据标识大于所述第三数据标识的所述处理结果作为目标数据输出至所述下游节点。
进一步地,在所述故障节点及所述故障节点的下游节点均出现故障时,按照所述故障节点故障之前的方式对输入数据进行处理后得到处理结果之后,所述方法还包括:
根据所述输入输出信息为所述处理结果分配第四数据标识以及时间戳;其中,所述第四数据标识以及时间戳的分配方式与所述故障节点故障之前一致。
进一步地,获取所述故障节点的最近一次快照数据,包括:
获取所述故障节点以及所述故障节点所影响到的所有下游节点的最近一次快照数据。
进一步地,获取所述故障节点的最近一次快照数据之后,还包括:
从所述故障节点的上游节点的输出缓存中获得所述输入数据;其中,从所述输出缓存中获得的所述输入数据为最近一次快照之后所述上游节点产生的输出数据。
进一步地,输出所述处理结果中的目标数据之后,还包括
根据所述最近一次快照数据依次恢复所述故障节点所影响到的所有下游节点,并对从各自的上游节点所接收到的输入数据依次进行处理后,输出至各自的下游节点。
第二方面,本公开实施例中提供了一种故障恢复装置。
具体的,所述故障恢复装置,包括:
第一获取模块,被配置为响应于故障节点的故障恢复事件,获取所述故障节点的最近一次快照数据;其中,所述快照数据至少包括最近一次快照时刻所述故障节点的状态、输入输出信息;
第一处理模块,被配置为根据所述快照数据恢复所述故障节点最近一次快照时刻的状态,并按照所述故障节点故障之前的方式对输入数据进行处理后得到处理结果;其中,所述输入数据根据所述输入输出信息获得,且为所述故障节点在最近一次快照之后、故障之前所接收到的数据;
输出模块,被配置为输出所述处理结果中的目标数据;其中,所述目标数据为所述故障节点的下游节点未获得过的数据。
进一步地,所述装置还包括:
确定模块,被配置为根据所述快照数据中的输入输出信息确定最近一次快照时刻所述故障节点从上游节点已获得的未处理数据的第一数据标识;其中,所述未处理数据的数据标识是由所述上游节点按照所述未处理数据的产出顺序分配的;
第二获取模块,被配置为根据所述未处理数据的第一数据标识从所述上游节点的输出缓存中获得所述输入数据;其中,所述输入数据包括所述未处理数据以及所述上游节点在所述未处理数据之后产生的数据。
进一步地,所述第一处理模块包括:
处理子模块,被配置为根据所述输入数据的时间戳的顺序对所述输入数据进行处理,并得到处理结果;其中,所述输入数据的时间戳由产生所述输入数据的上游节点按照产生时间分配的,且对所述输入数据进行处理时所采用的处理机制与所述故障节点故障之前所采用的处理机制一致。
进一步地,所述装置还包括:
第一分配模块,被配置为按照所述处理结果产生的顺序以及所述输入输出信息为所述处理结果分配具有顺序关系的第二数据标识。
进一步地,所述输出模块,包括:
确定子模块,被配置为确定所述故障节点失效前输出至下游节点的输出数据的第三数据标识;
输出子模块,被配置为将所述第二数据标识大于所述第三数据标识的所述处理结果作为目标数据输出至所述下游节点。
进一步地,所述装置还包括:
第二分配模块,被配置为根据所述输入输出信息为所述处理结果分配第四数据标识以及时间戳;其中,所述第四数据标识以及时间戳的分配方式与所述故障节点故障之前一致。
进一步地,所述第一获取模块,包括:
获取子模块,被配置为获取所述故障节点以及所述故障节点所影响到的所有下游节点的最近一次快照数据。
进一步地,所述装置还包括:
第三获取模块,被配置为从所述故障节点的上游节点的输出缓存中获得所述输入数据;其中,从所述输出缓存中获得的所述输入数据为最近一次快照之后所述上游节点产生的输出数据。
进一步地,所述装置还包括
第二处理模块,被配置为根据所述最近一次快照数据依次恢复所述故障节点所影响到的所有下游节点,并对从各自的上游节点所接收到的输入数据依次进行处理后,输出至各自的下游节点。
所述功能可以通过硬件实现,也可以通过硬件执行相应的软件实现。所述硬件或软件包括一个或多个与上述功能相对应的模块。
在一个可能的设计中,故障恢复装置的结构中包括存储器和处理器,所述存储器用于存储一条或多条支持故障恢复装置执行上述第一方面中故障恢复方法的计算机指令,所述处理器被配置为用于执行所述存储器中存储的计算机指令。所述故障恢复装置还可以包括通信接口,用于故障恢复装置与其他设备或通信网络通信。
第三方面,本公开实施例提供了一种电子设备,包括存储器和处理器;其中,所述存储器用于存储一条或多条计算机指令,其中,所述一条或多条计算机指令被所述处理器执行以实现第一方面所述的方法步骤。
第四方面,本公开实施例提供了一种计算机可读存储介质,用于存储故障恢复装置所用的计算机指令,其包含用于执行上述第一方面中故障恢复方法所涉及的计算机指令。
本公开实施例提供的技术方案可以包括以下有益效果:
本公开实施例在流计算应用中故障节点失效之后,通过获取故障节点最近一次快照数据以及最近一次快照数据之后的输入数据,进而根据快照数据恢复故障节点失效之前的状态,并按照失效之前的方式处理输入数据,进而输出处理结果中的目标数据。通过本公开实施例,可以在流计算应用中的任一节点失效后,通过快照数据恢复后的故障节点能够获取上游节点在快照之后产生的数据,并采用同样的处理方式进行处理后,将下游节点未获得过的数据输出给下游节点,既能够保证恢复后的故障节点与失效前的处理数据以及处理结果一致,并且又能够保证输出至下游节点的数据不会发生重复,也即能够保证故障节点的恢复不会引起下游节点的内部状态和/或输出数据与故障节点失效前不一致,因此通过本公开实施例能够实现故障恢复前后数据一致,并且能够实现失效节点的单点恢复,而无需进行全局回滚,进而能够保证故障恢复的实时性。
应当理解的是,以上的一般描述和后文的细节描述仅是示例性和解释性的,并不能限制本公开。
具体实施方式
下文中,将参考附图详细描述本公开的示例性实施方式,以使本领域技术人员可容易地实现它们。此外,为了清楚起见,在附图中省略了与描述示例性实施方式无关的部分。
在本公开中,应理解,诸如“包括”或“具有”等的术语旨在指示本说明书中所公开的特征、数字、步骤、行为、部件、部分或其组合的存在,并且不欲排除一个或多个其他特征、数字、步骤、行为、部件、部分或其组合存在或被添加的可能性。
另外还需要说明的是,在不冲突的情况下,本公开中的实施例及实施例中的特征可以相互组合。下面将参考附图并结合实施例来详细说明本公开。
相关技术中,Apache Flink是一个较为常用的分布式大数据处理引擎,其可对有限数据流和无限数据流进行有状态计算。Apache Flink的容错机制是基于分布式快照实现的,这些快照会保存流处理作业的状态。大体流程如下:1)Apache Flink的JobManage会周期性的向source operator(源节点)注入barrier。2)当source operator收到barrier后,立刻做一个快照,即记住当前的offset信息,然后将此barrier广播到所有的下游节点。3)当一个下游节点接到它所有的输入端的barrier后,立刻做一个快照,即记录当前这个下游节点的状态;然后将这个barrier广播到下游节点。4)直到最后的节点完成计算,才算一个完整的检查点完成。如果流计算节点发生失效的情况,系统可以从最近的一个检查点进行恢复,也即根据最近一次快照数据进行恢复。所有的节点恢复到检查点记录的状态,然后从源节点重新拉数据进行处理。
但是Apache Flink具有以下缺点:
1)无法保证故障恢复前后计算结果的一致性,因为数据到达节点的处理的顺序和故障前是不一样的,所以基于顺序+状态的计算,计算结果必然不同。
2)单点故障需要全局回滚,代价太高,故障恢复时间长。
Apache Spark是一个基于内存计算的开源的集群计算系统。Spark Streaming提供了checkpoint机制。它的Job Generator会定期生成每个batch对应的任务,同时将其检查点信息存储到可靠的外部存储,例如:硬盘。当任务完成后则将其在外部存储中的检查点信息删除。如果处理过程中应用失效,重新启动后可以从外部存储恢复未完成的任务,同时失效到恢复这段时间内进入系统的新数据会划分到新batch中。
但是Apache Spark具有如下缺点:
1)无法保证故障恢复前后计算结果的一致性,因为失效到恢复这段时间内进入系统的数据将会被划分到新的batch,这和未失效情况下batch的划分策略肯定是不一样的,所以计算结果必然不同。
2)单点故障需要整个batch重新计算,故障恢复时间长。
因此,本公开提出了一种故障恢复方法,能够解决实时数据计算产品故障恢复前后计算结果不一致和单点故障恢复时间长的问题。
图1示出根据本公开一实施方式的故障恢复方法的流程图。如图1所示,所述故障恢复方法包括以下步骤S101-S103:
在步骤S101中,响应于故障节点的故障恢复事件,获取所述故障节点的最近一次快照数据;其中,所述快照数据至少包括所述故障节点最近一次快照时的状态、输入输出信息;
在步骤S102中,根据所述快照数据恢复所述故障节点最近一次快照时状态,并按照所述故障节点故障之前的方式对输入数据进行处理后得到处理结果;其中,所述输入数据根据所述输入输出信息获得,且为所述故障节点在最近一次快照之后、故障之前所接收到的数据;
在步骤S103中,输出所述处理结果中的目标数据;其中,所述目标数据为所述故障节点的下游节点未获得过的数据。
流计算系统实时获取来自不同数据源的海量数据,经过实时分析处理,获得有价值的信息。流计算系统中的各个计算节点按照有向无环图的方式构成,上游节点的计算结果输出给下游节点,下游节点根据从上游节点获得的数据进行计算处理,并进一步输出给另一下游节点。计算机节点可以为流计算系统中执行计算逻辑的最小单元。本实施例中提出的故障恢复方法适用于任意分布式流计算系统。故障节点为流计算系统中的任一计算节点,在流计算系统中的任一节点出现故障时,可以根据本公开实施例提出的上述方法进行单点恢复。
本实施例中,流计算系统在运行过程中可为每个节点开辟一个input buffer(输入缓存)来接收上游节点产出的数据,也为每个节点开辟一个output buffer(输出缓存)来存放发往下游节点的数据。节点针对接收到的输入数据进行相应处理后产生输出数据,输出数据可以缓存在为该节点分配的输出缓存中;该节点还将输出数据输出给对应的下游节点,并作为下游节点的输入数据缓存输入缓存中。
在一实施例中,节点为每个处理产生的数据分配数据标识(例如顺序号)并确保严格递增,然后写入输出缓存;对输出缓存中中新写入的数据分配时间戳,为提高效率,可以对连续的一批数据分配同一个时间戳。
在一实施例中,节点还将分配的数据标识和时间戳的映射关系写到外部存储器,以便备份和持久化。节点异步地将上述已分配好数据标识和时间戳的数据不断发往下游节点,相同时间戳的数据可以整体打包发往下游节点。
在一实施例中,下游节点对接收到的来自所有不同上游节点的未处理数据统一按照数据自身的时间顺序依次进行处理,这里要求节点的处理逻辑是确定性的,即对相同的输入数据,每次都能产出相同的结果。
在一些实施例中,主节点定期给流计算系统中的源节点注入barrier(栅栏),并采用分布式快照的方式进行数据备份,barrier被注入到数据流中和其他数据一样作为数据流的一部分流动。源节点在接收到barrier后,立刻做一个快照,也即记录源节点当前的offset信息(offset信息包括上一次快照到本次快照所产生的新的变化信息),之后源节点将该barrier广播到下游节点,下游节点接收到barrier后,执行与源节点同样的操作,直至该源节点所在的有向无环图中的最后一个节点快照完成,这样就形成了一次完整的快照。本实施例中,不仅备份快照时刻节点的状态,同时还记录快照时刻节点的输入输出信息。在一实施例中,节点的数输入输出信息可以包括快照时刻在输入缓存和输出缓存中的数据信息,例如输入缓存和输出缓存中数据的数据标识和时间戳。
在故障节点故障后,可以根据之前的快照数据获取该故障了的故障节点的最近一次快照数据,最近一次快照数据可以包括最近一次快照时刻故障节点的状态、输入输出信息等。流计算系统可以启动一个替代节点,并将该替代节点恢复成最近一次快照时刻时的状态,同时该替代节点采用故障节点故障前的处理机制处理输入数据。此处的输入数据为最近一次快照时刻故障节点的上游节点输出给故障节点,且未被故障节点所处理的数据,可以根据最近一次快照数据中的输入输出信息获得。
故障节点的替代节点不但采用与故障节点相同的处理机制(例如计算方式),还采用相同的时间顺序处理输入数据,因此得到的处理结果与故障节点故障前的处理结果一致。也即故障节点故障之前的方式不但包括故障节点故障之前所采用的处理机制(例如计算方式),还包括对多个相同输入数据的处理顺序等。
处理结果中的目标数据为未被故障节点输出给过下游节点的数据,也即下游节点未从故障前的故障节点获得过的数据。由于故障节点在最近一次快照后以及故障前可能还进行过数据处理,因此处理结果也可能输出给了下游节点,因此本实施例中需要确定替代节点得到的处理结果中哪些数据已经被输出至下游节点了,避免重复输出至下游节点,而引起下游节点内部状态及输出数据与故障前不一致,导致整个系统无法恢复到与故障前完全一致的状态。
本公开实施例在流计算应用中故障节点失效之后,通过获取故障节点最近一次快照数据以及最近一次快照数据之后的输入数据,进而根据快照数据恢复故障节点失效之前的状态,并按照失效之前的方式处理输入数据,进而输出处理结果中的目标数据。通过本公开实施例,可以在流计算应用中的任一节点失效后,通过快照数据恢复后的故障节点能够获取上游节点在快照之后产生的数据,并采用同样的处理方式进行处理后,将下游节点未获得过的数据输出给下游节点,既能够保证恢复后的故障节点与失效前的处理数据以及处理结果一致,并且又能够保证输出至下游节点的数据不会发生重复,也即能够保证故障节点的恢复不会引起下游节点的内部状态和/或输出数据与故障节点失效前不一致,因此通过本公开实施例能够实现故障恢复前后数据一致,并且能够实现失效节点的单点恢复,而无需进行全局回滚,进而能够保证故障恢复的实时性。
在本实施例的一个可选实现方式中,如图2所示,所述方法进一步还包括以下步骤S201-S202:
在步骤S201中,根据所述快照数据中的输入输出信息确定最近一次快照时刻所述故障节点从上游节点已获得的未处理数据的数据标识;其中,所述未处理数据的数据标识是由所述上游节点按照所述未处理数据的产出顺序分配的;
在步骤S202中,根据所述未处理数据的第一数据标识从所述上游节点的输出缓存中获得所述输入数据;其中,所述输入数据包括所述未处理数据以及所述上游节点在所述未处理数据之后产生的数据。
该可选的实现方式中,每个节点将获得的数据存放在各自的输入缓存中,并且每个节点将自身处理产生的数据存放在各自的输出缓存中。每个节点为自身处理产生的数据分配数据标识,且该数据标识可以按照数据产生的顺序排列(例如使用递增或递减的序列号作为数据标识)。每个节点在为自身处理产生的数据分配了数据标识后,将其存放在输出缓存,并且异步地将输出缓存中的数据顺序输出至下游节点。在下游节点出现故障以后,根据最近一次快照数据进行恢复时,由于最近一次快照数据除了包括下游节点在快照时刻的状态之外,还包括快照时刻的输入输出信息,例如下游节点的输入缓存和输出缓存中的数据标识等。因此,可以根据最近一次快照时间中的输入输出信息确定最近一次快照时刻下游节点从上游节点已获得的未处理数据的数据标识,进而根据数据标识从上游节点获得该未处理数据。由于最近一次快照之后,流计算系统可能运行了一段时间,因此上游节点在最近一次快照之后可能产生了一些新的数据,而这些新的数据和快照时刻记录下来的未处理数据的数据标识之间有顺序关系,因此可以根据未处理数据的数据标识也从上游节点的输出缓存获得上游节点在最近一次快照之后也即未处理数据之后新产生的数据,那么未处理数据和这些新的数据构成了最近一次快照之后输出至该故障了的下游节点的输入数据。下游节点在恢复到最近一次快照时刻的状态后,可以继续对这些输入数据进行与故障之间相同的处理,进而能够产生与故障之前相同的处理结果,实现了故障节点的单点恢复,且无需流计算系统中其他节点的全局回滚,并保持了数据的一致性。
在本实施例的一个可选实现方式中,所述步骤S102中按照所述故障节点故障之前的方式对输入数据进行处理后得到处理结果的步骤,进一步包括以下步骤:
根据所述输入数据的时间戳的顺序对所述输入数据进行处理,并得到处理结果;其中,所述输入数据的时间戳由产生所述输入数据的上游节点按照产生时间分配的,且对所述输入数据进行处理时所采用的处理机制与所述故障节点故障之前所采用的处理机制一致。
该可选的实现方式中,每个节点除了为自身产生的数据分配数据标识外,还为产生的数据分配时间戳,为提高效率,节点可以对连续的一批数据分配同一个时间戳。故障了故障节点获得输入数据以后,可以采用故障之前所采用的处理机制按照时间戳的顺序对输入数据进行处理,这样由于所采用的处理机制一致,且处理顺序也一致的情况下,对于相同的输入数据处理所得到的输出数据与故障之前的能够保持一致,实现了故障恢复前后故障节点的内部状态以及输出数据的一致性。
在本实施例的一个可选实现方式中,所述步骤S102中按照所述故障节点故障之前的方式对输入数据进行处理后得到处理结果的步骤之后,所述方法进一步包括以下步骤:
按照所述处理结果产生的顺序以及所述输入输出信息为所述处理结果分配具有顺序关系的第二数据标识。
该可选的实现方式中,每个节点都可以为自身处理产生的数据分配具有顺序关系的数据标识,因此故障恢复之后的故障节点(或者故障节点的替代节点)也可以按照产生顺序对所产生的处理结果分配数据标识,该数据标识之间具有顺序关系,可以标识数据的产生顺序。此外,最近一次快照数据中的输入输出信息中会记录快照时刻故障节点的输出缓存中的输出数据的数据标识,在恢复到最近一次快照的状态后,目标节点(或替代节点)可以基于输入输出信息中输出数据的数据标识继续为新产生的处理结果分配具有顺序关系的第二数据标识。
在本实施例的一个可选实现方式中,如图3所示,所述步骤S103,即输出所述处理结果中的目标数据的步骤,进一步包括以下步骤S301-S302:
在步骤S301中,确定所述故障节点失效前输出至下游节点的输出数据的第三数据标识;
在步骤S302中,将所述第二数据标识大于所述第三数据标识的所述处理结果作为目标数据输出至所述下游节点。
该可选的实现方式中,最近一次快照之后,故障节点可能已经产生了一些输出数据并输出至了下游节点。为了避免重复输出,在恢复至最近一次快照时刻的状态后,通过处理输入数据所产生的处理结果中,只将未给下游节点输出过的处理结果输出,其他处理结果可以丢弃。为了实现这一目标,可以先确定最近一次快照之后、故障之前故障节点向下游节点输出过的数据的数据标识,然后再与故障恢复后故障节点(或替代节点)所产生的处理结果的数据标识进行比较,如果处理结果的数据标识小于等于最近一次快照之后、故障之前故障节点向下游节点输出过的数据的数据标识,那么由于该数据已经输出给了下游节点,则可以丢弃,否则输出至下游节点。
在一实施例中,最近一次快照之后、故障之前故障节点向下游节点输出过的数据的数据标识可以通过以下方式中的至少之一来确定:
在故障节点的输出缓存未失效的情况下,直接从故障节点的输出缓存确定输出数据的第三数据标识;
向下游节点询问当前从故障节点所获得的最新一个输入数据的数据标识,进而确定该输出数据的第三数据标识;
获取下游节点对应该故障节点所分配的输入缓存中的所有输入数据,并将其存放入故障节点对应该下游节点的输出缓存中(每个节点可以针对其每个下游节点分别设置一输出缓存,而每个节点也可以针对每个上游节点分别设置一输入缓存),根据故障节点对应该下游节点的输出缓存中的数据确定输出数据的第三数据标识。
在本实施例的一个可选实现方式中,所述步骤S102中按照所述故障节点故障之前的方式对输入数据进行处理后得到处理结果的步骤之后,所述方法进一步包括以下步骤:
根据所述输入输出信息为所述处理结果分配第四数据标识以及时间戳;其中,所述第四数据标识以及时间戳的分配方式与所述故障节点故障之前一致。
该可选的实现方式中,出现故障的故障节点在恢复时,假如其相邻的下游节点也出现了故障,那么可以先恢复故障节点,之后再采用同样的方式恢复下游节点。也就是说,出现相邻上下游节点同时出现故障的情况下(出现故障的相邻节点的数量可以大于等于2),可以从出现故障的最上游节点开始逐一采用本公开实施例提出的故障恢复方案进行恢复。然而,对于这种情况,由于下游节点也出现了故障,因此故障节点在恢复时可以先从外部存储获取故障节点故障前对于输出数据所分配的数据标识和时间戳,并针对同样的数据分配相同的数据标识和时间戳。如前所述,为了提高效率,连续一批产生的多条输出数据可能会被分配同样的时间戳,而在故障恢复后,重新处理输入数据所产生的多条输出数据的数据标识与故障前是一致的,但是时间戳可能不一致,而由于下游节点也出现了故障,因此输出至下游节点后该数据的时间戳与故障前也可能不一致,这会导致下游节点的内部状态和/或输出数据与故障之前也不一致(这是因为下游节点可能对应多个上游节点,而下游节点的处理方式是针对时间戳处理从多个上游节点接收到的数据的情况下,如果故障恢复前后该故障节点输出至下游节点的同一输出数据的时间戳不一致,则下游节点可能对该同一输出数据进行不同的处理),因此可以通过上述方式解决,也即从外部存储获取故障前数据标识和时间戳的分配方式,进而采用相同的分配方式为故障恢复后得到的处理结果分配数据标识和时间戳。
在本实施例的一个可选实现方式中,所述步骤S101中获取所述故障节点的最近一次快照数据的步骤,进一步包括以下步骤:
获取所述故障节点以及所述故障节点所影响到的所有下游节点的最近一次快照数据。
该可选的实现方式中,针对故障恢复级别中的Exactly Once和At least once来说,节点可以不给产生的数据分配数据标识和时间戳,但是在故障恢复的时候需要恢复该故障节点所在子DAG(有向无环图)中所有下游节点。
通常的故障级别分为如下几种:At most once:每条数据记录最多被处理一次,潜台词也表明数据会有丢失(没被处理掉)的可能。At least once:每条数据记录至少被处理一次,这个比上At most once强的地方在于这里至少保证数据不会丢,至少被处理过,不足之处在于数据可能会被重复处理。Exactly once:每条数据记录正好被处理一次。没有数据丢失,也没有重复的数据处理,但是无法保证故障切换前后处理结果一致。Exactly Same:每条数据记录正好被处理一次,没有数据丢失,也没有重复的数据处理,而且保证故障切换前后处理结果一致。
该可选的实现方式在Exactly Once和At least once语义下,响应于故障节点的故障恢复事件,可以获取到故障节点以及故障节点所影响到的所有下游节点的最近一次快照数据,以便对故障节点以及故障节点的所有下游节点进行恢复。故障节点所影响到的所有下游节点包括流计算集系统构成的有向无环图(DAG)中,属于故障节点所在子DAG中故障节点的所有下游节点。
在本实施例的一个可选实现方式中,所述步骤S101中获取所述故障节点的最近一次快照数据的步骤之后,所述方法进一步还包括以下步骤:
从所述故障节点的上游节点的输出缓存中获得所述输入数据;其中,从所述输出缓存中获得的所述输入数据为最近一次快照之后所述上游节点产生的输出数据。
该可选的实现方式中,对于Exactly Once和At least once语义,节点可以不为产生的数据分配数据标识和时间戳,那么在故障节点出现故障时,可以通过获取故障节点以及故障节点所影响到的所有下游节点的最近一次快照数据,并在故障恢复时,利用最近一次快照数据恢复故障节点以及所有下游节点的状态,同时故障节点以及下游节点均从各自的上游节点的输出缓存中获取输入数据进行处理,而上游节点的输出缓存中仅保留最近一次快照之后所产生的新的数据,快照之前的数据在进行快照的时候清空。通过这种方式,能够在Exactly Once和At least once语义下,不进行数据标识和时间戳分配的情况下也能够实现单点恢复后前后数据保持一致,而且所需要恢复的节点仅包括故障节点所影响到的下游节点,无需全局回滚操作。
在本实施例的一个可选实现方式中,所述步骤S103中输出所述处理结果中的目标数据的步骤之后,所述方法进一步还包括以下步骤:
根据所述最近一次快照数据依次恢复所述故障节点所影响到的所有下游节点,并对从各自的上游节点所接收到的输入数据依次进行处理后,输出至各自的下游节点。
该可选的实现方式中,如前所述,针对Exactly Once和At least once语义,在恢复了故障节点的状态,并从上游节点的输出缓存中获得输入数据进行处理后,将产生的处理结果存放在输出缓存中,并异步地将输出缓存中的数据输出至下游节点。需要说明的是,这种情况下,处理结果中的目标数据为所有处理结果。下游节点在接收到故障节点输出的数据后,也进行同样的恢复操作,依次类推,可以恢复故障节点以及故障节点影响到的所有下游节点。
下述为本公开装置实施例,可以用于执行本公开方法实施例。
图4示出根据本公开一实施方式的故障恢复装置的结构框图,该装置可以通过软件、硬件或者两者的结合实现成为电子设备的部分或者全部。如图4所示,所述故障恢复装置包括:
第一获取模块401,被配置为响应于故障节点的故障恢复事件,获取所述故障节点的最近一次快照数据;其中,所述快照数据至少包括所述故障节点最近一次快照时的状态、输入输出信息;
第一处理模块402,被配置为根据所述快照数据恢复所述故障节点最近一次快照时状态,并按照所述故障节点故障之前的方式对输入数据进行处理后得到处理结果;其中,所述输入数据根据所述输入输出信息获得,且为所述故障节点在最近一次快照之后、故障之前所接收到的数据;
输出模块403,被配置为输出所述处理结果中的目标数据;其中,所述目标数据为所述故障节点的下游节点未获得过的数据。
流计算系统实时获取来自不同数据源的海量数据,经过实时分析处理,获得有价值的信息。流计算系统中的各个计算节点按照有向无环图的方式构成,上游节点的计算结果输出给下游节点,下游节点根据从上游节点获得的数据进行计算处理,并进一步输出给另一下游节点。计算机节点可以为流计算系统中执行计算逻辑的最小单元。本实施例中提出的故障恢复方法适用于任意分布式流计算系统。故障节点为流计算系统中的任一计算节点,在流计算系统中的任一节点出现故障时,可以根据本公开实施例提出的上述方法进行单点恢复。
本实施例中,流计算系统在运行过程中可为每个节点开辟一个input buffer(输入缓存)来接收上游节点产出的数据,也为每个节点开辟一个output buffer(输出缓存)来存放发往下游节点的数据。节点针对接收到的输入数据进行相应处理后产生输出数据,输出数据可以缓存在为该节点分配的输出缓存中;该节点还将输出数据输出给对应的下游节点,并作为下游节点的输入数据缓存输入缓存中。
在一实施例中,节点为每个处理产生的数据分配数据标识(例如顺序号)并确保严格递增,然后写入输出缓存;对输出缓存中中新写入的数据分配时间戳,为提高效率,可以对连续的一批数据分配同一个时间戳。
在一实施例中,节点还将分配的数据标识和时间戳的映射关系写到外部存储器,以便备份和持久化。节点异步地将上述已分配好数据标识和时间戳的数据不断发往下游节点,相同时间戳的数据可以整体打包发往下游节点。
在一实施例中,下游节点对接收到的来自所有不同上游节点的未处理数据统一按照数据自身的时间顺序依次进行处理,这里要求节点的处理逻辑是确定性的,即对相同的输入数据,每次都能产出相同的结果。
在一些实施例中,主节点定期给流计算系统中的源节点注入barrier(栅栏),并采用分布式快照的方式进行数据备份,barrier被注入到数据流中和其他数据一样作为数据流的一部分流动。源节点在接收到barrier后,立刻做一个快照,也即记录源节点当前的offset信息(offset信息包括上一次快照到本次快照所产生的新的变化信息),之后源节点将该barrier广播到下游节点,下游节点接收到barrier后,执行与源节点同样的操作,直至该源节点所在的有向无环图中的最后一个节点快照完成,这样就形成了一次完整的快照。本实施例中,不仅备份快照时刻节点的状态,同时还记录快照时刻节点的输入输出信息。在一实施例中,节点的数输入输出信息可以包括快照时刻在输入缓存和输出缓存中的数据信息,例如输入缓存和输出缓存中数据的数据标识和时间戳。
在故障节点故障后,可以根据之前的快照数据获取该故障了的故障节点的最近一次快照数据,最近一次快照数据可以包括最近一次快照时刻故障节点的状态、输入输出信息等。流计算系统可以启动一个替代节点,并将该替代节点恢复成最近一次快照时刻时的状态,同时该替代节点采用故障节点故障前的处理机制处理输入数据。此处的输入数据为最近一次快照时刻故障节点的上游节点输出给故障节点,且未被故障节点所处理的数据,可以根据最近一次快照数据中的输入输出信息获得。
故障节点的替代节点不但采用与故障节点相同的处理机制(例如计算方式),还采用相同的时间顺序处理输入数据,因此得到的处理结果与故障节点故障前的处理结果一致。也即故障节点故障之前的方式不但包括故障节点故障之前所采用的处理机制(例如计算方式),还包括对多个相同输入数据的处理顺序等。
处理结果中的目标数据为未被故障节点输出给过下游节点的数据,也即下游节点未从故障前的故障节点获得过的数据。由于故障节点在最近一次快照后以及故障前可能还进行过数据处理,因此处理结果也可能输出给了下游节点,因此本实施例中需要确定替代节点得到的处理结果中哪些数据已经被输出至下游节点了,避免重复输出至下游节点,而引起下游节点内部状态及输出数据与故障前不一致,导致整个系统无法恢复到与故障前完全一致的状态。
本公开实施例在流计算应用中故障节点失效之后,通过获取故障节点最近一次快照数据以及最近一次快照数据之后的输入数据,进而根据快照数据恢复故障节点失效之前的状态,并按照失效之前的方式处理输入数据,进而输出处理结果中的目标数据。通过本公开实施例,可以在流计算应用中的任一节点失效后,通过快照数据恢复后的故障节点能够获取上游节点在快照之后产生的数据,并采用同样的处理方式进行处理后,将下游节点未获得过的数据输出给下游节点,既能够保证恢复后的故障节点与失效前的处理数据以及处理结果一致,并且又能够保证输出至下游节点的数据不会发生重复,也即能够保证故障节点的恢复不会引起下游节点的内部状态和/或输出数据与故障节点失效前不一致,因此通过本公开实施例能够实现故障恢复前后数据一致,并且能够实现失效节点的单点恢复,而无需进行全局回滚,进而能够保证故障恢复的实时性。
在本实施例的一个可选实现方式中,如图5所示,所述装置还包括:
确定模块501,被配置为根据所述快照数据中的输入输出信息确定最近一次快照时刻所述故障节点从上游节点已获得的未处理数据的数据标识;其中,所述未处理数据的数据标识是由所述上游节点按照所述未处理数据的产出顺序分配的;
第二获取模块502,被配置为根据所述未处理数据的第一数据标识从所述上游节点的输出缓存中获得所述输入数据;其中,所述输入数据包括所述未处理数据以及所述上游节点在所述未处理数据之后产生的数据。
该可选的实现方式中,每个节点将获得的数据存放在各自的输入缓存中,并且每个节点将自身处理产生的数据存放在各自的输出缓存中。每个节点为自身处理产生的数据分配数据标识,且该数据标识可以按照数据产生的顺序排列(例如使用递增或递减的序列号作为数据标识)。每个节点在为自身处理产生的数据分配了数据标识后,将其存放在输出缓存,并且异步地将输出缓存中的数据顺序输出至下游节点。在下游节点出现故障以后,根据最近一次快照数据进行恢复时,由于最近一次快照数据除了包括下游节点在快照时刻的状态之外,还包括快照时刻的输入输出信息,例如下游节点的输入缓存和输出缓存中的数据标识等。因此,可以根据最近一次快照时间中的输入输出信息确定最近一次快照时刻下游节点从上游节点已获得的未处理数据的数据标识,进而根据数据标识从上游节点获得该未处理数据。由于最近一次快照之后,流计算系统可能运行了一段时间,因此上游节点在最近一次快照之后可能产生了一些新的数据,而这些新的数据和快照时刻记录下来的未处理数据的数据标识之间有顺序关系,因此可以根据未处理数据的数据标识也从上游节点的输出缓存获得上游节点在最近一次快照之后也即未处理数据之后新产生的数据,那么未处理数据和这些新的数据构成了最近一次快照之后输出至该故障了的下游节点的输入数据。下游节点在恢复到最近一次快照时刻的状态后,可以继续对这些输入数据进行与故障之间相同的处理,进而能够产生与故障之前相同的处理结果,实现了故障节点的单点恢复,且无需流计算系统中其他节点的全局回滚,并保持了数据的一致性。
在本实施例的一个可选实现方式中,所述第一处理模块402包括:
处理子模块,被配置为根据所述输入数据的时间戳的顺序对所述输入数据进行处理,并得到处理结果;其中,所述输入数据的时间戳由产生所述输入数据的上游节点按照产生时间分配的,且对所述输入数据进行处理时所采用的处理机制与所述故障节点故障之前所采用的处理机制一致。
该可选的实现方式中,每个节点除了为自身产生的数据分配数据标识外,还为产生的数据分配时间戳,为提高效率,节点可以对连续的一批数据分配同一个时间戳。故障了故障节点获得输入数据以后,可以采用故障之前所采用的处理机制按照时间戳的顺序对输入数据进行处理,这样由于所采用的处理机制一致,且处理顺序也一致的情况下,对于相同的输入数据处理所得到的输出数据与故障之前的能够保持一致,实现了故障恢复前后故障节点的内部状态以及输出数据的一致性。
在本实施例的一个可选实现方式中,所述装置还包括:
第一分配模块,被配置为按照所述处理结果产生的顺序以及所述输入输出信息为所述处理结果分配具有顺序关系的第二数据标识。
该可选的实现方式中,每个节点都可以为自身处理产生的数据分配具有顺序关系的数据标识,因此故障恢复之后的故障节点(或者故障节点的替代节点)也可以按照产生顺序对所产生的处理结果分配数据标识,该数据标识之间具有顺序关系,可以标识数据的产生顺序。此外,最近一次快照数据中的输入输出信息中会记录快照时刻故障节点的输出缓存中的输出数据的数据标识,在恢复到最近一次快照的状态后,目标节点(或替代节点)可以基于输入输出信息中输出数据的数据标识继续为新产生的处理结果分配具有顺序关系的第二数据标识。
在本实施例的一个可选实现方式中,如图6所示,所述输出模块403包括:
确定子模块601,被配置为确定所述故障节点失效前输出至下游节点的输出数据的第三数据标识;
输出子模块602,被配置为将所述第二数据标识大于所述第三数据标识的所述处理结果作为目标数据输出至所述下游节点。
该可选的实现方式中,最近一次快照之后,故障节点可能已经产生了一些输出数据并输出至了下游节点。为了避免重复输出,在恢复至最近一次快照时刻的状态后,通过处理输入数据所产生的处理结果中,只将未给下游节点输出过的处理结果输出,其他处理结果可以丢弃。为了实现这一目标,可以先确定最近一次快照之后、故障之前故障节点向下游节点输出过的数据的数据标识,然后再与故障恢复后故障节点(或替代节点)所产生的处理结果的数据标识进行比较,如果处理结果的数据标识小于等于最近一次快照之后、故障之前故障节点向下游节点输出过的数据的数据标识,那么由于该数据已经输出给了下游节点,则可以丢弃,否则输出至下游节点。
在一实施例中,最近一次快照之后、故障之前故障节点向下游节点输出过的数据的数据标识可以通过以下方式中的至少之一来确定:
在故障节点的输出缓存未失效的情况下,直接从故障节点的输出缓存确定输出数据的第三数据标识;
向下游节点询问当前从故障节点所获得的最新一个输入数据的数据标识,进而确定该输出数据的第三数据标识;
获取下游节点对应该故障节点所分配的输入缓存中的所有输入数据,并将其存放入故障节点对应该下游节点的输出缓存中(每个节点可以针对其每个下游节点分别设置一输出缓存,而每个节点也可以针对每个上游节点分别设置一输入缓存),根据故障节点对应该下游节点的输出缓存中的数据确定输出数据的第三数据标识。
在本实施例的一个可选实现方式中,所述装置包括:
第二分配模块,被配置为根据所述输入输出信息为所述处理结果分配第四数据标识以及时间戳;其中,所述第四数据标识以及时间戳的分配方式与所述故障节点故障之前一致。
该可选的实现方式中,出现故障的故障节点在恢复时,假如其相邻的下游节点也出现了故障,那么可以先恢复故障节点,之后再采用同样的方式恢复下游节点。也就是说,出现相邻上下游节点同时出现故障的情况下(出现故障的相邻节点的数量可以大于等于2),可以从出现故障的最上游节点开始逐一采用本公开实施例提出的故障恢复方案进行恢复。然而,对于这种情况,由于下游节点也出现了故障,因此故障节点在恢复时可以先从外部存储获取故障节点故障前对于输出数据所分配的数据标识和时间戳,并针对同样的数据分配相同的数据标识和时间戳。如前所述,为了提高效率,连续一批产生的多条输出数据可能会被分配同样的时间戳,而在故障恢复后,重新处理输入数据所产生的多条输出数据的数据标识与故障前是一致的,但是时间戳可能不一致,而由于下游节点也出现了故障,因此输出至下游节点后该数据的时间戳与故障前也可能不一致,这会导致下游节点的内部状态和/或输出数据与故障之前也不一致(这是因为下游节点可能对应多个上游节点,而下游节点的处理方式是针对时间戳处理从多个上游节点接收到的数据的情况下,如果故障恢复前后该故障节点输出至下游节点的同一输出数据的时间戳不一致,则下游节点可能对该同一输出数据进行不同的处理),因此可以通过上述方式解决,也即从外部存储获取故障前数据标识和时间戳的分配方式,进而采用相同的分配方式为故障恢复后得到的处理结果分配数据标识和时间戳。
在本实施例的一个可选实现方式中,所述第一获取模块401包括:
获取子模块,被配置为获取所述故障节点以及所述故障节点所影响到的所有下游节点的最近一次快照数据。
该可选的实现方式中,针对故障恢复级别中的Exactly Once和At least once来说,节点可以不给产生的数据分配数据标识和时间戳,但是在故障恢复的时候需要恢复该故障节点所在子DAG(有向无环图)中所有下游节点。
通常的故障级别分为如下几种:At most once:每条数据记录最多被处理一次,潜台词也表明数据会有丢失(没被处理掉)的可能。At least once:每条数据记录至少被处理一次,这个比上At most once强的地方在于这里至少保证数据不会丢,至少被处理过,不足之处在于数据可能会被重复处理。Exactly once:每条数据记录正好被处理一次。没有数据丢失,也没有重复的数据处理,但是无法保证故障切换前后处理结果一致。Exactly Same:每条数据记录正好被处理一次,没有数据丢失,也没有重复的数据处理,而且保证故障切换前后处理结果一致。
该可选的实现方式在Exactly Once和At least once语义下,响应于故障节点的故障恢复事件,可以获取到故障节点以及故障节点所影响到的所有下游节点的最近一次快照数据,以便对故障节点以及故障节点的所有下游节点进行恢复。故障节点所影响到的所有下游节点包括流计算集系统构成的有向无环图(DAG)中,属于故障节点所在子DAG中故障节点的所有下游节点。
在本实施例的一个可选实现方式中,所述装置还包括:
第三获取模块,被配置为从所述故障节点的上游节点的输出缓存中获得所述输入数据;其中,从所述输出缓存中获得的所述输入数据为最近一次快照之后所述上游节点产生的输出数据。
该可选的实现方式中,对于Exactly Once和At least once语义,节点可以不为产生的数据分配数据标识和时间戳,那么在故障节点出现故障时,可以通过获取故障节点以及故障节点所影响到的所有下游节点的最近一次快照数据,并在故障恢复时,利用最近一次快照数据恢复故障节点以及所有下游节点的状态,同时故障节点以及下游节点均从各自的上游节点的输出缓存中获取输入数据进行处理,而上游节点的输出缓存中仅保留最近一次快照之后所产生的新的数据,快照之前的数据在进行快照的时候清空。通过这种方式,能够在Exactly Once和At least once语义下,不进行数据标识和时间戳分配的情况下也能够实现单点恢复后前后数据保持一致,而且所需要恢复的节点仅包括故障节点所影响到的下游节点,无需全局回滚操作。
在本实施例的一个可选实现方式中,所述装置还包括:
第二处理模块,被配置为根据所述最近一次快照数据依次恢复所述故障节点所影响到的所有下游节点,并对从各自的上游节点所接收到的输入数据依次进行处理后,输出至各自的下游节点。
该可选的实现方式中,如前所述,针对Exactly Once和At least once语义,在恢复了故障节点的状态,并从上游节点的输出缓存中获得输入数据进行处理后,将产生的处理结果存放在输出缓存中,并异步地将输出缓存中的数据输出至下游节点。需要说明的是,这种情况下,处理结果中的目标数据为所有处理结果。下游节点在接收到故障节点输出的数据后,也进行同样的恢复操作,依次类推,可以恢复故障节点以及故障节点影响到的所有下游节点。
图7是适于用来实现根据本公开实施方式的故障恢复方法的电子设备的结构示意图。
如图7所示,电子设备700包括中央处理单元(CPU)701,其可以根据存储在只读存储器(ROM)702中的程序或者从存储部分708加载到随机访问存储器(RAM)703中的程序而执行上述图1所示的实施方式中的各种处理。在RAM703中,还存储有电子设备700操作所需的各种程序和数据。CPU701、ROM702以及RAM703通过总线704彼此相连。输入/输出(I/O)接口705也连接至总线704。
以下部件连接至I/O接口705:包括键盘、鼠标等的输入部分706;包括诸如阴极射线管(CRT)、液晶显示器(LCD)等以及扬声器等的输出部分707;包括硬盘等的存储部分708;以及包括诸如LAN卡、调制解调器等的网络接口卡的通信部分709。通信部分709经由诸如因特网的网络执行通信处理。驱动器710也根据需要连接至I/O接口705。可拆卸介质711,诸如磁盘、光盘、磁光盘、半导体存储器等等,根据需要安装在驱动器710上,以便于从其上读出的计算机程序根据需要被安装入存储部分708。
特别地,根据本公开的实施方式,上文参考图1描述的方法可以被实现为计算机软件程序。例如,本公开的实施方式包括一种计算机程序产品,其包括有形地包含在及其可读介质上的计算机程序,所述计算机程序包含用于执行图1所示方法的程序代码。在这样的实施方式中,该计算机程序可以通过通信部分709从网络上被下载和安装,和/或从可拆卸介质711被安装。
附图中的流程图和框图,图示了按照本公开各种实施方式的系统、方法和计算机程序产品的可能实现的体系架构、功能和操作。在这点上,路程图或框图中的每个方框可以代表一个模块、程序段或代码的一部分,所述模块、程序段或代码的一部分包含一个或多个用于实现规定的逻辑功能的可执行指令。也应当注意,在有些作为替换的实现中,方框中所标注的功能也可以以不同于附图中所标注的顺序发生。例如,两个接连地表示的方框实际上可以基本并行地执行,它们有时也可以按相反的顺序执行,这依所涉及的功能而定。也要注意的是,框图和/或流程图中的每个方框、以及框图和/或流程图中的方框的组合,可以用执行规定的功能或操作的专用的基于硬件的系统来实现,或者可以用专用硬件与计算机指令的组合来实现。
描述于本公开实施方式中所涉及到的单元或模块可以通过软件的方式实现,也可以通过硬件的方式来实现。所描述的单元或模块也可以设置在处理器中,这些单元或模块的名称在某种情况下并不构成对该单元或模块本身的限定。
作为另一方面,本公开还提供了一种计算机可读存储介质,该计算机可读存储介质可以是上述实施方式中所述装置中所包含的计算机可读存储介质;也可以是单独存在,未装配入设备中的计算机可读存储介质。计算机可读存储介质存储有一个或者一个以上程序,所述程序被一个或者一个以上的处理器用来执行描述于本公开的方法。
以上描述仅为本公开的较佳实施例以及对所运用技术原理的说明。本领域技术人员应当理解,本公开中所涉及的发明范围,并不限于上述技术特征的特定组合而成的技术方案,同时也应涵盖在不脱离所述发明构思的情况下,由上述技术特征或其等同特征进行任意组合而形成的其它技术方案。例如上述特征与本公开中公开的(但不限于)具有类似功能的技术特征进行互相替换而形成的技术方案。