写点什么

专访滴滴出行李贤辉:滴滴 iOS 客户端的架构演变之路

  • 2016-03-17
  • 本文字数:2994 字

    阅读完需:约 10 分钟

滴滴出行作为国内互联网出行平台的代表,短短几年时间就从一个小小的创业公司成为一线互联网公司,发 展速度令人瞩目,在如此快速的发展之下,滴滴 App 在架构上又经历了哪些演变?InfoQ 记者采访了滴滴出行平台产品中心 iOS 技术负责人李贤辉,了解了 滴滴 iOS 客户端的架构演变之路。

受访嘉宾介绍:

李贤辉,滴滴出行平台产品中心 iOS 技术负责人。多年客户端开发经验,2010 年加入百度日文输入法部门,2011 年从 C/C++ 的 PC 端开发转到百度音乐移动端的 iOS 开发,2013 年加入滴滴。

InfoQ:请向大家介绍一下您自己,您是何时加入滴滴的?

李贤辉:大家好,我是李贤辉,业余时间喜欢踢踢足球和旅行。我在 2013 年 5 月加入滴滴,目前是平台产品中心的 iOS 负责人,经历了滴滴的 2.0 到现在的 4.2.5 版本,并且随着滴滴的快速发展和业务增加,团队规模也不断扩大,业务上经历了拆分整合的过程。很幸运能进入一线互联网公司,选择了热门的技术方向,并且跟 随快速增长的创业公司一起成长。

InfoQ:在滴滴高速发展的过程中,iOS 客户端架构发生了哪些大的改变?

李贤辉:2013 年 5 月,我们启动了滴滴 2.0 ,主要是 UI 交互方式的改变,采用了 MVC 的方式,代码结构上做到了更清晰。

2014 年 5 月,新增了专车业务线,需要支持出租车、专车 2 个业务线,启动了滴滴 3.0 的开发;借鉴了游戏里的状态机,把订单中的阶段,例如:出租车的等待抢单、出租车的等待接驾、专车的等待抢单、专车的等待接驾,都当成一种独立的状态,每 个状态机只需要知道可能要导向的状态机,从而做到了相对独立,状态机满足了出租车、专车双业务线的需求。

2015 年 1 月,滴滴开启了多元化,需要快速上线顺风车、代驾、试驾、巴士等多项业务,代码耦合严重,功能开发和协同发版成为痛点;滴滴的技术团队分散在北京、杭州、上海,不在同一个城市,而需要在同一个 App 里进行发布,客观上增加了架构的难度。

2015 年 6 月到年底,滴滴进行代号为 The One 的组件化框架开发,为了实现“代码治理”,可以“分而治之”的目标,在各个业务线各自开发的情况下防止代码大面积腐化,方便未来再做更加细致的架构重构, 采用 CocoaPods 的方式进行拆分;组件化之后,公共部分拆分为技术组件、公用业务组件,每个业务线是单独组件,如出租车组件、专车组件、快车组件; 通过把不同功能的组件代码拆分到不同的 pod 里,实现了业务线仅依赖于公共就可以迭代开发,改善了功能开发和协同发版。组件化只是做了治理的第一步,后面的架构优化还任重而道远。

InfoQ:目前滴滴 iOS 采用的是哪种架构模式?在 controller 瘦身上有哪些实践?

李贤辉:目前滴滴的 iOS 架构采用 MVCS 和 MVVM 的架构方式。MVCS 的 S 是 Store 的意思,包括服务器访问接口控制、数据共享、数据缓存的能力,每个 Store 处理一类情况,例如:订单 Store 会包括发单、取消订单、结束订单、评价订单等,常用地址 Store 会包含编辑常用地址、删除常用地址、拉取常用地址等。MVCS 这种方式的思考逻辑是希望做到组件无状态,完全依赖于 Store 所返回的各种状态信息,这种思想是非常类似于 React Native + Redux 的思路。

项目启动时,原计划用 Objective-C / Java 这种原生代码做一个类似于 React Native 的框架,但是工作量过于巨大且不成熟,不适合在 The One 这种量级项目中使用,后来没有开发该框架。采用 MVCS 的同时也采用 MVVM,用 VM 为 Controller 减肥,但 VM 要通过 Store 处理数据层逻辑,达到了为 Controller 瘦身的目的。

