The evolution of 58.com's high-performance mobile push platform architecture

This article describes in detail the three stages of the evolution of 58.com's high-performance mobile push platform architecture, and introduces what is mobile push, why it is needed, principles and solutions; how to design the architecture of the first stage (single platform) of mobile push; Analysis and solution of typical performance problems of Push push, and how to ensure high availability, high performance, and high stability.

What is Mobile Push

Mobile Push is one of the most basic requirements of the mobile Internet, which is used to meet the arrival of messages to the App client in the mobile Internet environment. Take Zhuanzhuan (an idle trading platform of real individuals under 58 Ganji) as an example, when a buyer places an order, we notify the seller through a mobile push message, and when the seller has shipped the goods, we inform the buyer through a mobile push message to let the buyer know the order. Buyers and sellers can grasp the real-time order dynamics of second-hand commodity transactions in a timely manner.

Why do you need Mobile Push?

In the mobile Internet network environment, weak network environment often occurs, especially in 2G, 3G and other network environments, the network is not stable enough, the long connection between the App client and the corresponding server has been disconnected, and the message cannot reach the App client. Our business needs to push messages such as Message (Zuanzhuan App transaction messages, etc.), Operation (Zuanzhuan App operation activities, etc.), Alert (Zuanzhuan red envelope unconsumed reminders, etc.) and other messages to the App client, thereby triggering users to see these messages. , and reach the corresponding target by clicking on these Push messages.

Push principle and scheme comparison

There are three main ways to implement mobile push.

  1. Mobile App Polling Mode (PULL) 
    The App client periodically initiates a Push message query request to achieve the purpose of message push. The advantages and disadvantages of the PULL scheme are obvious. The overall architecture is simple but the real-time performance is poor. We can improve the real-time performance by speeding up the query frequency, but this will cause excessive power and traffic consumption.

  2. The mobile App sends push messages through SMS messages based on the SMS Push method 
    , and inserts a SMS interception module on the client side, which can intercept the SMS messages, parse them and forward them to the App for processing. This solution has good real-time performance and high arrival rate, but the cost is very high.

  3. Mobile App long-connection method (Push) 
    Mobile Push is implemented based on TCP long-connection, and the message is real-time. This is the current mainstream implementation method. It needs to maintain the long-connection heartbeat between the App client and the server, which will bring additional power and traffic. Consumption; When designing the architecture, some compromises need to be made to avoid large consumption of traffic and power. In addition, the Push push technology has a relatively high complexity, maintaining a large number of long-term connection requests of the mobile App client, and establishing an encrypted channel for communication with the App client, integrating into a small number of limited internal long-term connections, and compressing and decompressing the communication data to save flow.

At present, the mobile Push technology is basically carried out in combination with these three schemes, but for different mobile terminal platforms, there are different implementations. Here, the specific implementation schemes on the iOS and Android platforms are introduced in detail.

iOS platform

For the iOS platform, due to its particularity, mobile Push is relatively simple. iOS applications do not allow the service to be resident in the background, so you have no other choice, and there is no way to complete the push by developing your own Push service. It is done through Apple APNS. The iOS mobile Push push process is shown in Figure 1.

Figure 1 iOS mobile PUSH push process

Android platform

On the Android platform, since there is no restriction on service resident, there are more available solutions: it can be completed through Google's official C2DM, open source solutions (such as XMPP), with the help of third parties, or completely self-developed mobile Push solutions. 
The main process of Google C2DM is shown in Figure 2.

Figure 2 C2DM mobile PUSH push process

The Google C2DM and Apple APNS processes are roughly similar, but the biggest problem is that the mobile Push server is located abroad, which is easy to be blocked, and the push delay is relatively large. In addition, due to the serious division of the Android community, many manufacturers directly removed the C2DM module, so this solution is extremely unreliable in China and has become a theoretical solution.

Mobile Push push open source solution

