管理开口巴:基于 MQTT 协议的实时通信编程模型

iOS11针对性WKWebView的效应更是全面,新增如下效果:

概要

有人常问,云巴实时通信系统到底提供了平等种何等的劳务,与任何提供推送或
IM
服务之厂商有哪里本质区别。其实,从技术角度分析,云巴与其余同类厂商都是面向开发者的通信服务,宏观之编程模型都是各有千秋,真正差异则聚焦于活一定,业务模式,基础技术水平等重重细节上。本文暂无讨论具体产品形态上的距离,着重从技术角度浅谈实时通信的编程模型。

  1. Manager Cookies
  2. Fileter unwanted content
  3. Provide custom resources

咦是实时通信

「实时」(realtime) 一歌词在语义层面上含蓄着对时间的封锁(real-time
constraint),在工程上,我们习惯对「需要在必然时间外」
完成的操作称为「实时操作」。通常,实时可密切分为 「软实时」(soft
realtime),「准实时」(firm realtime)和 「硬实时」(hard
realtime)。它们中的歧异,简单来说,就是对准无法在指定时间距离内(deadline)完成工作之隐忍程度。维基百科上针对就三哟有如下解释:

  • Hard – missing a deadline is a total system failure.
  • Firm – infrequent deadline misses are tolerable, but may degrade
    the system’s quality of service. The usefulness of a result is
    zero after its deadline.
  • Soft – the usefulness of a result degrades after its deadline,
    thereby degrading the system’s quality of service.

一经我们管无法按期完成任务(missing a
deadline)称为不行事件,那么硬实时系统无法耐受异常事件;准实时系统则只是忍极少量的那个事件,但跨一定数额后系统可用性为
0;软实时系统而是忍异常事件,但是每有同样次等很事件,系统可用性降低。

概括,我们好举例:

  • 火星上的无人探测器是健康时系统,因为同一软特别事件就顶生或造成探测器不可用,同理可类推核电站的监督体系,军用无人机系统,远程导弹的导航系统等一律名目繁多军工产品;

  • 金融交易系统是准实时系统,此类系统而是忍极少数的贸易故障,一旦故障次数增加,系统便会见陷于崩溃状态;

  • 短信 / 手机推送 /
    电商购物等都是软实时系统。对于此类系统,用户还可以忍受异常事件,但是最好多之十分事件则会大幅减退系统可用程度,用户体验急剧下挫。

尽管现阶段吧,绝大多数互联网产品(甚至好说凡是
100%)都是软实时系统。云巴实时通信系统的对象虽然是使召开一个强可用的软实时系统

脚是针对一一特性的简单介绍,详细而参见源码。

一个无限简便易行的实时通信编程模型

于软件工程被,很多错综复杂的品种其实都得据此一个万分简洁的型来概括。正使爱因斯坦所说之:「一切还应该尽量地概括,但并非太简单」(Everything
should be made as simple as possible, but not
simpler)。虽然这是讲述物理世界之经验之谈,但同样适用于计算机领域,将大体世界之涉嫌投射到某种人为语言(物理公式/计算机编程语言),其原理其实还是共通的。

为我们设这么一个略的观:本着 10 个客户端发送一长达消息

其一需求实际上可以据此伪码表示也:

for (i..10) {
    send_message(get_socket(i))
}

若下图所示:

管理 1

以斯大概的需要下,我们只有待被这 10 单客户端独家同服务器建立 TCP
连接(本文暂时就谈谈 TCP
协议),然后遍历地发送信息即可。显而易见,这是一个 O(N) 复杂度的逻辑。

基于此简单的型,我们好认为相同修信息于出到接收,有以下几只延时:

  • 纱延迟 ,一般是一个较为安静之价,比如从京及深圳,ping
    延迟大约为 40 ms 左右;

  • 系处理延迟,较之网络延迟,该值变化幅度比较充分,且可能以处理要求数的多而狠增大;

说道巴实时通信系统以 200 ms
延迟作为总延迟标准,也就是说,假如网络链路是起京城至深圳,除去网络延迟的
40 ms,要想上 200 ms 的通信时间,系统延迟必须低于 160 ms。

