每个人都在谈论Serverless;几乎没有人知道如何实现Serverless;但是大家都觉得其他人在大力做Serverless;所以大家都说自己在做Serverless。本文将分享阿里巴巴资深技术专家对Serverless行业发展现状的一些看法。《喧哗与骚动》是我最喜欢的作家威廉·福克纳的小说。小说通过多个家庭成员的意识流,从不同的角度描绘了一个家庭三代人的悲剧。这部小说的有趣之处在于,对于同一件事,不同的人从跳跃的意识中可以看到完全不同的场景。今天大家明白Serverless也有这个意思,所以我就以此为题来分析一下。文章仅代表作者本人观点。Serverless就像青春期不知道你有没有听过这样的话:大数据就像青春期:大家都在谈论它,但没有人真正知道怎么做,每个人都认为其他人都在做,所以每个人都声称自己是做它。让我们改变大数据:人工智能就像青少年的性行为:每个人都在谈论它,但没有人真正知道该怎么做,每个人都认为其他人都在做,所以每个人都声称自己在做。让我们用Serverless取代AI:Serverless就像青少年性行为:每个人都在谈论它,但没有人真正知道该怎么做,每个人都认为其他人都在做,所以每个人都声称自己在做。由此我们可以总结出以下几点:每个人都在谈论Serverless;几乎没有人知道如何实现Serverless;但是大家都觉得其他人在大力做Serverless;所以大家都宣称自己在做Serverless。Serverless和微服务等很多词一样,没有准确的定义,也没有事实上的标准。什么是事实标准?Kubernetes是事实上的标准;SpringBoot/SpringCloud是Java程序员的事实标准。事实标准是一种已经被广泛实施并占领市场的想法/方法。落地通常意味着两点:它是开放的(opensource)。所以不会出现厂商锁定,大家可以放心使用;有很多成功案例。许多人在关键业务系统中使用它,因此它被广泛证明。今天的Serverless/FaaS领域有这样的东西吗?还没有。无服务器的愿景下图是来自GoogleTrends的图表,其中微服务为红色,无服务器为蓝色。自2016年AWS发布Lambda以来,全球开发者和云厂商对Serverless的热情持续高涨,可见大家对Serverless所描述的愿景非常认同。这个异象是什么?愿景是无服务器的?但是工程师们都知道,服务器本质上是存在的,顶多是加了一层抽象,让我们看不到服务器,但它仍然可以正常运行。我个人认为对Serverless愿景最清晰的描述是一个比喻,它来自加州大学伯克利分校今年2月发表的论文:简单地说:我们今天操作云资源的方式类似于几十年来早期程序员写的方式集会。如果你没有写过/学过汇编语言,或者忘记了汇编语言,我特意找到这本书拍下内容:感觉图中的寄存器、栈、程序计数器,以及相关的汇编指令?很陌生?如果让你用这样的语言来写业务逻辑,效率必然会变得很低。好在我们有Java、Go、JavaScript等高级语言,而且这些高级语言也配备了相关的编译器/虚拟机,可以高效的翻译面向业务的高级语言进入面向机器的汇编/机器代码。今天,虽然计算机的基本架构没有发生根本性的变化,但我们程序运行的环境与20年前相比已经发生了根本性的变化。20年前的大部分程序都是跑在单机上的,但是今天我们的程序都是设计来跑在云端的。为了让程序运行在云端,我们需要做配套的工作,包括云资源(容器、缓存、队列)的应用和回收,包括弹性伸缩的控制等等。这些东西和业务逻辑无关,但是研发/运维的同学却花了不少时间在上面。我想打个不成熟的比喻:在单机时代,操作系统管理硬件资源,依附于资源层,高级语言让程序员描述业务,依附于业务层,编译器/VM将高级语言翻译成机器码,交给操作系统;在如今的云时代,资源的单位不再是CPU、内存、硬盘,而是容器、分布式队列、分布式缓存、分布式文件系统。云端OS的作用基本上可以说是被Kubernetes生态承担了,那么云端的编译器/VM呢?开发语言和框架呢?好像没有这回事。今天,当我们将应用程序迁移到云端(也就是CloudNative)时,我们通常会做两件事:第一,将庞大的应用程序拆解成更小的应用程序,并将其变成微服务;二是成为yaml工程师,写很多yaml文件来管理云上的资源。从本质上讲,每个人都在将为单机架构编写的应用程序迁移到云架构。我认为这里有两个巨大的差距,这两个差距在图中用灰色框表示:1编程语言和框架目前主流的编程语言基本都是假设单机架构来运行。到时候在上面再套上一层相框。对应的资源还是停留在单机架构的那些资源上(当然这里也有例外,比如erlang/OTP天生就是为分布式设计的)。云时代,首先是基本的资源单元发生了变化,从原来的cpu、内存变成了容器、函数、分布式队列等;其次,云天生就是分布式的,单机时代流行的同步模型已经不适用了。2Compiler程序员不应该花很多时间写yaml文件。这些面向资源的yaml文件应该是由机器生成的。我称它们为云编译器。高级编程语言用于表达业务领域模型和逻辑。Cloud编译器负责将语言编译成资源描述。我个人喜欢Erlang的Actor模型,它也用其他语言实现,例如语法参考Ruby并运行在ErlangOTP上的Elixir,JVM上的Akka,以及.NET上的Orleans。不同于其他语言的设计,Actor模型从一开始就是基于分布式的前提下设计的。因此,如果将这种模式换成纯云资源管理对其对应的资源管理,我认为是非常可行的。一句话总结,我觉得Serverless的愿景应该是:写在本地,编译到云端。你在忙什么?除了仰望天空,谈论许多美好的愿景,你还必须低着头走路。我们先来看看这个。沿途其他人在做什么。我整理了过去一年Serverless行业发生的一些比较重要的事件。我建议你打开阅读这篇文章《Serverless 领域近一年行业发展回顾》(你可以在微信后台发送“评论”获取)。为了能够更清楚的看清这堆产品和技术,我简单的把serverless领域做的东西分成了三层,从下往上分别是资源层、DevOps层、框架和运行时层。资源层侧重于资源(如容器)的生命周期管理和安全隔离。这就是Kubernetes的世界,Firecracker、gVisor等产品都在做轻量级的安全沙箱。该层主要关注如何更快地生产资源并确保安全。DevOps层侧重于变更管理、流量分配和弹性扩展,以及基于事件的模型和云生态系统集成。这一层的核心目标是如何消除运维(NoOps)。虽然所有的云厂商都有自己的产品(各种FaaS),但我个人更喜欢Knative这种开源产品,原因有二:一是它的模型非常完备;二是生态发展非常迅速健康。很可能未来所有的云厂商都会兼容Knative标准,就像今天所有的云厂商都兼容Kubernetes一样。以下是过去一年Knative贡献者的增长和贡献数量。数据来自《KnativeaYearLater:Serverless,KubernetesandYou》演讲。至于framework和runtime层,由于个人经验有限,只看Java领域。其实核心就是解决Java应用(GraalVM)启动慢的问题。当然,框架如何避免供应商锁定也很重要。每个人都害怕被一个云厂商束缚,害怕另一个云厂商要改代码。这主要是通过SpringCloudFunction来完成的。一个产品要想成功,就需要有核心竞争力。这个核心竞争力,往往是你解决了一个用户头疼的问题,其他产品却解决不了的问题。这样的问题我姑且称之为用户的刚性需求吧。那么Serverless可以解决哪些用户的迫切需求呢?我先对用户做一些简单的分析:很多技术产品基本上都会经历以下四个阶段:初期,一个小团队围绕新业务做试错,从零开始,技术上,什么东西可以上线迅速地。这个时候团队规模很小,可能两三个人,所有的代码都放在一个应用里面,不需要分布式或者隔离。成熟期,业务成功,用户量不断增加,业务也越来越复杂。这个时候,团队的规模已经发展到几十人到几百人,团队还是一个部门。彼此之间有足够的信任,通信带宽也有足够的保障。一个应用模型已经不能满足协作的需要。架构师开始拆分应用,系统变成分布式,按照业务划分做流程级隔离。平台阶段的业务太成功了,所以希望把积累的能力赋能给其他类似的业务。与成熟期相比,此时有了一些新的变化。第一,参与开发的人数增加了,往往是数百人甚至数千人;第二,参与开发的成员大多不再是核心产品团队的成员,他们往往分属不同部门,互信度大大提高。减弱,通信带宽开始明显变窄。由于核心团队缺乏对其他部门开发的组织控制,因此优先考虑技术隔离需求,以防止平台上的开发人员不小心拖累平台本身。伴随着隔离,成本问题也每天都被提起。当平台上数百个插件运行在与平台本身相同的进程中时,资源自然被复用,整体可以模糊计算;当数百个插件被隔离在独立的容器中运行时,它们的资源使用需要额外的调度系统来控制和优化。云产品阶段平台太成功了,所以希望把它做成云服务,赋能社会同类业务,发挥更大的价值。如果说在平台时期,隔离只是一个重要但不是必须的需求(很多平台并没有真正做好隔离),那么云产品时期的产品就必须具备非常强的隔离能力。平台期对隔离的最大需求是稳定性(整个平台不会被平台上的开发者破坏),而云产品期对隔离的最大需求是安全。如图所示,产品上的开发人员已经和产品团队不在同一个组织,这样的开发人员可能是恶意的。因此,除了容器隔离,还需要虚拟机级别的隔离、网络隔离等。随着技术产品不断成长并不断取得成功,参与其中的开发人员数量不断增长,核心团队对这些开发人员的控制力越来越弱。通信带宽不断缩小,信任度不断下降,进而导致稳定性和安全性。风险在上升,这就需要不断提高隔离能力。随着隔离的引入和资源使用的增加,成本成为了不得不面对的问题。为了更好地分配资源,解决成本问题,提出了调度要求。所以对于平台阶段和云产品阶段的产品来说,技术隔离和调度能力是他们所需要的。框架和运行时创新上面提到的刚性需求都是从稳定性、安全性和资源成本的角度来讨论的。另外,我们还需要讨论另外一个话题,就是开发效率,而开发效率在技术上体现在框架上。我们可以进一步将框架分为两类:1)为了提高开发效率而面临技术问题的框架,如Spring通过依赖注入解决对象组装问题;HSF解决分布式同步通信问题;RocketMQ解决分布式异步通信问题;Hystrix解决分布式通信引入的不可靠网络等问题。通过使用这些框架,技术的自然复杂性在很大程度上得到了屏蔽。2)针对业务问题提高开发效率的框架阿里很多业务平台团队会根据自身场景(如交易、门店、供应链等)开发业务框架,以实现快速迭代业务的开发。通常,技术问题的框架会由一个团队开发,而业务问题的框架则由各个业务平台团队提供,这再次证明了康威定律的正确性。康威定律翻译成中文方言几乎就是“屁股决定脑袋”。技术团队不愿意接触业务问题,业务平台团队的框架在解决技术问题上不如技术团队专业。最后的结果是:二帧比较厉害。你可能听过这样一个故事:有一条恶龙每年都要村里祭祀一个处女。每年,这个村子都会有一位少年英雄与恶龙战斗,但无一幸免。另一位英雄出发时,有人悄悄跟在他身后。巨龙的巢穴里布满了金银财宝,英雄用剑将巨龙刺死,然后坐在尸体上,看着闪闪发光的珠宝,慢慢长出鳞片、尾巴和触须,最后变成了巨龙。虽然看起来有些夸张,但在我看来,这部分反映了主流框架在一些大中型研发组织中的现状:这些框架在组织发展史上发挥了极其重要的作用,但在今天,随着云服务的出现正在不断成熟,大家都在谈云原生。基于云构建业务系统时,框架需要强制用户绑定语言(如Java),而服务还没有做好,将逻辑插入到用户的应用中。中间。有的甚至要求用户的代码必须部署到平台的巨型应用中。这些限制在短期内实现了业务目标,交付了业务价值,但从长远来看,基本浇灭了业务发展对框架创新的积极性。他们更习惯于等待“ateamintherightposition”来解决问题,而“intherightpositionCorrectlypositionedteam”的学生可能一时半会感觉不到那些问题。毫不奇怪,当专注于short的框架时-组织内部的商业价值被推向云端,推向社区,面向更普遍更通用的需求,会得到更少的认可。传统的框架和运行时只在单机层面管理资源,但当每个人都使用云服务来构建自己的业务,框架和运行时需要管理的不再是单机资源,而是云资源。业界已经有很多这方面的产品,比较知名的有Terraform和Pulumi,但我觉得还不够。我觉得理想的云原生框架应该是这样的:可以帮助开发屏蔽对云资源的管理。开发不像写汇编那样喜欢写yaml,所以需要框架负责资源分配、回收、编排等;纯异步和事件驱动。这是由云的分布式特性决定的。如果编程语言范式还是同步模型,这个框架就无法实现;没有供应商锁定。不绑定实际的云厂商,只有厂商中立的开发框架才能被广泛使用。框架定义了编程API,具体厂商可以提供相关驱动;同时具备云资源管理和大规模软件开发所必需的编程范式。这里的编程范式可能描述的不太恰当,但是找不到更好的词,面向对象设计是最主流的编程范式,Spring就是围绕这种编程范式构建的。在一个框架中解决两个问题,将会带来很棒的开发体验。总结Serverless这个领域看起来非常美好,但是一旦深入其中,你会发现它其实非常复杂。这种复杂性体现在涉及的工程技术范围之广,用户预期的巨大差异,以及大家对未来的判断差异巨大。【本文为专栏作者《阿里巴巴官方技术》原创稿件,转载请联系原作者】点此查看作者更多好文