对于开源移动Push推送协议,常见的有XMPP等, 事实上Google的C2DM底层也是基于XMPP协议实现的,我们通过线下测试发现,开源移动Push推送方案主要有两个问题:第一,没有ACK机制,消息到达没有保证,不可靠;第二,当移动Push消息请求量并发增大时,系统开始变得不稳定,甚至出现了模块宕机的情况。因此直接使用移动Push推送开源方案,也不是非常可靠,我个人建议:在大规模使用开源的移动Push推送方案之前,必须做到对开源技术方案整体把握住,不然一旦出现问题,无法及时定位和修复的话,带来的后果将会是灾难性的。

借助第三方移动Push推送方案

除此之外,目前移动Push推送市场上,还有不少第三方推送产品可供选择,但需要面临以下几个问题:

  • 到达率 
    虽然第三方移动Push推送产品都宣传到达率高于90%,但是实际使用起来,发现远远达不到。当然到达率低的问题,除了第三方移动Push推送平台本身技术原因外,还和业务推送方的用户选取有很大关系,如果用户较活跃,到达率就会高些,如果用户不活跃,或者用户已经卸载了相应的App客户端,必然造成到达率进一步降低。

  • 实时性&控制度 
    第三方移动Push推送产品的推送通道是共用的,会面向多个推送客户,如果某一个客户Push推送量特别大,那么其他的消息实时性可能就会受到影响,这些都是业务推送方不可控的,会比较被动。

完全自主研发的移动Push推送方案

我们曾经考虑实现一套完全自主的移动Push推送平台,如果从零开始来做,需要解决几个难点:第一,移动Push推送服务端对移动App客户端海量长连接的维护管理。第二,App客户端常驻 service稳定性,如何使Push service常驻?我们可以借助父子进程互相监控的方式来做到,一旦发现对方进程不在了,会重新建立,继续循环监控。第三,手机内存不足时,系统会杀掉Push service,甚至有些操作系统比较强势,它会向iOS系统一样并不允许第三方Push service 常驻。第四,移动Push推送到达率的提高,除了技术手段外,还有一些PR的手段,比如移动App客户端Push service通过在相应操作系统上添加白名单的方式使其永久常驻。总之,在移动互联复杂的场景下如何让移动Push推送到达率变得更高,不是一件简单的事儿。

58同城移动Push推送方案

我们综合考虑前面讲述的开源、基于第三方、完全自主研发方案,58同城并没有选择从零开始完全自主研发而是采用了基于第三方移动Push推送平台和自主研发高性能Provider的方案(如图3所示),满足每天百亿量级的吞吐量,并通过动态组合和扩展的方式,结合离线的移动Push推送数据分析,不同手机使用不同的推送策略,针对性地优化。在Android平台,我们融合多种第三方移动Push平台,从而有效提升到达率。

图3 58同城移动PUSH推送平台技术架构

第一阶段(单平台):架构如何设计

背景&需求

2011年我们研发了58帮帮,这是一款满足58用户和商户之间沟通的即时通讯软件,用户间可以互相添加好友、收发消息等。58帮帮的消息推送基于App客户端和服务器的长连接,一旦这条长连接断开,那么IM服务端的消息将无法推送给App客户端,用户也无法看到这些消息。在iOS平台上,58帮帮App切换到后台后,App与IM的长连接断开,消息无法触达,这时候我们需要借助iOS APNS机制,IM消息需要发送给APNS,APNS再转发对应的消息到58帮帮App。Android切换至后台,App与IM的长连接保持,IM消息可以正常推送,因此在这个阶段我们需要解决的问题是在iOS平台上,当58帮帮App切后台后,IM在长连接断开后的消息触达需求。

设计目标

基于上述的背景和需求,我们在设计移动Push推送第一阶段(单平台)架构时,首先要满足在iOS平台上,当IM长连接断开后,IM消息的能够触达到App客户端。其次我们的移动Push推送协议设计也具备很好的扩展性,在可以预见的未来,Push推送平台将逐步接入更多的App,因此我们设计目标iOSProvider是一个通用的iOS推送服务。不同App通过使用不同的移动Push推送证书借助同一iOSProvider完成移动Push消息推送,对于不同App的接入,我们采用了配置文件方式动态扩展接入,iOSProvider根据所配置App证书与APNS建立并维护多条TSL连接。配置文件的格式如下:

