您的位置:首页 > 科技 > 正文

网络波动背景下数据稳定性传输的讨论与分析

2021-09-26 10:29:57 来源:C114通信网

一、引言

在通信系统或者多系统协同的软件系统里,网元或系统之间经常需要进行信息同步或者信息查询。系统间的消息查询一般为长链接,如果遇到网络异常或者对端系统处理不过来的情况,会在短时间内产生大量的查询消息。反复查询反复失败,前面失败的消息以及新到达的查询消息大量积压,反复的查询和大量的消息处理使得系统性能急剧下降,甚至影响到其他无关的业务。因此,为保障系统的稳定可靠,对于异常情况的处理至关重要。尤其是适用“5个9”要求的通信系统,导致服务出问题的往往是一些异常情况,需要有充足的逻辑来保障出现异常情况时,系统仍然能够稳定、可靠地处理业务。

下面我们就沿着是什么,怎么做,为什么这样做的思路逐步讨论分析。

二、是什么产生网络信息波动

如上图,我们看到大部分业务的开展都是三方系统之间的服务应用在交互,这样在很大程度上就有多种因素会导致消息传输的波动,以上业务的逻辑,我将它归纳为两点一线。

两点指的是起始端和目的端,一线指的是传输介质:

1)两点间的服务中断或者异常就会导致信息传输的不可达,直接导致信息的丢失,造成业务失败。

2)传输介质的网络质量不行,例如丢包率过大,也会导致信息传输异常,造成业务失败。

基于以上两点,让我们大致了解业务中网络信息波动产生的原因,接下来我们阐述一下该如何应对。

三、怎么做降低信息传输失败的概率

1)设计方案

针对系统间信息同步时的异常情况,基于消息队列+Redis缓存,采用退避算法,实现了消息延迟消费。当出现网络波动或者对端网元响应缓慢时,失败的消息按照退避算法进行合理退让。这样,不仅减少了消息的无效尝试,降低了无效的系统开销,而且保障了其他正常业务的顺利运行,确保了即使在网络波动或者对端系统回复延迟的异常情况下,也不会因为大量堆积的查询消息消耗过多的系统资源,系统性能的稳定可靠得到保障。

2)技术架构

(1)消息通过Kafka或其他消息中间件进入正常的消费队列进行生产和消费,如果都成功,则完成信息处理。

(2)消息如果在经过Kafka等消息中间件发生异常,根据消息失败的情况,根据规避算法,计算出该消息需要延迟的时间,写入消息的延迟时间里,将消息按照一定的格式(sortedSet)存储到Redis中。

(3)通过每秒级别的定时轮询,通过reverseRangeByScore获取到消息。根据消息的延迟时间判断该消息是否达到消费时间,如果达到消费时间,将再次进入kafka的中间件进入重试消费队列进行生产和消费。如果没有达到消费时间,继续排队,优先处理其他延迟时间已到的消息。这样的机制减少了无效的消息重试,保障了队列中其他消息能够得到及时处理。

(4)此外,系统在高并发的情况下,会继续产生大量查询消息。为避免队列中的消息堆积,消息的重复消费具有次数限制。根据测试,3次重试是一个有效的保障值,如果3次重试还是没有响应,该消息将落库DB数据库,不再占用队列资源。最后定时任务会每小时对DB里的堆积消息进行轮询,轮询到的消息会再次进入Kafka的重试队列进行消费。

四、为什么这样做,好处是什么?

(1)从业务上讲:

从图一,我们可知我们对接的业务都是彼此分离的三方业务系统,在产生网络信息波动的情况下,我们从两点一线中能尽快解决的就是属于自己业务服务侧的一点,其他的一点和传输介质都需要耗费较大的人力去沟通解决。我们需要尽可能地将消费失败的信息传输到三方,但同时也要保证自己服务的消息不被积压,致使自己系统的服务崩溃,以上架构很好地解决了磁力问题

(2)从先进性上讲:

本方案的消息中间件探索了一条在高并发场景下,减少堆积消息的有效路径。在传统设计模式下,系统间的查询消息均是等间隔地进行查询,在网络稳定和并发量低的情况下,这样的技术方案可以表现稳定。但是一旦网络波动或者并发量加大,等间隔的消息查询会造成大量的堆积消息,从而影响到系统的稳定性和可靠性。在解决堆积消息方面,网上较多的方案是进行队列的消息预警,这样的解决方案相当于一种事后补救方案。但是本方案消息中间件从消息的源头进行有效的算法设计,保障了从源头上减少无效的重复消息。这样的解决方案弥补了主流技术设计上的不足,是一种比较先进的设计思路,填补了公司在处理高并发、高稳定性要求的业务上的技术空白。

(3)从兼容性上讲:

在本架构中,采用了多种技术的组合设计,不拘泥于某一种特定的技术。现在市场上流行的消息中间件如:ActiveMQ、RabbitMQ、Kafka、RocketMQ、ZeroMQ等,都可以在架构中使用。本方案消息中间件的架构设计具有很强大的兼容性。

(4)从灵活性上讲:

在本架构中,消息的延时消费等级可以根据自己项目的需要自由设定,消息的延时消费次数也可以根据自己项目的需要自由设定,系统灵活性强。

(5)从可复用性上讲:

本消息中间件采用常用的消息队列+Redis缓存,是一种可复用性很强的消息中间件,可广泛应用于各类高并发、高可靠性要求的业务系统。

(6)从性能的角度讲:

redis可以作为一个高性能的存储db,性能要比MySQL好很多,并且支持持久化,稳定性好。redis SortedSet队列天然支持以时间作为条件排序,完美满足我们选出要推送记录的需要。为保障消息均能得到及时处理,一次从队列中取出执行的数量可以设置得大一点或启动多个推送的服务。假设一次从队列中取出执行的数量设置为:2000,推送的服务节点为:3个,定时任务执行间隔为:1秒,一分钟内可以实际推送的数量为:2000 * 60 * 3 = 360000(理想情况下:多个推送队列subscribe-queue的推送任务分布均匀)。这个数量已经可以满足绝大部分的需求。

五、总结

本文探讨的方案是从三方系统的消息稳定性出发设计的,其实这一套设计也可适用于本系统多个模块的营运服务,随着技术的迭代更新,相信会有更好、更加完善的解决方案问世。本文方案仅做抛砖引玉,希望相关问题能够得到大家更多的关注和讨论,期待各位提供更好的思路和建议,谢谢大家。