发明内容
本公开实施例至少提供一种访问请求处理的方法、装置、计算机设备及存储介质,可以实现各个服务实例均匀的处理服务访问请求,可以提升服务性能的稳定性。
第一方面,本公开实施例提供了一种访问请求处理的方法,所述方法包括:
接收服务请求端发送的服务访问请求,并从所述服务访问请求携带的请求参数中提取出目标标识码;
基于所述目标标识码出现的频率,确定所述服务访问请求是否属于目标访问请求;
若确定出所述服务访问请求不属于所述目标访问请求,基于预设的哈希路由表,查询出与所述目标标识码匹配的服务实例的第一网络地址,向所述服务请求端发送所述第一网络地址;
若确定出所述服务访问请求属于所述目标访问请求,向所述服务请求端发送当前访问量最低的服务实例的第二网络地址。
一种可选的实施方式中,根据以下步骤生成所述哈希路由表:
获取提供服务的服务实例的实例数量,并确定各所述服务实例的实例编号;
基于所述实例数量确定待生成的所述哈希路由表中格子的格子数量及格子编号;
通过随机排序算法,生成各所述服务实例的特征序列,所述特征序列的长度与所述格子数量相匹配;
根据各所述服务实例的实例编号的编号顺序、各所述服务实例的特征序列以及所述格子编号,将各所述服务实例的实例编号填入至对应的格子中,生成所述哈希路由表。
一种可选的实施方式中,针对任一所述服务实例,根据以下步骤生成所述服务实例的特征序列:
按照第一哈希算法,将所述服务实例的实例编号进行哈希运算,得到第一哈希值;
按照第二哈希算法,将所述服务实例的实例编号进行哈希运算,得到第二哈希值;
基于所述第一哈希值、所述第二哈希值以及所述格子数量,通过随机排序算法,生成所述服务实例的特征序列。
一种可选的实施方式中,所述方法还包括:
在将任一所述服务实例的实例编号填入所述哈希路由表中时,基于所述服务实例的特征序列中的第一数字,确定待填充的格子;
若所述待填充的格子被占用,按照所述服务实例的所述特征序列中各个数字的顺序,确定所述特征序列中位于所述第一数字之后的第二数字,将所述服务实例的实例编号填入与所述第二数字关联的格子中;其中,所述第二数字关联的格子未被占用。
一种可选的实施方式中,在所述根据各所述服务实例的实例编号的编号顺序、各所述服务实例的特征序列以及所述格子编号,将各所述服务实例的实例编号填入至对应的格子中,生成所述哈希路由表之后,所述方法还包括:
遍历所述哈希路由表中的格子;
若存在空格子,则基于所述哈希路由表中实例编号的出现次数,确定目标服务实例;
将所述目标服务实例的实例编号填入所述空格子。
一种可选的实施方式中,所述基于预设的哈希路由表,查询出与所述目标标识码匹配的服务实例的第一网络地址,包括:
按照第三哈希算法,对所述目标标识码进行哈希计算,得到第三哈希值;
从所述哈希路由表中,查找出与所述第三哈希值匹配的格子中的目标实例编号;
确定与所述目标实例编号关联的服务实例的第一网络地址。
一种可选的实施方式中,基于所述目标标识码出现的频率,确定所述服务访问请求是否属于目标访问请求,包括:
确定在接收到所述服务访问请求之前的预设时长内,所述目标标识码出现的次数;
若所述目标标识码出现的次数大于或等于预设阈值,则确定所述服务访问请求为目标访问请求。
一种可选的实施方式中,若确定出所述服务访问请求属于所述目标访问请求,向所述服务请求端发送当前访问量最低的服务实例的第二网络地址,包括:
确定在接收到所述服务访问请求之前,各个服务实例的被访问次数;
将对应的被访问次数最少的服务实例的第二网络地址发送给所述服务请求端。
第二方面,本公开实施例还提供一种访问请求处理的装置,所述装置包括:
提取模块,用于接收服务请求端发送的服务访问请求,并从所述服务访问请求携带的请求参数中提取出目标标识码;
确定模块,用于基于所述目标标识码出现的频率,确定所述服务访问请求是否属于目标访问请求;
查询模块,用于若确定出所述服务访问请求不属于所述目标访问请求,基于预设的哈希路由表,查询出与所述目标标识码匹配的服务实例的第一网络地址,向所述服务请求端发送所述第一网络地址;
发送模块,用于若确定出所述服务访问请求属于所述目标访问请求,向所述服务请求端发送当前访问量最低的服务实例的第二网络地址。
一种可选的实施方式中,所述装置还包括生成模块;所述生成模块,用于根据以下步骤生成所述哈希路由表:
获取提供服务的服务实例的实例数量,并确定各所述服务实例的实例编号;
基于所述实例数量确定待生成的所述哈希路由表中格子的格子数量及格子编号;
通过随机排序算法,生成各所述服务实例的特征序列,所述特征序列的长度与所述格子数量相匹配;
根据各所述服务实例的实例编号的编号顺序、各所述服务实例的特征序列以及所述格子编号,将各所述服务实例的实例编号填入至对应的格子中,生成所述哈希路由表。
一种可选的实施方式中,针对任一所述服务实例,所述生成模块包括生成单元;所述生成单元,用于根据以下步骤生成所述服务实例的特征序列:
按照第一哈希算法,将所述服务实例的实例编号进行哈希运算,得到第一哈希值;
按照第二哈希算法,将所述服务实例的实例编号进行哈希运算,得到第二哈希值;
基于所述第一哈希值、所述第二哈希值以及所述格子数量,通过随机排序算法,生成所述服务实例的特征序列。
一种可选的实施方式中,所述生成模块还包括:
确定单元,用于在将任一所述服务实例的实例编号填入所述哈希路由表中时,基于所述服务实例的特征序列中的第一数字,确定待填充的格子;
第一填充单元,用于若所述待填充的格子被占用,按照所述服务实例的所述特征序列中各个数字的顺序,确定所述特征序列中位于所述第一数字之后的第二数字,将所述服务实例的实例编号填入与所述第二数字关联的格子中;其中,所述第二数字关联的格子未被占用。
一种可选的实施方式中,所述生成模块还包括第二填充单元:
所述第二填充单元,用于遍历所述哈希路由表中的格子,若存在空格子,则基于所述哈希路由表中实例编号的出现次数,确定目标服务实例,将所述目标服务实例的实例编号填入所述空格子。
一种可选的实施方式中,所述查询模块,用于根据以下步骤查询所述第一网络地址:
按照第三哈希算法,对所述目标标识码进行哈希计算,得到第三哈希值;
从所述哈希路由表中,查找出与所述第三哈希值匹配的格子中的目标实例编号;
确定与所述目标实例编号关联的服务实例的第一网络地址。
一种可选的实施方式中,所述确定模块,用于根据以下步骤确定所述服务访问请求是否属于目标访问请求:
确定在接收到所述服务访问请求之前的预设时长内,所述目标标识码出现的次数;
若所述目标标识码出现的次数大于或等于预设阈值,则确定所述服务访问请求为目标访问请求。
一种可选的实施方式中,所述发送模块,用于根据以下步骤将所述第二网络地址发送给所述服务请求端:
确定在接收到所述服务访问请求之前,各个服务实例的被访问次数;
将对应的被访问次数最少的服务实例的第二网络地址发送给所述服务请求端。
第三方面,本公开实施例还提供一种计算机设备,包括:处理器、存储器和总线,所述存储器存储有所述处理器可执行的机器可读指令,当计算机设备运行时,所述处理器与所述存储器之间通过总线通信,所述机器可读指令被所述处理器执行时执行上述第一方面,或第一方面中任一种可能的实施方式中的步骤。
第四方面,本公开实施例还提供一种计算机可读存储介质,所述计算机可读存储介质上存储有计算机程序,所述计算机程序被处理器运行时执行上述第一方面,或第一方面中任一种可能的实施方式中的步骤。
本公开实施例提供的访问请求处理的方法、装置、计算机设备及存储介质,通过哈希路由表为服务请求端分配服务实例,可以防止长尾请求导致缓存击穿情况的发生,并通过将目标访问请求分配给访问量低的服务实例,可以防止数据倾斜情况的发生,与现有技术中在服务发现中,会出现由于长尾请求造成缓存命中率低而导致缓存击穿的情况,以及存在数据倾斜的情况相比,本公开可以实现各个服务实例均衡地处理服务访问请求,可以提升服务性能的稳定性。
进一步,本公开实施例提供的访问请求处理的方法,根据各服务实例的实例编号的编号顺序、各服务实例的特征序列以及格子编号,将各服务实例的实例编号填入至对应的格子中,生成哈希路由表,可以使哈希路由表中尽可能均匀的分布各个服务实例的实例编号,这样,通过哈希路由表为服务请求端分配服务实例,可以防止长尾请求导致缓存击穿情况的发生。
为使本公开的上述目的、特征和优点能更明显易懂,下文特举较佳实施例,并配合所附附图,作详细说明如下。
具体实施方式
为使本公开实施例的目的、技术方案和优点更加清楚,下面将结合本公开实施例中附图,对本公开实施例中的技术方案进行清楚、完整地描述。显然,所描述的实施例仅仅是本公开一部分实施例,而不是全部的实施例。通常在此处附图中描述和示出的本公开实施例的组件可以以各种不同的配置来布置和设计。因此,以下对在附图中提供的本公开的实施例的详细描述并非旨在限制要求保护的本公开的范围,而是仅仅表示本公开的选定实施例。基于本公开的实施例,本领域技术人员在没有做出创造性劳动的前提下所获得的所有其他实施例,都属于本公开保护的范围。
经研究发现,在服务发现中,仍然面临由于长尾请求造成缓存命中率低而导致缓存击穿的问题;在处理缓存击穿问题时,又出现数据倾斜的问题,在没有解决上述问题时,将难以实现各个服务实例均匀的处理服务访问请求,因而,导致服务性能稳定性下降。
基于上述研究,本公开提供了一种访问请求处理的方法、装置、计算机设备及存储介质,通过哈希路由表为服务请求端分配服务实例,可以防止长尾请求导致缓存击穿情况的发生,并通过将目标访问请求分配给访问量低的服务实例,可以防止发生数据倾斜的情况,从而实现各个服务实例均匀的处理服务访问请求,提升服务的稳定性。
本公开阐述的方案,均是发明人在经过实践并仔细研究后得出的结果,因此,上述问题的发现过程以及下文中本公开针对上述问题所提出的解决方案,都应该是发明人对本公开做出的贡献。
应注意到:相似的标号和字母在下面的附图中表示类似项,因此,一旦某一项在一个附图中被定义,则在随后的附图中不需要对其进行进一步定义和解释。
为便于对本实施例进行理解,首先对本公开实施例所公开的一种访问请求处理的方法进行详细介绍,本公开实施例所提供的访问请求处理的方法的执行主体一般为具有一定计算能力的计算机设备,该计算机设备例如包括:终端设备或服务器或其它处理设备,终端设备可以为用户设备(User Equipment,UE)、移动设备、用户终端、终端、蜂窝电话、无线电话、个人数字处理(Personal Digital Assistant,PDA)、手持设备、计算设备、车载设备、可穿戴设备等。在一些可能的实现方式中,该访问请求处理的方法可以通过处理器调用存储器中存储的计算机可读指令的方式来实现。
下面以执行主体为计算机设备为例对本公开实施例提供的访问请求处理的方法加以说明。
实施例一
参见图1所示,为本公开实施例提供的一种访问请求处理的方法的流程图,所述方法包括步骤S101~S104,其中:
S101:接收服务请求端发送的服务访问请求,并从所述服务访问请求携带的请求参数中提取出目标标识码。
在该步骤中,在接收到服务请求端发送的服务访问请求后,先获取该服务访问请求携带的请求参数,并出该请求参数中提取出目标标识码,这里,利用目标标识码,可以确定出用于为服务请求端提供服务的服务实例其中,请求参数可以包括请求内容的标识、服务请求端的标识、服务请求端的版本等;标识码可以为涉及请求内容的标识,比如文章ID、视频ID、评论ID,标识码也可以为服务请求侧用户的用户身份标识,比如用户ID。
进一步地,可以根据以下步骤从服务访问请求携带的请求参数中提取出目标标识码:
在接收到服务请求端发送的服务访问请求后,根据服务访问请求的请求内容所属的目标场景,从服务访问请求携带的请求参数中提取出与所述目标场景相匹配的目标标识码。
一示例中,服务访问请求的请求内容为请求阅读文章A,则可以从服务访问请求携带的请求参数中提取出与文章相匹配的文章A的ID。
需要说明的是,接收服务请求端发送的服务访问请求可以为中间件,中间件用于建立服务请求端和服务提供端之间的连接,其中,中间件使用应用系统所提供的基础服务,衔接网络上应用系统的各个部分或不同的应用,能够达到资源共享、功能共享的目的。
这里,服务提供端用于提供服务,每个服务均可以由至少一个服务实例提供。
S102:基于所述目标标识码出现的频率,确定所述服务访问请求是否属于目标访问请求。
在该步骤中,在从服务访问请求携带的请求参数中提取出目标标识码后,统计目标标识码出现的频率,基于目标标识码出现的频率,来确定服务访问请求是否为目标访问请求,这里,目标访问请求即为热门访问请求,即访问量超过一定阈值的请求。
进一步地,步骤S102中基于所述目标标识码出现的频率,确定所述服务访问请求是否属于目标访问请求,包括以下步骤:
确定在接收到所述服务访问请求之前的预设时长内,所述目标标识码出现的次数;若所述目标标识码出现的次数大于或等于预设阈值,则确定所述服务访问请求为目标访问请求。
这里,可以利用W-TinyLFU算法(现代的缓存算法)进行次数的统计,W-TinyLFU算法是利用有限的空间可以记录随时间变化的访问频率的算法。
在W-TinyLFU中使用Count-Min Sketch算法(计数最小草图算法)记录访问频率,而这个也是布隆过滤器的一种变种。如果需要记录一个值,那需要通过多种哈希算法对其进行处理哈希,然后在对应的哈希算法的记录中+1,一个压缩算法必定会出现冲突。比如我们建立一个Long的数组,通过计算出每个数据的哈希的位置,比如张三和李四,他们两有可能哈希值都是相同,比如都是1,相应位置就会增加相应的频率,张三访问1万次,李四访问1次这个位置就是1万零1,如果取李四的访问频率的时候就会取出是1万零1,但是李四命名只访问了1次。为了解决这个问题,所以W-TinyLFU用了多个哈希算法,可以理解为是二维数组的一个概念,比如在第一个算法张三和李四冲突了,但是在第二个,第三个中很大的概率不冲突,若一个算法大概有1%的概率冲突,那四个算法一起冲突的概率是1%的四次方,通过这个模式我们取李四的访问率的时候取所有算法中,李四访问最低频率的次数。如果一个哈希路由表来记录这个频率,如果有100个数据,那这个哈希路由表就得存储100个这个数据的访问频率。即使这个缓存的容量是1,由于W-TinyLFU的规则必须全部记录这个100个数据的访问频率。其中,预设时长和预设阈值可以根据实际业务需要进行设置。
S103:若确定出所述服务访问请求不属于所述目标访问请求,基于预设的哈希路由表,查询出与所述目标标识码匹配的服务实例的第一网络地址,向所述服务请求端发送所述第一网络地址。
在该步骤中,若确定出服务请求端发送的服务访问请求不为目标访问请求,则利用预设的哈希路由表,查询出与目标标识码匹配的服务实例,并将与目标标识码匹配的服务实例的第一网络地址发送给服务请求端,以便服务请求端访问该服务实例。其中,哈希路由表用于根据服务访问请求中的目标标识码,为服务请求端分配服务实例。
这里,在服务发现中,若存在长尾请求,通常会因为缓存命中率低而导致缓存击穿,为了解决缓存击穿的问题,可以对服务发现进行一致性哈希,即将带有相同的标识码的服务访问请求均分配至同一服务实例。这样,通过利用哈希路由表,可以尽可能快速地将各个服务访问请求分配至对应的服务实例中进行处理,防止长尾请求导致缓存击穿情况的发生。
需要说明的是,长尾请求是指服务访问请求处理的时间明显高于处理时间均值的那部分占比较小的请求,业界关于延迟有一个常用的P99标准,也就是99%的请求延迟要满足在一定耗时以内,只有1%的请求会大于这个耗时,而这1%就可以认为是长尾请求,比如,1s为处理时间均值,即使服务处理时间超过1s的比例仅为0.01%,当需要同时查询的实例数达到2000时,服务延时大于1秒的请求数将超过18%,因此,当服务访问请求的数量较大时,服务延时的概率将大大提升,如果此时长尾请求中大量访问的数据缓存中没有,需要到数据库中查询,就会造成缓存击穿。
这里,通常在处理服务访问请求时,先从缓存中取数据,取到直接返回结果,取不到时从数据库中取,数据库取到更新缓存,并返回结果,数据库也没取到,那直接返回空结果。缓存击穿是指缓存中没有但数据库中有的数据,这时由于并发用户特别多,同时读缓存没读到数据,又同时去数据库去取数据,引起数据库压力瞬间增大,造成过大压力,比如,服务访问请求中有长尾请求时。
进一步地,生成的哈希路由表,要确保将服务访问请求中的标识码进行哈希打散,以保障标识码映射到服务实例的分布尽可能均匀,下面对生成哈希路由表的过程进行阐述,也即,根据以下步骤生成所述哈希路由表:
步骤a1:获取提供服务的服务实例的实例数量,并确定各所述服务实例的实例编号。
在该步骤中,先确定提供每种服务的服务实例的实例数量,进而,在确定服务实例的实例数量后,为提供该种服务的每个服务实例进行编号,得到每个服务实例的实例编号。
步骤a2:基于所述实例数量确定待生成的所述哈希路由表中格子的格子数量及格子编号。
在该步骤中,在确定出提供服务的服务实例的实例数量后,根据该实例数量,可以确定待生成的哈希路由表中格子的格子数量,通常,将格子数量可以设置为大于实例数量的两倍,且要保证哈希路由表中格子的格子数量为质数,这样可以减少哈希值的聚集和碰撞,让分布更均匀。
这里,通常哈希路由表中格子数量会大于可以提供服务的服务实例的实例数量,所以,哈希路由表中,同一个服务实例可能出现在多个格子中,可以让各个服务实例在哈希路由表中出现的次数大致相同。这样,可以确保每个服务实例处理的服务访问请求的请求量大致相同,即实现各个服务实例均匀的处理服务访问请求,提升服务的稳定性。
步骤a3:通过随机排序算法,生成各所述服务实例的特征序列,所述特征序列的长度与所述格子数量相匹配。
在该步骤中,针对每个服务实例,根据随机排序算法,为每个服务实例生成一个长度为格子数量的特征序列,这里,将每个服务实例的特征序列的长度设置与哈希路由表中格子的格子数量相匹配,可以让每个服务实例尽量均匀地分布在哈希路由表中。即,让每个服务实例均有相同机会写入格子中,如果将每个服务实例的特征序列的长度小于哈希路由表中格子的格子数量,由于存在哈希路由表中格子被占用的情况,有的服务实例可能无法写入格子中,或出现有的服务实例写入哈希路由表中格子的数量较少。
一示例中,格子数量为7,一个服务实例对于的特征序列为permutation(7)={3,0,4,1,5,2,6},permutation代表序列。
进一步地,针对任一服务实例,根据以下步骤生成该服务实例的特征序列:
按照第一哈希算法,将所述服务实例的实例编号进行哈希运算,得到第一哈希值;按照第二哈希算法,将所述服务实例的实例编号进行哈希运算,得到第二哈希值;基于所述第一哈希值、所述第二哈希值以及所述格子数量,通过随机排序算法,生成所述服务实例的特征序列。
在该步骤中,先选取两个独立无关联的哈希算法,若先利用第一哈希算法对实例编号进行哈希运算,得到第一哈希值;利用第二哈希算法对实例编号进行哈希运算,得到第二哈希值,进而,基于第一哈希值、第二哈希值以及格子数量,通过随机排序算法,生成服务实例的特征序列。这里,通过使用两个独立无关联的哈希算法,可以减少映射结果的碰撞次数,进而提高随机性,其中,生成特征序列的方法可以有很多种,比如直接采用一个随机序列等,无论采用何种方式生成特征序列,目的都是一样的,要使生成的特征序列随机且均匀。
一示例中,先取两个无关联的哈希函数h1和哈希函数h2,若一个服务实例的实例编号为b,格子数量为M,先利用哈希函数h1对应的第一哈希算法对实例编号b进行哈希运算,得到第一哈希值offset,以及利用哈希函数h2对应的第二哈希算法对实例编号b进行哈希运算,得到第二哈希值skip,针对每个j,计算出每个j对应的该服务实例对应的特征序列中的每个数字,其中,j为0至M-1中的每个整数,计算公式可以为:
offset=h1(b)%M;
skip=h2(b)%(M-1)+1;
特征序列中的第j个数字为=(offset+j×skip)%M。
步骤a4:根据各所述服务实例的实例编号的编号顺序、各所述服务实例的特征序列以及所述格子编号,将各所述服务实例的实例编号填入至对应的格子中,生成所述哈希路由表,具体地,可以先按照实例编号从小到大的顺序将各个服务实例的实例编号进行填入,并在将每个服务实例进行填入时,根据该服务实例的特征序列中数字,确定将该服务实例填入的目标位置,进而,将该服务实例填入哈希路由表中。
在该步骤中,按照服务实例的实例编号的编号顺序,以及每个服务实例的特征序列中数字,将各个服务实例的实例编号轮流填入至哈希路由表中的格子,将格子填满后,生成哈希路由表,这里,通过利用随机排序算法,生成每个服务实例的特征序列,进而利用每个服务实例的特征序列,将各个服务实例的实例编号填入表中,可以在一定程度上使表格中均匀分布各个服务实例的实例编号,这样,可以使各个服务实例均匀的处理服务访问请求。
进一步地,在将任一所述服务实例的实例编号填入所述哈希路由表时,基于所述服务实例的特征序列中的第一数字,确定待填充的格子;若所述待填充的格子被占用,按照所述服务实例的所述特征序列中各个数字的顺序,确定所述特征序列中位于所述第一数字之后的第二数字,将所述服务实例的实例编号填入与所述第二数字关联的格子中;其中,所述第二数字关联的格子未被占用。
进一步地,为防止某一格子为空的情况发生,即出现空格子时,在将各个服务实例的实例编号轮流填入至所述哈希路由表中的格子之后,遍历所述哈希路由表中的格子;若存在空格子,则基于所述哈希路由表中实例编号的出现次数,确定目标服务实例;将所述目标服务实例的实例编号填入所述空格子。
在该步骤中,在确定哈希路由表中的存在空格子时,统计当前哈希路由表中出现次数最少的实例编号,并将该实例编号填入空格子中,这样,可以使哈希路由表中各个服务实例的实例编号更均匀。
进一步地,步骤S103中所述基于预设的哈希路由表,查询出与所述目标标识码匹配的服务实例的第一网络地址,包括:
按照第三哈希算法,对所述目标标识码进行哈希计算,得到第三哈希值;从所述哈希路由表中,查找出与所述第三哈希值匹配的格子中的目标实例编号;确定与所述目标实例编号关联的服务实例的第一网络地址。
在该步骤中,在从服务访问请求中提取出目标标识码后,按照第三哈希算法,对目标标识码进行哈希计算,得到第三哈希值,并从哈希路由表中,查找出处于第三哈希值的格子中的目标实例编号,确定与目标实例编号关联的服务实例的第一网络地址,这里,目标标识码对应的第三哈希值为哈希路由表中格子的序号。
需要说明的是,在建立哈希路由表后,可以为每个哈希表中的格子分配一个哈希值。具体地,可以将哈希路由表中每个格子的序号与一个哈希值进行关联,每个哈希值是通过对服务实例可以处理的服务访问请求中的标识码进行哈希后得到的,这里,多个标识码可以对应一个哈希值。在接收到一个服务访问请求时,采用相同的哈希算法,对目标标识码进行哈希值运算得到第三哈希值,这样,可以从哈希路由表中,找到与第三哈希值对应的哈希路由表中格子的格子序号,进而,根据该格子需要找到该格子内写入的目标实例编号,根据目标实例编号关联的服务实例的第一网络地址。
这里,哈希算法也被称为散列算法,哈希算法虽然被称为算法,但实际上它更像是一种思想,哈希算法没有一个固定的公式,只要符合散列思想的算法都可以被称为是哈希算法。
一实例中,哈希算法为取余,若标识码为11,则标识码为11对应的哈希值为hash(11)=11%3=2。图2示出了本公开实施例所提供的生成哈希路由表的示意图,左边的纵列示出了每个实例编号对应的特征序列,实例编号为B0、B1、B2,其中,实例编号为B0的服务实例对应的特征序列为{3,0,4,1,5,2,6},实例编号为B1的服务实例对应的特征序列为{0,2,4,6,1,3,5},实例编号为B2的服务实例对应的特征序列为{3,4,5,6,0,1,2},右边的纵列示出了哈希路由表,哈希路由表的每个表格中填充有服务实例的实例编号,这里,哈希路由表的格子数量为7。
针对图2示出的生成哈希路由表的示意图,对根据各个服务实例的特征序列在空的哈希路由表中填充实例编号,生成哈希路由表的过程进行阐述,按照各个服务实例的实例编号的编号顺序,以及每个服务实例的特征序列中数字,将各个服务实例的实例编号轮流填入至空的哈希路由表中的格子,具体地,1)按照实例编号由小到大的顺序,找到实例编号为B0的特征序列中的第一个数字是3,进而将B0填充至表中序号为3的格子中,在填充完B0后,找到实例编号为B1的特征序列中的第一个数字是0,进而将B1填充至表中序号为0的格子中,找到实例编号为B2的特征序列中的第一个数字是3,由于序号为3的格子已经被占用,确定B2的特征序列中的位于数字3之后的数字为4,进而将B2填充至表中序号为4的格子中,至此,第一轮填充实例编号B0、B1、B2的过程完成;2)接下来,又轮到B0填充了,确定B0的特征序列中的第2个数字,是0,但序号为0的格子被占用了,继续看B0的特征序列的第3个数字,是4,但序号为4的格子被占用了,直到测试到数字1可以用,则填充B0到序号为1的格子中,按照上述填充方法,直到把整张哈希路由表填充满为止。
S104:若确定出所述服务访问请求属于所述目标访问请求,向所述服务请求端发送当前访问量最低的服务实例的第二网络地址。
在该步骤中,在确定出服务请求端发送的服务访问请求为目标访问请求,为防止目标访问请求不能得到及时的处理,确定当前访问量最低的服务实例,并将当前访问量最低的服务实例的第二网络地址发送给服务请求端,以便服务请求端访问该服务实例。
需要说明的是,虽然通过预设的哈希路由表,可以快速地将服务访问请求分配至各个服务实例,可以实现防止长尾请求导致缓存击穿情况的发生,但是,由于将带有相同的标识码的服务访问请求均分配至同一服务实例,会出现数据倾斜的情况,即命中目标访问请求的服务实例访问量会很大,而过大负载会导致服务稳定性的下降,为解决这一问题,本公开将目标访问请求分配给访问量低的服务实例,可以防止数据倾斜情况的发生。也就是说,本公开对于目标访问请求和非目标访问请求这两种请求,选取为服务请求端提供服务的服务实例所采取的方式不同,对于非目标访问请求,通过预设的哈希路由表来选取为服务请求端提供服务的服务实例,对于目标访问请求,为服务请求端直接选取访问量低的服务实例,这样,通过两种方案的结合,可以实现各个服务实例均匀的处理服务访问请求,可以提升服务的稳定性。
其中,数据倾斜是指缓存数据分散度不够,导致大量的缓存数据集中到了一台或者几台服务实例上,称为数据倾斜,一般来说数据倾斜是由于负载均衡实施的效果不好引起的。通常,在单位时间内,来自服务访问请求中的标识码计数符合齐夫分布(Zipfian分布),则认为服务访问请求存在数据倾斜,Zipfian分布的公式为
其中,a越大,分布越密集,对于本公开Zipfian分布表达的含义是有少数服务实例经常被使用,大部分的服务实例很少被使用,即,目标访问请求被分配至同一服务实例,该服务实例处理的访问量较大,而导致数据倾斜。
进一步地,步骤S104中若确定出所述服务访问请求属于所述目标访问请求,向所述服务请求端发送当前访问量最低的服务实例的第二网络地址,包括以下步骤:
确定在接收到所述服务访问请求之前,各个服务实例的被访问次数;将对应的被访问次数最少的服务实例的第二网络地址发送给所述服务请求端。
这里,将目标访问请求分配给访问量低的服务实例,可以防止数据倾斜情况的发生。
需要说明的是,统计各个服务实例的被访问次数的过程可以是周期性进行的,这样,可以基于服务访问请求接收的时间,直接获取每个服务实例的被访问次数。也可以是接收到访服务问请求之后,再进行统计每个服务实例的被访问次数的统计。
在本公开实施例中,通过从接收到的服务请求端发送的服务访问请求中提取出目标标识码,并基于目标标识码出现的频率,确定服务访问请求是否为目标访问请求,若不是,则基于预设的哈希路由表,将查询出与目标标识码匹配的服务实例的第一网络地址发送给服务请求端,若是,则将当前访问量最低的服务实例的第二网络地址发送给服务请求端。基于上述方式,通过哈希路由表为服务请求端分配服务实例,可以防止长尾请求导致缓存击穿情况的发生,并通过将目标访问请求分配给访问量低的服务实例,可以防止发生数据倾斜的情况,从而实现各个服务实例均匀的处理服务访问请求,提升服务的稳定性。
本领域技术人员可以理解,在具体实施方式的上述方法中,各步骤的撰写顺序并不意味着严格的执行顺序而对实施过程构成任何限定,各步骤的具体执行顺序应当以其功能和可能的内在逻辑确定。
基于同一发明构思,本公开实施例中还提供了与访问请求处理的方法对应的访问请求处理的装置,由于本公开实施例中的装置解决问题的原理与本公开实施例上述访问请求处理的方法相似,因此装置的实施可以参见方法的实施,重复之处不再赘述。
实施例二
参照图3至图5所示,图3示出了本公开实施例所提供的一种访问请求处理的装置300的示意图之一;图4示出了本公开实施例所提供的一种访问请求处理的装置300的示意图之二;图5示出了本公开实施例所提供的访问请求处理的装置300中,生成模块350的具体示意图。
如图3所示,所述访问请求处理的装置300包括:
提取模块310,用于接收服务请求端发送的服务访问请求,并从所述服务访问请求携带的请求参数中提取出目标标识码;
确定模块320,用于基于所述目标标识码出现的频率,确定所述服务访问请求是否属于目标访问请求;
查询模块330,用于若确定出所述服务访问请求不属于所述目标访问请求,基于预设的哈希路由表,查询出与所述目标标识码匹配的服务实例的第一网络地址,向所述服务请求端发送所述第一网络地址;
发送模块340,用于若确定出所述服务访问请求属于所述目标访问请求,向所述服务请求端发送当前访问量最低的服务实例的第二网络地址。
在一种可能的实施方式中,如图4所示,所述访问请求处理的装置300还包括生成模块350;所述生成模块350,用于根据以下步骤生成所述哈希路由表:
获取提供服务的服务实例的实例数量,并确定各所述服务实例的实例编号;
基于所述实例数量确定待生成的所述哈希路由表中格子的格子数量及格子编号;
通过随机排序算法,生成各所述服务实例的特征序列,所述特征序列的长度与所述格子数量相匹配;
根据各所述服务实例的实例编号的编号顺序、各所述服务实例的特征序列以及所述格子编号,将各所述服务实例的实例编号填入至对应的格子中,生成所述哈希路由表。
在一种可能的实施方式中,如图5所示,针对任一所述服务实例,所述生成模块350包括生成单元351;所述生成单元351,用于根据以下步骤生成所述服务实例的特征序列:
按照第一哈希算法,将所述服务实例的实例编号进行哈希运算,得到第一哈希值;
按照第二哈希算法,将所述服务实例的实例编号进行哈希运算,得到第二哈希值;
基于所述第一哈希值、所述第二哈希值以及所述格子数量,通过随机排序算法,生成所述服务实例的特征序列。
在一种可能的实施方式中,如图5所示,所述生成模块350还包括:
确定单元352,用于在将任一所述服务实例的实例编号填入所述哈希路由表中时,基于所述服务实例的特征序列中的第一数字,确定待填充的格子;
第一填充单元353,用于若所述待填充的格子被占用,按照所述服务实例的所述特征序列中各个数字的顺序,确定所述特征序列中位于所述第一数字之后的第二数字,将所述服务实例的实例编号填入与所述第二数字关联的格子中;其中,所述第二数字关联的格子未被占用。
在一种可能的实施方式中,如图5所示,所述生成模块350还包括第二填充单元354:
所述第二填充单元354,用于遍历所述哈希路由表中的格子,若存在空格子,则基于所述哈希路由表中实例编号的出现次数,确定目标服务实例,将所述目标服务实例的实例编号填入所述空格子。
在一种可能的实施方式中,如图3所示,所述查询模块330,用于根据以下步骤查询所述第一网络地址:
按照第三哈希算法,对所述目标标识码进行哈希计算,得到第三哈希值;
从所述哈希路由表中,查找出与所述第三哈希值匹配的格子中的目标实例编号;
确定与所述目标实例编号关联的服务实例的第一网络地址。
在一种可能的实施方式中,如图3所示,所述确定模块320,用于根据以下步骤确定所述服务访问请求是否属于目标访问请求:
确定在接收到所述服务访问请求之前的预设时长内,所述目标标识码出现的次数;
若所述目标标识码出现的次数大于或等于预设阈值,则确定所述服务访问请求为目标访问请求。
在一种可能的实施方式中,如图3所示,所述发送模块340,用于根据以下步骤将所述第二网络地址发送给所述服务请求端:
确定在接收到所述服务访问请求之前,各个服务实例的被访问次数;
将对应的被访问次数最少的服务实例的第二网络地址发送给所述服务请求端。
在本公开的实施例中,通过从接收到的服务请求端发送的服务访问请求中提取出目标标识码,并基于目标标识码出现的频率,确定服务访问请求是否属于目标访问请求,若不属于,则基于预设的哈希路由表,向服务请求端发送查询出与目标标识码匹配的服务实例的第一网络地址,若属于,则向服务请求端发送当前访问量最低的服务实例的第二网络地址。基于上述方式,通过哈希路由表为服务请求端分配服务实例,可以防止长尾请求导致缓存击穿情况的发生,并通过将目标访问请求分配给访问量低的服务实例,可以防止发生数据倾斜的情况,从而实现各个服务实例均匀的处理服务访问请求,提升服务的稳定性。
关于装置中的各模块的处理流程、以及各模块之间的交互流程的描述可以参照上述方法实施例中的相关说明,这里不再详述。
实施例三
基于同一技术构思,本公开实施例还提供了一种计算机设备。参照图6所示,为本公开实施例提供的计算机设备600的结构示意图,包括处理器601、存储器602、和总线603。其中,存储器602用于存储执行指令,包括内存6021和外部存储器6022;这里的内存6021也称内存储器,用于暂时存放处理器601中的运算数据,以及与硬盘等外部存储器6022交换的数据,处理器601通过内存6021与外部存储器6022进行数据交换,当计算机设备600运行时,处理器601与存储器602之间通过总线603通信,使得处理器601在执行以下指令:
接收服务请求端发送的服务访问请求,并从所述服务访问请求携带的请求参数中提取出目标标识码;
基于所述目标标识码出现的频率,确定所述服务访问请求是否属于目标访问请求;
若确定出所述服务访问请求不属于所述目标访问请求,基于预设的哈希路由表,查询出与所述目标标识码匹配的服务实例的第一网络地址,向所述服务请求端发送所述第一网络地址;
若确定出所述服务访问请求属于所述目标访问请求,向所述服务请求端发送当前访问量最低的服务实例的第二网络地址。
实施例四
本公开实施例还提供一种计算机可读存储介质,该计算机可读存储介质上存储有计算机程序,该计算机程序被处理器运行时执行上述方法实施例中所述的访问请求处理的方法的步骤。其中,该存储介质可以是易失性或非易失的计算机可读取存储介质。
本公开实施例所提供的访问请求处理的方法的计算机程序产品,包括存储了程序代码的计算机可读存储介质,所述程序代码包括的指令可用于执行上述方法实施例中所述的访问请求处理的方法的步骤,具体可参见上述方法实施例,在此不再赘述。
本公开实施例还提供一种计算机程序,该计算机程序被处理器执行时实现前述实施例的任意一种方法。该计算机程序产品可以具体通过硬件、软件或其结合的方式实现。在一个可选实施例中,所述计算机程序产品具体体现为计算机存储介质,在另一个可选实施例中,计算机程序产品具体体现为软件产品,例如软件开发包(Software DevelopmentKit,SDK)等等。
所属领域的技术人员可以清楚地了解到,为描述的方便和简洁,上述描述的系统和装置的具体工作过程,可以参考前述方法实施例中的对应过程,在此不再赘述。在本公开所提供的几个实施例中,应该理解到,所揭露的系统、装置和方法,可以通过其它的方式实现。以上所描述的装置实施例仅仅是示意性的,例如,所述单元的划分,仅仅为一种逻辑功能划分,实际实现时可以有另外的划分方式,又例如,多个单元或组件可以结合或者可以集成到另一个系统,或一些特征可以忽略,或不执行。另一点,所显示或讨论的相互之间的耦合或直接耦合或通信连接可以是通过一些通信接口,装置或单元的间接耦合或通信连接,可以是电性,机械或其它的形式。
所述作为分离部件说明的单元可以是或者也可以不是物理上分开的,作为单元显示的部件可以是或者也可以不是物理单元,即可以位于一个地方,或者也可以分布到多个网络单元上。可以根据实际的需要选择其中的部分或者全部单元来实现本实施例方案的目的。
另外,在本公开各个实施例中的各功能单元可以集成在一个处理单元中,也可以是各个单元单独物理存在,也可以两个或两个以上单元集成在一个单元中。
所述功能如果以软件功能单元的形式实现并作为独立的产品销售或使用时,可以存储在一个处理器可执行的非易失的计算机可读取存储介质中。基于这样的理解,本公开的技术方案本质上或者说对现有技术做出贡献的部分或者该技术方案的部分可以以软件产品的形式体现出来,该计算机软件产品存储在一个存储介质中,包括若干指令用以使得一台计算机设备(可以是个人计算机,服务器,或者网络设备等)执行本公开各个实施例所述方法的全部或部分步骤。而前述的存储介质包括:U盘、移动硬盘、只读存储器(Read-OnlyMemory,ROM)、随机存取存储器(Random Access Memory,RAM)、磁碟或者光盘等各种可以存储程序代码的介质。
最后应说明的是:以上所述实施例,仅为本公开的具体实施方式,用以说明本公开的技术方案,而非对其限制,本公开的保护范围并不局限于此,尽管参照前述实施例对本公开进行了详细的说明,本领域的普通技术人员应当理解:任何熟悉本技术领域的技术人员在本公开揭露的技术范围内,其依然可以对前述实施例所记载的技术方案进行修改或可轻易想到变化,或者对其中部分技术特征进行等同替换;而这些修改、变化或者替换,并不使相应技术方案的本质脱离本公开实施例技术方案的精神和范围,都应涵盖在本公开的保护范围之内。因此,本公开的保护范围应所述以权利要求的保护范围为准。