其中,第一个域为推送服务类型Type,以备扩展,1为APNS;第二个域为内部定义的APPID号,对应服务的App;第三个域为App的Apple证书文件名;第四个域为与APNS建立的连接数; 
每个App接入的配置为一行,举例如下:

除此之外,iOSProvider需要对每个接入App的APNS连接池进行管理,动态增删TSL连接,具备动态重连机制,并具有单独的反馈接收线程,用于异步接收APNS返回无效的Token,反馈给移动Push推送业务方,用于下次移动Push消息推送的优化。iOSProdiver根据Type、APPID选择对应的APNS连接,通过推送线程组装APNS包发送到APNS服务器,如图4所示。

图4 iOSProvider架构图

第二阶段(多平台):架构如何设计优化

随着移动互联时代的到来,58同城研发了多个App,每一个App都有移动Push消息推送的需求(消息、运营活动、过期提醒等),并且每一款App同时具有多个终端:Android版、iOS版等。在这样的需求背景下,我们的移动Push推送平台需要继续演进,如何演进呢?

iOS移动Push推送通道可以很好的满足业务推送需求,但目前还不具备Android移动Push推送的能力,因此我们急需要研发Android移动Push推送通道。如何做?综合目前可选择的方案,我们选择了基于第三方推送平台以及自主研发高性能AndroidProvider的方案。

首先重点讲述针对Android移动Push推送的流程:第一,App客户端向第三方移动Push推送平台注册,获取对应的App唯一标示(Token)。第二,App将Token信息发送给AndroidProvider并集中存储,以便后续基于Token的移动Push推送。第三,AndroidProvider通过HTTPS或者TSL的方式和第三方移动Push推送平台建立连接,并把需要推送的消息发送到第三方移动Push推送平台。第四,第三方移动Push推送平台收到AndroidProver推送的消息后,会把此消息及时推送到App,从而完成整个推送过程,如图5所示。

图5 Android移动PUSH推送流程

AndroidProvider子系统整体结构分为四个层次,第一层为业务方移动Push推送接入,用于众多移动Push推送业务方的接入。第二层为网络交互层,用于接收移动Push推送业务方的消息数据以及发送请求处理层的处理数据给业务推动调用。第三层为请求处理层,用于处理网络交互层放入请求队列的数据,组装成第三方移动Push推送接口需要的数据,通过HTTP或者HTTPS的方式调用下游的接口,并等待请求结果的返回,把请求返回的结果放入回应队列。第四层为第三方移动Push推送平台,由第三方提供,开放给使用方接口,供调用其功能,如图6所示。

图6 AndroidProiver系统架构图

随着越来越多的移动App接入,移动Push推送需求趋向多样化,同时移动Push推送业务逻辑复杂化(多终端、批量发送、业务规则多样),公共策略每个业务方重复开发(深夜防打扰功能、发送频率和发送速率的限制等),造成开发效率低下。为了解决这些问题,我们抽象了公共的逻辑,并进行了统一的封装,对业务调用方透明,这些公共的逻辑包括:通用的策略和通用的控制,如图7所示。

图7 Android移动PUSH推送演进业务架构

在移动Push推送第二阶段(多平台)阶段,我们具备了Android、iOS的通道服务能力,满足推送消息的需求。但是我们没有提供统一的发送接口,业务方需要各自组包(Android、iOS)发送不同的推送通道,除此之外,推送通道性能方面还有待提升,推送通道稳定性还有待提升,此外推送通道包含了相对共同的业务逻辑,推送通道还不够“纯粹”。

第三阶段:架构和协议如何设计和优化

移动Push推送第二阶段还存在一系列的问题,因此在第三阶段需要解决,并且随着更多App接入,我们需要提供公司级统一的高性能移动Push推送平台。基于第三方移动Push推送平台,我们自主研发了满足每天推送百亿量级的高性能Provider,推送平台具备了高稳定性、接入方便,并提供了较高的推送到达率。