InfoQ:滴滴 iOS 客户端的组件化是如何划分的,采用什么技术实现?

李贤辉:我们在 15 年后半年实施了组件化,组件包括技术组件和业务组件,技术组件是可以跨 App 使用的,例如:网络组件(长连接和短连接)、界面导航管理组件(统一界面转场方式,模块间界面转场,通过 openURL 方式解耦);根据业务功能,已经实 现了支付、登录、消息、定位、广告 SDK、数据统计、分享等组件,每个组件是独立的 CocoaPods。

组件采用私有 CocoaPods 来实现,并采用了 Local Pods 的方式,可以在本地不提交代码的情况下,组件与调用方实现调试。组件间的页面间跳转支持 openURL 的方式,由 ONERoute 模块进行管理,页面在 +(void)load 方法中完成注册,ONERoute 内部保存一份 URL 与 Class 的对应表,当调用 openURL 时,会查找到对应的类,然后生成对应的实例对象。这种方式可以通过 URL 解耦具体的类名称,方便从 H5 拉起 Native 页面,未来还可以实现流程的可配置化。在设置页面里,还是直接依赖类的方式,避免过度使用 openURL。为了增加安全性,每个页面会设置是否允许外部打开,仅有允许外部打开的页面才可以通过系统的 openURL 方式打开。

InfoQ:从客户端展现来看,滴滴需要同时获取快车、的士、专车等的实时数据,在数据的传输、展示上有哪些挑战?滴滴是如何应对的?

李贤辉:挑战如下:

(1) 消息不及时:如乘客发单后,有司机抢单了,需要尽快知道。后来采用了 socket 长连接,使服务端具备主动通知客户端的能力。

(2) 流量过大:我们和服务器交互较多,流量消耗较大。我们现在在用 protobuf 作为数据载体,有效的减少了流量消耗。

(3) 数据易被修改:共享业务数据多,最初没有限制修改数据的权限,出现一些莫名其妙的问题;后来一方面减少共享的业务数据,并且共享数据对外,尽量是只读,如 果某个状态来源于服务器,则只能在模块内部,在收到服务器结果时,修改接口数据,即 MVCS 的 Store 内部可以修改数据。

(4) 共享地图是另外一个挑战,为减少内存占用,业务线之间切换流畅,在滴滴首页只能有一份地图实例。首页作为主页面,包括导航栏、地图、多个业务线子页面。为 了降低对业务线代码的侵入性,业务线首页从系统的 UIViewController 派生,由首页来设置业务线首页的背景色为透明色;业务线首页的 UI 元素,会在业务线内部完成处理;而在地图模块的操作,首页会收到手势,通过把手势传递给地图模块,使地图得到响应;此外,为了使业务线之间的地图元素互不 干扰,每个业务线的都包括一块独立画布,所有地图元素都在独立画布里处理,当切换业务线时,移除原画布上的所有元素,切换回来时,再恢复画布内容。

InfoQ:你们是否使用了热修复技术,目前实践情况如何?

李贤辉:滴滴采用了 Lua 和 JSPatch 两种热修复技术,由于 JSPatch 更加被苹果官方认可,目前在线上主要使用 JSPatch。我们还在开发一套 JSPatch 发布平台,内部使用者可以通过后台可以下发和管理脚本,并且处理传输安全等部署工作,提供了脚本后台管理、版本管理,并保证传输安全等功能。

InfoQ:滴滴 iOS 团队和 Android 团队的代码共同情况如何?

李贤辉:iOS 和 Android 团队在 socket 长连接库使用了同一份代码,iOS 和 Android 底层都是 Unix 系列的内核,对于网络操作是一致的,可以使用同一套系统接口,其次,这套代码的稳定性要求很高,功能与系统无关,一份代码可以降低人力消耗,并保证一致 性。对于和系统相关的功能,都采用设计思路一致,iOS 和 Android 分别开发的方式。

InfoQ:在对新技术的应用上,滴滴目前是否有用过 Swift?或者准备何时采用?