足想象,当客户端数量达一定数额级(比如百万级别)时,以上系模型的实时性将面临极端严酷的考验。

1.Manager Cookies

iOS11激增了一个看似来特别管理Cookies:WKHTTPCookieStore。它要含有了了针对性Cookie的操作:删除、添加、获取等。
据这种光景:
一个页面默认登录,当自家莫登录的下会弹有输入框,输入账号。输入完以后,会提示已经报到。再次打开该页面时,页面会先判断发生没发cookie,有cookie直接提示已登录,没有cookie则再次弹框让用户登录。
然而现在发只新需求:第一坏安装APP,启动之时候就发出只默认的账户登录,而非待弹框输入。这便因此到了cookie的长。在APP将要加载webView之前,通过HTTPCookie来初始化一个实例,将其塞到webView的configuration的数据存储着。这样加载WebView时即都来cookie存在了。这样即便打熬了首不好默认登录的职能。关键代码如下:

let cookie = HTTPCookie.init(properties: [
            .domain:"172.16.10.26",
            .path:"/src/p/index/index.html",
            .version:0,
            .expires:Date.init(timeIntervalSinceNow: 30*60*60),
            .name:"username",
            .value:"zhanggui33"
            ])

let cookieStore = myWKWebView.configuration.websiteDataStore.httpCookieStore

cookieStore.setCookie(cookie!) {

            self.myWKWebView.load(URLRequest.init(url: URL.init(string: "http://172.16.10.26:3333/src/p/index/index.html")!))
        }

呢不怕是于加载网页前,将cookie注入。更多可参见这里源代码。

分而治之

以海量用户下保持平静的实时性,其实过多时段就是单发生一个手法:分而治之

希冀 1
表示的凡单机处理状态。当单机的处理能力,带富都无法答应本着客户端数量可以增加的当儿,我们尽管非得以线路开展分割。而且图
1
只体现了推送的用意(单向),但通信往往是一个双向的概念,综上,我们将 
1
 改成为下面的 图 2

管理 2

如此这般各个台机器就得处理符合该手上水位的连天。

于切实开发被,我们可能不仅仅满足于一个这样简约的信网,我们恐怕想要发离线消息,数据统计,数据缓存,限流等同样密密麻麻操作,所以我们尚足以重优化一下架构:

  • 用完全架构划分成业务逻辑层和数据存储层;

  • 数量存储层又可以根据存储数据类型的差来更是细分;

  • 前端可以独立划分一个网接入层;

  • 数据包的流向可以用 MQ 来串联;

如此咱们得以获以下的图 3:

管理 3

在这模型中,网络接入层和信息业务逻辑层整体达标应当是一个 stateless
的模块,可以比较轻松地举行横行扩展。存储层作为一个发状态的模块,想使到位横行扩展是一律宗很不爱的政工。如果遗弃开这点来拘禁,至此,这个模型理论及在承诺本着海量用户之光景下应该是立竿见影的。

2.Fileter unwanted content

除此以外一个初特色即是过滤而不思量如果的情节。比如说你于app中加载的网页中带有http请求,你可以根据以下规则以http资源加载之前转换成为https加载。这个是苹果官方演示的一个规则:

let jsonString = """
            [{
                "trigger":{
                    "url-filter": ".*"
                },
                "action":{
                    "type": "make-https"
                }

            }]
            """

这边要采取了WKContentRuleListStore。下面就是来详细对那个进展介绍。

通信协议和技巧栈的选项

举行一个信息网,不可避免地设干到对通信协议的精选。我们当针对通信协议的选择上,遵循以下几个规格:

  • 商量尽可能精简轻量,因为当系统规划的新我们尽管考虑了对物联网的支撑,省电,节约流量都是目标之一;

  • 通用性好,扩展性强,方便后期做特色开发;

  • 协和于业界为大承认,且尽量多的发出两样语言的开源实现,以福利不同技能栈的客户做并;