移动Push推送平台第三阶段我们如何架构和设计?首先我们满足对下游接入方多种连接的管理(HTTP、HTTPS、TCP、SSL、TSL),具备了多种连接动态伸缩性,从而满足Provider层对移动Push推送连接的要求。其次平台要具备高并发的特性,通过完全异步的设计和多线程支持,做到了高并发和支持10万QPS吞吐量。再次我们需要对接入下游的错误进行处理,一旦发现连接被断开等错误后,要能够自动使用新的连接,并且对已经发出还没到达App客户端的推送消息进行重发,以保证消息不丢失。第四我们需要对通道进行封装,对外提供统一的友好接入接口,屏蔽底层iOS和Android接入的差异性。最后在Android移动推送方面,我们接入了更多的第三方推送平台,以达到更高的到达率。

基于这些方面的考虑,58同城移动Push推送平台采用了低耦合的分层架构设计(如图3所示),分为三层Push Entry、Push Transfer、Provider(iOSProvider和AndroidProvider)。其中Push Entry是业务方调用的入口,我们采用异步消息队列的方式,提供了较高的业务方发送的速度,并且具备了消息缓冲的功能,使得高峰期的海量移动Push消息推送对整个平台冲击较少,也起到了保护推送系统的作用。Push Transfer会从Push Entry层接收消息进行解析,对推送消息进行合法性检查,如果格式不合法,直接丢弃,同时会进行接收到的推送消息格式转换成内部的消息格式,分平台转发到iOSProvider或者AndroidProvider上;provider接收到Push Transfer的消息后,会按照下游需要的消息格式(APNS协议、Android协议)进行转换,进行消息的下发,在下发的过程中,会进行消息的重发,以确保消息下发到第三方推送平台。

Provider模块内部如何设计?以iOSProvider为例,它分为三个层次:接入逻辑、业务逻辑、APNS出口。其中接入逻辑主要处理网络交互和请求分发;业务逻辑主要处理线程分裂扩展、并发处理和错误处理;APNS出口处理向APNS的发送逻辑,如图8所示。

图8 iOSProvider模块结构图

对于移动Push推送平台来说,追求达到率是我们最核心的指标,没有之一。因此在Android方面,我们融合了多个第三方推送平台,通过机型控制,对不同的机型使用不同通道,进一步提升推送到达率。AndroidProvider层进行消息推送策略的控制,先推送一通道,根据此推送通道ACK情况,是否继续推送其他通道。推送多个Push通道,会出现推送消息重复到达App客户端的情形,此时需要App客户端根据推送消息ID进行去重,收到的重复推送消息忽略处理。

典型性能问题分析解决以及高可用、高性能、高稳定性如何保证

在移动Push推送不断演进的过程中,我们遇到了AndroidProvider并发低的问题,仔细分析,是因为我们采用HTTPS库,由于库中HTTPS的连接实现不是线程安全的,对每个HTTPS的请求都加锁串行化处理,以保证线程的安全性。发现问题后,我们通过在线上增加多进程部署的方式暂时解决,使得我们有足够的时间分析此问题产生的根本原因。经过深入分析,发现原因是我们对HTTPS的库掌握不够,导致加锁粒度过大,通过HTTPS库提供的更小粒度的锁,我们不仅解决了线程不安全的问题,也提升了AndroidProvider的并发度,如图9所示。

图9 HTTPS库细粒度锁实现方式

总之,58同城统一的高性能移动Push推送平台通过无状态化设计和冗余部署等方式确保了推送平台的高可用,通过纯异步、动态多线程的支持提供推送平台的高性能,通过质量保证、多种监控机制(进程监控、语义监控、错误日志监控、数据波动监控等),有问题及时发现处理保证了推送平台的高稳定性。

最后,我要感谢项目组的同学,特别感谢姚劲同学,有了你们持续不断的努力和付出,才有了今天这篇文章;也感谢老婆大人,有你在背后默默的支持,才有了今天这篇文章。


孙玄:58赶集集团系统架构师,技术负责人,技术委员会架构组主任,也是58同城即时通讯、C2C技术负责人,负责58核心系统的架构以及优化工作。分布式系统存储专家,前百度高级工程师,参与社区搜索部多个基础系统的设计与实现。

本文为《程序员》原创文章,未经允许不得转载,订阅2016年《程序员》请点击 http://dingyue.programmer.com.cn

Guess you like

Origin http://10.200.1.11:23101/article/api/json?id=327100668&siteId=291194637