李贤辉:滴滴目前还没有用 Swift,因为在 iOS 8 及以下的平台上,使用 Swift 需要将 Swift 运行时打包到 App,会增大 App 体积。滴滴的乘客端由于受限于即将超过 100M 的包体积,目前还没有采用 Swift 的计划。滴滴的出租车司机端预计在下一季度会小范围尝试 Swift 。

2016-03-17 09:4411305
用户头像

发布了 164 篇内容, 共 108.1 次阅读, 收获喜欢 392 次。

关注

评论

发布
暂无评论
发现更多内容

前端开发之动态管理Nginx集群的方法

@零度

nginx 前端开发

低代码实现探索(十五)安全检查报告提高低代码数据安全性

零道云-混合式低代码平台

skywalking核心概念

淡泊明志、宁静致远

基于实例数据详解准确率和召回率

华为云开发者联盟

数据集 AUC 信息检索 准确率 召回率

在Spark Scala/Java应用中调用Python脚本,会么?

华为云开发者联盟

Python spark python脚本 Spark Scala Java应用

助力产教融合,夯实数据库产业人才基座!openGauss社区分委会正式成立

openGauss

【量化】量化交易入门系列6:量化交易学习书籍推荐(二)

恒生LIGHT云社区

量化策略 量化投资 量化交易 量化

面试官惊叹,好小子!你这多线程基础可以啊!

XiaoLin_Java

1月月更

使用Amazon Redshift Simple Replay实用程序简化Amazon Redshift RA3迁移评估

亚马逊云科技 (Amazon Web Services)

mad

风口上的“低代码”,是时候来系统学一学了!

博文视点Broadview

低代码实现探索(十四)工程化思想提高项目质量与可维护性

零道云-混合式低代码平台

为什么零售业需要借助CRM系统蓬勃发展

低代码小观

企业管理 CRM 企业管理系统 CRM系统 企业管理软件

MySQL高级特性篇教程

编程江湖

MySQL

从四种时序数据库选型中脱颖而出,TDengine在工控领域边缘侧的应用

TDengine

数据库 大数据 tdengine 物联网

开源demo| 智慧协同demo升级——协同更直观方便

anyRTC开发者

音视频 白板 智慧协同 开源demo 远程协助

恒源云(GPUSHARE)_语音识别与语义处理领域之低资源机器翻译综述

恒源云

机器翻译 语音识别

【网络安全】你必须知道的几个网络安全概念

行云管家

运维 网络安全 防火墙 IT

openGauss 助力邮储银行分布式新核心迈向智能运维时代

openGauss

霸屏综艺,牵手明星,扩列神器皮皮APP的出圈始末

联营汇聚

linux系统管理与自动化运维工具用哪款好?

行云管家

Linux 运维 IT运维 自动化运维

Linux云计算好学吗?Linux云计算运维学习资料 vim编辑器和恢复ext4下误删文件

学神来啦

使用 Simple Replay 实用程序简化 Amazon Redshift RA3 迁移评估

亚马逊云科技 (Amazon Web Services)

mad

workflow 之 Prefect 基本用法(qbit)

qbit

工作流 pipeline workflow 数据流

万字详解 Spark 数据倾斜及解决方案

五分钟学大数据

spark 1月月更

中山市政务服务数据管理局党组书记叶永忠:积极构筑智慧联接新底座,打造中型智慧城市标杆

InfoQ_967a83c6d0d7

3个重点,20个函数分析,浅析FFmpeg转码过程

奔着腾讯去

音视频 WebRTC ffmpeg RTMP RTSP

Mysql索引

zdd

MySQL

工具 | 如何对 MySQL 进行 TPC-C 测试?

RadonDB

MySQL RadonDB

斯图飞腾数据分析平台Stratifyd获评“2021大数据产业创新服务产品”

InfoQ_967a83c6d0d7

效果提升28个点!基于领域预训练和对比学习SimCSE的语义检索

百度大脑

人工智能

openGauss数据库源码解析系列文章——存储引擎源码解析(五)

openGauss

专访滴滴出行李贤辉:滴滴iOS客户端的架构演变之路_移动_徐川_InfoQ精选文章