综上,我们尚无再打定义一客通信协议,而是选择了依据长连接的 MQTT。从很多角度来拘禁,MQTT
非常适合做信息总线的通信协议,而且协议栈也够轻巧和容易落实。云巴实时消息网传输的音体积比较小(一般小于
4 KB),比如控制信号,普通聊天信息相当。就顿时点达到,针对物联网设计的 MQTT
有在原之优势。后面,在时时刻刻地研究被我们以发现,MQTT
其实不仅适用于物联网场景,在重重求小顺延高稳定性的非物联网场景也一律适用(比如手机端
app 推送,IM,直播弹幕等)。

于眼前几单章节我们视,云巴信息网是一个天下无双的 IO
密集型系统。在由开发效率以及安静之设想下,我们挑选了 Erlang/OTP
作为主力开发语言。Erlang/OTP
作为同样派系小众开发语言(无论是国内或国际),在应付当时好像 IO
密集型系统上,有着出色的优势(可参考 RabbitMQ 这个基于
Erlang/OTP 的头面开源项目):

  • 依据 actor 的历程创造模型,可以啊每个数据包创建一个 Erlang
    处理进程,充分利用多对;

  • OTP
    的支付框架抽象了分布式开发之广大细节,使得开发者在十分粗的心智负担下虽会轻松便捷地开出功能原型;

  • Erlang/OTP
    充分运用了容错思想,应针对异常不是谨防,而是容,很多时节咱们形容来有安康逻辑上发出漏洞的代码,在
    Erlang/OTP 上竟也会办事得美好的;

随着不断深入地使 Erlang/OTP,
其属性问题为逐渐凸显出来。我们发现,当客户端请求量增加的时候,用
Erlang/OTP 写有之模块轻而易举地就是得以 CPU
跑满,从而让眼前实例超负荷运转。很多时光由于成本及的勘查,我们鞭长莫及取舍重复多核数的机械来提升
Erlang
虚拟机运行的性质(此点未明朗说明了),所以不得不选择相当增加服务处理实例来解决压力。

可是,通过对事情模块更周密粒度的剪切,我们可以有为主的略微模块用 C/C++
语言改写,在自然限制的复杂度内,可以中提升整体处理性能。这吗是我们连下去优化中心系统的思绪之一。

创一个Trigger字典

一个trigger的字典总得使含有url-filter这个key,它指定了匹配url的模式。其他的饶是可选的了,例如你可限制指定的域名,让该域名的情无加载。例如下面的之trigger规则,制定了用来图片以及体裁资源的规则trigger,不含有写域名及之:

"trigger": {
        "url-filter": ".*",
        "resource-type": ["image", "style-sheet"],
        "unless-domain": ["your-content-server.com", "trusted-content-server.com"]
}

除上面提到的trigger
key,还有url-filter-is-case-sensitive、is-domain、unless-domain、resource-type等。具体的详尽介绍好参见管理法定解释。

MQTT 的 Pub/Sub 模型与高可用 KV 存储

MQTT 协议下的是 Pub/Sub
的编程模型。其中起三独比重要的动作:publishsubscribe 和 unsubsribe。通过前几单章的讨论,我们以足以得如此一个现象:

苟是一个订阅量巨大的 topic(百万层),如何当单次 publish
中管实时性 ?

实在,解决思路及之前的面貌是均等的:分而治之。我们得通过某种政策对
topic 进行分片,然后用分片分发及不同的 publish
模块上进展拍卖。在得之算法复杂度下,这个题目理论及是好叫中缓解之。于是,topic
的分片策略就是成为了高性能 publish 的关键。其实,如果想使 MQTT
做海量信息网,订阅关系之军事管制得是无力回天绕开的很题目。它至关重要出以下几单计划难点:

  • 如采取 KV 方式囤,如何统筹数据结构
    ?同齐,我们设什么样去规划相同种高效的 topic 分片存储策略;

  • 订阅关系之田间管理是 MQTT
    消息网的着力模块,假如这存储模块失效,就决然会招信息通信失败,从而被客户端了不顶信息,这就是务须要求是模块一定是赛可用之,也不怕意味着我们得构建一个高可用的
    KV 存储集群,该集群要能隐忍一定水平的节点失效;

  • 冷热 topic 要发淘汰机制,要发生一定策略将无活跃的 topic
    定期淘汰到磁盘以省内存容量;

  • KV 存储集群要能够快地动态扩容;

