Netflix的微服务深入应用之痛:工程原则矛盾的调和

社区编辑2018-05-14 17:30



作为一家架构在云上的公司,美国在线视频提供商Netflix积累了大量的技术实战经验,并开源了不少的团队成果,包括一些前沿的大数据、机器学习相关的技术。而Netflix在Docker容器和微服务(Microservice)方面的实践,也被业界广为传颂。从业者在Netflix的技术博客及该公司技术负责人的分享中,可以领略到前沿思想的光芒。这里要谈的是Netflix深入应用微服务的工程挑战与解决。

 

遭遇矛盾的工程原则

自由(Freedom)责任(Responsibility)是Netflix工程文化的基石,每一个团队/工程师都在为自己的核心使命自由地工作,团队为自己的系统完全负责,从设计、架构、开发、部署到运维。在这种情况下,基于需求的共性实现代码重用、整合,避免重造轮子,是很自然的想法。 

很早之前,Netflix就已经成功尝试了微服务,采用面向接口或服务的架构分离了界面与数据层,Netflix API成为Netflix微服务生态系统的“大门”。而Netflix的一项最新尝试,就是在跨团队协调API环境中的开发者代码和流程所有权——跨团队共享服务,正是要最大限度发挥Netflix微服务架构的价值。 

由于每个团队的自由和责任是不同,对数据的访问以及服务的依赖是不同的,所以微服务架构下不同开发者的需求矛盾是不言而喻的。Netflix工程经理Katharina Probst和Justin Becker在一篇技术博客文章《Engineering Trade-Offs and The Netflix API Re-Architecture》中概括说,他们正在进行的工作,就是“调和看似矛盾的工程原则:速度和完全所有权 vs. 代码重用最大化和代码整合”。 

作为“大门”,API提供了对构建响应各种请求所需的所有服务进行调用的逻辑。它从后端服务收集所需的信息,以任何需要的顺序,根据需要格式化和过滤数据,并返回响应。所以,Netflix API的核心是一个编排服务,通过组合微服务提供的细粒度功能来暴露粗粒度的API。 

目前,API服务暴露三类粗粒度的API:非会员(注册、计费、免费试用等),发现(推荐的节目和电影、搜索等)和播放(有关流媒体体验的决策、确保用户可以观看特定内容的许可、观看历史记录、收藏等)。这些API会调用其所需的各种底层微服务。有些服务的界限相对清晰,有些服务却是播放和非播放请求都需要的。




Netflix有两个团队,API团队负责编排层的设计,播放团队负责播放相关的API。但API团队需要负责整个API体系,包括发布、全天候支持、回滚等。这虽然对代码重用相当有用,但与另外的一条原则冲突:团队在生产环境中拥有和运维他们构建的东西。

所以,Netflix希望新架构能够实现如下两个目标:

  1. 每个团队生产环境中拥有和运维自己的代码,这样可以实现更有针对性的预警和更快的MTTR。
  2. 每个团队拥有自己的发布计划,并尽可能不被不相关的变更所影响。

 

两种解决办法 

为了实现未来的目标,Netflix思考了两种解决办法。第一种思路,API编排层以Pass-through的方式,将所有的播放请求直接发送给与专门的播放编排层(playback-specific orchestration layer),让后者处理与播放相关服务的编排工作。另外一些少量的共享服务,API编排层会用与播放编排层所需的信息对请求进行扩充,从而让相关服务顺利响应请求。




第二种方法,则是将API编排层简单地拆分为两套相互独立的API,分别负责播放请求的编排与非播放请求的编排。




这两种方式,都可以满足前述的目标,Netflix认为,这已经是很大的进步。具体的选择,则从开发者体验、组织影响和共享组件以及简洁性三个维度进行折衷思考。 

Probst曾在QCon New York 2016上表示,她计划改进单一API的方法。她认为,提供一个API在所有不同微服务及各个API之间扮演协调服务的角色,这种设计的问题是,各个服务对用户消费数据的方式没有多少控制权,并且API承担处理各种消费者请求的负担。这个API影响每个消费者服务,这就留下了一个单点故障的空间。 

另一种方法可以是确保每个微服务具有自己的API用于与消费者直接通信,但是将每个消费者请求的负担放于微服务上,不符合将其作为在最大生产率下完全独立服务的idea。 

Probst想保留单一API的方法,所有面向消费者的微服务都与之通信,但通过使用容器进行流程隔离来弱化单点故障的风险,解决微服务下共享工具和服务的痼疾。 

然而,在使用容器之外,Netflix对另外的一些API决策仍然没有一个清晰的答案,例如是通过多个协调API为底层服务提供更好的编排控制,还是减少现有API中的逻辑数量,以便它可以作为一个数据的接口很好地服务。这两种方法各有优势,但根据Netflix的暗示,解决方案是在不同取舍之间的折衷。 

 

小结

一位国内的知名架构师曾经说过:好的架构不是设计出来的,而是演进出来的。是的,从流量的角度,初创公司在初期很难预估百倍流量是什么样的情况,亦无资金、精力和人才去设计一个千万级大并发的流量架构;然而深入的实践,有一定业务规模和团队积累的企业,也未必能够演进形成一个一劳永逸的技术架构——勇于探索如Netflix,当前尚且不能找到一种完美的解决方案,“权衡”依然是必备的技能,但这不是一种很难三言两语说清楚的东西。所以,企业的容器和微服务实践,适合业务场景的云服务是不错的选择,专业的应用云化服务也是必要的。如果能有一个指导我们如何“权衡”的专业课程,就最好不过了。