每当生丰富一段时间的实施备受,我们使用过一些种植 KV
存储的集群方案,踩了诸多坑,最后还是决定好往轮子来开发一个胜似可用之 KV
存储模块。不过就又是一个雅十分之话题,我们将以延续博客中实际阐述我们的做法。

开创一个Action字典

当trigger匹配到了符合条件的资源,浏览器就是会履及trigger相关联的操作。当有着的trigger都为评估后,action便会仍顺序执行。
Action只生零星独key:type和selector。type是得使有,selector可选,如果type是css-display-none,那么selector也是必要有些。其他的type中selector是可选的。
type的路有:block、block-cookies、css-display-none、ignore-previous-rules、make-https。更多得瞻仰合法说。
比如我思屏蔽页面被有图片的加载:

 //把所有的图片阻塞加载
        let jsonString = """
            [{
                "trigger":{
                    "url-filter": ".*",
                    "resource-type":["image"]
                },
                "action":{
                    "type":"block"
                }
            }]
            """
        WKContentRuleListStore.default().compileContentRuleList(forIdentifier: "demoRuleList", encodedContentRuleList: jsonString) { (list, error) in
            guard let contentRuleList = list else { return }
            let configuration = self.filterWebView.configuration
            configuration.userContentController.add(contentRuleList)
            self.filterWebView.load(URLRequest.init(url: URL.init(string: "http://m.baidu.com")!))
        }

再次多词义的分解还是看合法文档,里面介绍的不行详细。

短和不足

以社前进最初,由于人力及时空相当类因素,我们把工作逻辑模块出成了一个高大的单体架构使。在组织规模比较小之图景下,单体架构的使用确实于好保护和支出,但随着新人的进入,单体架构则严重制约着特性开发以及总体性优化。从架构层面达到来拘禁,合理地划分更密切粒度的模块,在性及可维护性上采用微服务(microservice)设计模式,成了我们前途优化系统的样子之一。

3.Provide custom resources

夫特点允许而提供自定义之资源,这为堪实现离线缓存。例如你拿装有的图纸都放app里面,然后网页加载图片时仍一定的scheme(比如:wk-feature://cat)来加载,然后以客户端代码中采用一定的SchemeHandler来分析即可。这里关键行使了WKURLSchemeHandler和WKURLSchemeTask。
重大代码如下:

        let configuration = WKWebViewConfiguration()
        let schemeHandler = MyCustomSchemeHandler.init(viewController: self)

        configuration.setURLSchemeHandler(schemeHandler, forURLScheme: "wk-feature")

兑现了投机之SchemeHandler,然后对一定的Scheme进行拍卖。

总结

软件工程达到生「没有银弹」(No Silver
Bullet)这长达则,用户挑选开口服务商亦凡这般,绝对没有两全的老三着说服务商,每一样下都可能在鲜明的优点和缺点。用户必须由自己行使场景以及痛点出发,选择适合的后端服务。云巴将会见于自己活之核心竞争力上频频发力,精打细磨,吸取行业外之快速实践经验,打造起更为可观的胜可用实时通信系统。

总结

使您还在以UIWebView,那么尽快更换也WKWebView吧。毕竟苹果还赞成被WKWebView。不断地拿该功能丰富。而且经过了几个版迭代,使用WKWebView的坑也都慢慢填平。

附源码

1.WKWebViewNewFeature

参考

  1. Customized Loading in
    WKWebView
  2. Introduction to Safari Content-Blocking
    Rules

转载请注明来源:http://www.cnblogs.com/zhanggui/p/8260136.html

Post Author: admin

发表评论

电子邮件地址不会被公开。 必填项已用*标注