基础架构是指支持应用程序的所有软件和硬件,包括数据中心、操作系统、部署流水线、配置管理以及支持应用程序生命周期所需的任何系统或软件。

已经有无数的时间和金钱花在了基础架构上。通过多年来不断的技术演化和实践提炼,有些公司已经能够运行大规模的基础架构和应用程序,并且拥有卓越的敏捷性。高效运行的基础架构可以使得迭代更快,缩短投向市场的时间,从而加速业务发展。

使用云原生基础架构是有效运行云原生应用程序的要求。如果没有正确的设计和实践来管理基础架构,即使是最好的云原生应用程序也会浪费。本书中的实践并不一定需要有巨大的基础架构规模,但如果您想从云计算中获取回报,您应该听从开创了这些模式的人的经验。

在我们探索如何构建云中运行的应用程序的基础架构之前,我们需要了解我们是如何走到这一步。首先,我们将讨论采用云原生实践的好处。接下来,我们将看一下基础架构的简历,然后讨论下一阶段的功能,称为“云原生”,以及它与您的应用程序、运行的平台及业务之间的关系。

在明白了这一点后,我们将向您展示解决方案及实现。

云原生的优势

采用本书中的模式有很多好处。它们仿照谷歌、Netflix 和亚马逊这些成功的公司 —— 不是单靠模式保证它们的成功,而是它们提供了这些公司成功所需的可扩展性和敏捷性。

通过选择在公有云中运行基础架构,您可以更快地创造价值并专注于业务目标。只需构建您的产品所需的内容,并从其他提供商那里获得服务,就可以缩短交付时间,提高灵活性。有些人可能因为“供应商锁定”而犹豫不决,但最糟糕的锁定是您自己建立的锁定。有关不同类型的锁定,以及您应该如何处理的更多信息,请参阅附录 B。

消费服务还可让您使用所需服务构建定制平台(有时称为服务即平台 [SaaP])。当您使用云托管的服务时无需精专于管理应用程序所需要的每项服务。这极大地加强了业务变更和业务增值的能力。

当您无法使用服务时,您应该构建应用程序来管理基础架构。当您这样做时,规模瓶颈不再取决于每个运维工程师可以管理多少台服务器。相反,您可以像扩展应用程序一样来扩展您的基础架构。换句话说,如果您能够运行可扩展的应用程序,则可以使用应用程序扩展您的基础架构。

同样的好处适用于构建灵活且易于调试的基础架构。您可以使用与管理业务应用程序相同的工具来洞察您的基础架构。

云原生实践还可以缩小传统工程角色之间的差距(DevOps 的共同目标)。系统工程师将能够从应用程序中学习最佳实践,开发工程师可以拥有应用程序运行所在的基础架构的所有权。

云原生基础架构的解决方案不一定适用于所有问题,您有责任了解它是否适合您的环境(参见第 2 章)。然而,在创造了这些实践的公司以及采用以该模式创建的工具的公司中,云原生基础架构的成功可以说显而易见。请参见附录 C 的一个例子。

在深入了解解决方案之前,先让我是探究一下是什么问题导致这些模式的出现。

服务器

在互联网早期,Web 基础架构始于物理服务器。服务器庞大,吵闹且昂贵,需要大量的电力和人员投入以保持它们的运行。需要细心照料,尽可能保持长时间运行。与云基础架构相比,购买这些设备让应用程序运行在上面会更困难。

一旦您买了服务器,它就是您的了,无论好坏,都要维护。使用物理服务器适合已确定成本的业务。持有物理服务器并运行的时间越长,您花费的钱越多。做适当的产能规划并确保您获得最佳的投资回报是很重要的。

物理服务器非常棒,因为它们功能强大,可以根据需要进行配置。故障率相对较低,使用冗余电源供应,风扇和 RAID 控制器来避免出现故障。也可以持续运行很长时间。企业可以通过延长保修和更换零部件,从购买的硬件中挤出额外的价值。

但是,物理服务器会导致浪费。服务器不仅没有被充分利用,而且还带来了很多开销。在同一台服务器上运行多个应用程序是很困难的。当在同一台服务器上最大限度得部署多个应用程序时,软件冲突,网络路由和用户访问都变得更加复杂。

硬件虚拟化承诺可以解决其中的一些问题。

虚拟化

虚拟化使用软件来模拟物理服务器的硬件。虚拟服务器可以按需创建,完全可以通过软件编程,只要您可以模拟硬件,就永远不会出现损耗。

使用 hypervisor 可以增加这些优势,因为您可以在物理服务器上运行多个虚拟机(VM)。它还使得应用程序可移植,因为您可以将虚拟机从一台物理服务器移动到另一台物理服务器。

然而,运行自己的虚拟化平台的一个问题是虚拟机仍然需要硬件来运行。公司仍然需要拥有运行物理服务器所需的所有人员和流程,但是现在容量规划变得更加困难,因为他们还必须考虑到虚拟机的开销。至少,公有云出现之前就是如此。

基础架构即服务

基础架构即服务(IaaS)是云提供商的众多产品之一。它提供了原始的网络、存储和计算能力,客户可以根据需要使用它们。它还包括一些支持服务,如身份和访问管理(IAM)、供应和库存系统。

IaaS 允许公司摆脱他们的所有硬件,并从别人那里租用虚拟机或物理服务器。这释放了大量人力资源,摆脱了购买、维护以及在某些情况下容量规划所需的流程。

IaaS 从根本上改变了基础架构与业务的关系。不是随着时间的推移受益的资本支出,而是运营业务的运营支出。企业可以像支付电力和人们的时间一样支付基础架构。通过基于消费的计费,您越早摆脱基础架构,运营成本就越低。

托管的基础架构还为客户提供了可消费的 HTTP 应用编程接口(API),以便按需创建和管理基础架构。工程师不需要购买订单并等待物品出货,就可以进行 API 调用,并创建服务器。服务器可以轻松删除和丢弃。

在云中运行基础架构不会使您的基础架构成为云原生。IaaS 仍然需要基础架构管理。在购买和管理物理资源之外,您可以(也有许多公司)认为 IaaS 与过去购买服务器在自己的数据中心架设的传统基础架构一模一样。

即使没有“货架和堆叠”,仍然有大量的操作系统、监控软件和支持工具。自动化工具帮助减少了运行应用程序所需的时间,但通常根深蒂固的流程会削弱 IaaS 的优势。

平台即服务

就像 IaaS 对 VM 消费者隐藏了物理服务器一样,平台即服务(PaaS)也对应用程序隐藏了操作系统。开发人员编写应用程序代码并定义应用程序的依赖关系,平台负责创建运行,管理和暴露它所必要的基础架构。与需要基础架构管理的 IaaS 不同,PaaS 中的基础架构由平台提供商管理。

事实证明,PaaS 限制要求开发人员以不同的方式编写应用程序,以便平台可以有效管理。应用程序必须包含允许由平台管理而不访问底层操作系统的功能。工程师不能再依赖 SSH 登入到服务器来读取磁盘上的日志文件。现在应用程序的生命周期和管理由 PaaS 控制,工程师和应用程序需要适应这个流程。

这些限制带来了很大的好处。应用程序开发周期变短了,因为工程师不需要花时间管理基础架构。在平台上运行的应用程序是我们现在称为“云原生应用程序”的开始。利用代码中的平台限制,已经一定程度上改变了当今编写应用程序的方式。

12 因素应用程序

Heroku 是提供公有 PaaS 的早期先驱之一。通过自己平台的多年扩展,该公司能够确定帮助应用程序在其环境中更好运行的模式。Heroku 定义了应用程序时应实现的 12 个主要因素。

这 12 个因素是通过将代码逻辑与数据分离来使开发人员更高效,尽可能自动化,独立的构建、传输和运行阶段过程;并声明所有的应用程序的依赖关系。

如果您使用 PaaS 提供商所提供的基础架构,恭喜您已拥有云原生基础架构的诸多优势。这包括 Google App Engine、AWS Lambda 和 Azure Cloud Services 等平台。任何成功的云原生基础架构都将向应用工程师展示自助服务平台,以部署和管理代码。

但是,许多 PaaS 平台不足以满足业务需求。它们通常会限制平台运行的语言、库和功能以实现从应用程序中抽离基础架构的承诺。公有 PaaS 提供商还将限制哪些服务可以与应用程序集成以及这些应用程序可以在哪里运行。

公有平台牺牲了应用程序的灵活性,使基础架构成为别人的问题。图 1-1 是如果您运行自己的数据中心,在 IaaS 中创建基础架构,在 PaaS 上运行应用程序或通过软件即服务(SaaS)运行应用程序时需要管理的组件的直观表示。

您需要运行的基础架构组件越少越好;但是在公有 PaaS 提供商中运行所有应用程序可能不是一种选择。

image
图 1-1. 基础架构层

云原生基础架构

“云原生”是一个过度使用的术语。尽管它已被市场所劫持,但仍具有工程和管理上的意义。对我们来说,它意味着在这个公有云提供商的世界中正发生的技术变革。

云原生基础架构是隐藏在有用的抽象背后的基础架构,由 API 控制,由软件管理并具有运行应用程序的目的。利用这些特征运行基础架构,能以可扩展高效的方式管理该基础架构。

当它们成功地向消费者隐藏复杂性时,抽象是有用的。它们可以实现技术的更复杂的使用,但是它们也限制了技术的使用方式。它们适用于底层技术,例如 TCP 如何提取 IP 或更高级别的技术,如虚拟机如何抽象物理服务器。抽象应该总是允许消费者“向上移动堆栈”而不是重新实现底层。

云原生基础架构需要抽象基础 IaaS 产品以提供自己的抽象。新层负责控制它下面的 IaaS,并将自己的 API 暴露给消费者控制。

由软件管理的基础架构是云中的一个关键区别点。软件控制的基础架构使基础架构能够扩展,并且在弹性、供应和可维护性方面也发挥着重要作用。软件需要了解基础架构的抽象概念,并知道如何获取抽象资源并相应地在可消费的 IaaS 组件中实现它。

这些模式不仅影响基础架构的运行方式,而且在云原生基础架构上运行的应用程序类型、在其上工作的人员类型与传统基础架构中是不同的。

如果云原生基础架构看起来很像 PaaS 产品,那么我们如何才能知道构建自己的产品时需要注意什么?我将快速描述一些领域,它们可能看起来像是云原生解决方案,但不提供云原生基础架构的所有方面。

什么不是云原生基础架构?

云原生基础架构不等于在公有云上运行基础架构。仅租用服务器并不会使您的基础架构云原生化。管理 IaaS 的流程与运行物理数据中心通常没有什么不同,许多将现有基础架构迁移到云的公司都未能获得回报。

云原生不等于在容器中运行应用程序。Netflix 最先推出云原生基础架构时,几乎所有应用程序都部署在虚拟机中,而不是在容器中。使用容器的方式打包应用程序并不能意味着拥有了自治系统的可扩展性和优势。即使应用程序是通过持续集成和持续交付渠道自动构建和部署的,也不等于就可以从 API 驱动部署的基础架构中受益。

也不是说只要您运行了容器编排器(例如 Kubernetes 和 Mesos)就是云原生架构。容器编排器提供了云原生基础架构所需的平台功能,但如果未按预期方式使用这些功能的话,那也只是将应用程序会动态调度到一组服务器上而已。这是一个非常好的起步,但仍有很多工作要做。

调度器与编排器

“调度器”和“编排器”这两个术语通常可以互换使用。

在大多数情况下,编排器负责集群中的所有资源使用(例如:存储,网络和 CPU)。该术语通常用于描述执行许多任务的产品,如健康检查和云自动化。

调度器是编排平台的一个子集,仅负责为进程和服务选择所运行的服务器。

云原生不等于微服务或基础架构即代码。微服务意味着更快的开发周期和更小的独立功能,但是单体应用程序可以具有相同的功能,使其能够通过软件有效管理,并且还可以从云原生基础架构中受益。

基础架构即代码以机器可解析的语言或领域特定语言(DSL)定义、使基础架构自动化。使用代码管理基础架构的传统工具包括配置管理工具,例如 Chef 和 Puppet。这些工具在自动执行任务和提供一致性方面很有用,但是对于为超出单个服务器的基础架构提供必要的抽象描述方面存在缺陷。

配置管理工具一次只自动化一台服务器,并靠人将服务器提供的功能绑定在一起。人成了管理大规模基础架构的潜在瓶颈。这些工具也不会使构建完整系统所需的云基础架构(例如存储和网络)的额外部分自动化。

尽管配置管理工具为操作系统的资源(例如软件包管理器)提供了一些抽象,但它们对底层操作系统的抽象还不足以轻松管理软件包。如果有工程师想要管理系统中的所有软件包和文件,这将是一个非常痛苦的过程,因为软件包对于每个配置变体来说都是独一无二的。同样,定义不存在或不正确的资源配置管理只会白白的消耗系统资源而不能给我们提供任何价值。

虽然配置管理工具可以帮助自动化部分基础架构,但它们无法更好地管理应用程序。我们将在后面的章节中通过查看部署、管理、测试和操作基础架构的流程,探讨云原生基础架构与配置管理工具的不同之处,但在此之前我们将了解何为成功的应用以及使用云原生基础架构的时机。

云原生应用程序

就像云改变了业务和基础架构之间的关系一样,云原生应用程序也改变了应用程序和基础架构之间的关系。我们需要了解与传统应用程序相比,云本身有什么不同,因此我们需要了解它们与基础架构的新关系。

为了写好本书,也为了有一个共享词汇表,我们需要定义“云原生应用程序”是什么意思。云原生与 12 因素应用程序不同,即使它们可能共享一些类似的特征。如果您想了解更多细节,请阅读 Kevin Hoffman 撰写的 Beyond the Twelve-Factor App(O’Reilly,2012)。

云原生应用程序被设计为在平台上运行,具有弹性、敏捷性、可操作性和可观测性。弹性能够容忍故障而不是试图阻止故障,利用了在平台上运行的动态特性。敏捷性允许快速部署和快速迭代。可操作性从应用程序内部控制应用程序生命周期,而不是依赖外部进程和监视器。可观测性提供信息来回答有关应用程序状态的问题。

云原生定义

云原生应用程序的定义仍在发展中。还有像 CNCF 这样的组织可以提供其他的定义。

云原生应用程序的这些特征是通过各种方式获取的。它通常取决于应用程序的运行位置以及企业流程和文化。以下是实现云原生应用程序所需特性的常用方法:

  • 微服务
  • 健康报告
  • 遥测数据
  • 弹性
  • 声明式的,而不是反应式的

微服务

作为单个实体进行管理和部署的应用程序通常称为单体应用。最开始开发应用程序时,单体有很多好处。它们更易于理解,并允许您在不影响其他服务的情况下更改主要功能。

随着应用程序复杂性的增长,单体应用的优势也在逐渐减小。它们变得更难理解,而且失去了敏捷性,因为工程师很难推断和修改代码。

对付复杂性的最好方法之一是将明确定义的功能分成更小的服务,并让每个服务独立迭代。这增加了应用程序的灵活性,允许根据需要更轻松地更改部分应用程序。每个微服务可以由单独的团队进行管理,使用适当的语言编写,并根据需要进行独立扩缩容。

只要每项服务都遵守强有力的合约,应用程序就可以快速改进和改变。当然,转向微服务架构还有许多其他的考虑因素。最后才考虑的是弹性通信,我们在附录 A 中有讨论。

我们无法考虑到迁移到微服务的所有考虑因素。使用微服务并不意味着就是云原生基础架构。如果您想拓展阅读,我们推荐 Sam Newman 的 Building Microservices(O’Reilly,2015)。虽然微服务是实现应用程序灵活性的一种方式,但正如我们之前所说的,它们不是云原生应用程序的必需条件。

健康报告

停止逆向工程并开始从应用内部进行监控。

——Kelsey Hightower,Monitorama PDX 2016:healthz

没有人能比开发者更了解应用程序需要哪些条件才能健康运行了。曾经基础架构管理员都试图为自己负责运行的应用程序定义“健康”状态。在不了解是什么因素真正使应用程序的健康的情况下,监控和告警应用程序的不健康时状态往往是脆弱和不完整的。

为了提高云原生应用程序的可操作性,应用程序应该暴露健康检查。开发人员可以以命令或过程信号的方式实现,以便应用程序在执行自我检查之后响应,或者更常见的是:通过应用程序提供 Web 服务,返回 HTTP 状态码来检查健康状态。

Google Borg 示例

Google 的 Borg 报告中列出了一个健康报告的例子:

几乎每个在 Borg 下运行的任务都包含一个内置的 HTTP 服务器,该服务器发布有关任务运行状况和数千个性能指标(如 RPC 延迟)的信息。Borg 会监控运行状况检查 URL 并重新启动不及时响应或返回 HTTP 错误代码的任务。其他数据由监控工具跟踪,用于仪表板和服务级别目标(SLO)的告警。

将监控应用健康的责任转移到应用程序内部,这使得应用程序更容易管理和自动化。应用程序应该知道自己是否在正常运行以及自己的依赖(例如,访问数据库)。开发人员需要与产品经理合作来定义应用服务的业务功能并相应地编写测试。

提供健康检查的应用程序示例例如 Zookeeper 的 ruok 命令和 etcd 的 HTTP 健康端点。

应用程序不仅仅有健康或不健康的状态。它们将经历一个启动和关闭过程,在这个过程中它们应该通过健康检查,报告它们的状态。如果应用程序可以让平台准确了解它所处的状态,平台将更容易知道如何操作。

平台需要知道应用程序何时可以接收流量,这就是一个很好的例子。在应用程序启动时,如果它不能正确处理流量,它就应该表现为未准备好。此额外状态将防止应用程序过早终止,因为如果运行状况检查故障,平台可能会认为应用程序不健康,并且会反复重启它。

应用程序健康只是自动化应用程序生命周期的一部分。除了知道应用程序是否健康之外,您还需要知道应用程序正在进行哪些工作。这些信息来自遥测数据。

遥测数据

我们使用遥测数据(telemetry)来进行决策。遥测数据可能与健康报告重叠,但它们用途不同。健康报告汇报应用程序的生命周期状态,而遥测数据汇报应用程序的业务目标。

我们测量的指标有服务等级指标(SLI)或关键性能指标(KPI)。这些是特定于应用程序的数据,可以确保应用程序的性能处于服务级别目标(SLO)内。如果您需要更多关于这些术语的信息以及与应用程序、业务需求的关系,我们推荐您阅读来自 Site Reliability Engineering(O’Reilly)的第 4 章。

遥测和度量标准用于解决以下问题:

  • 应用程序每分钟收到多少请求?
  • 有没有错误?
  • 应用程序延迟怎么样?
  • 下单需要多长时间?

通常会将数据抽取或推送到时间序列数据库(例如 Prometheus 或 InfluxDB)进行聚合。遥测数据需要被收集数据的系统格式化。

至少需要实施度量标准的 RED(Rate、Error、Duration)方法,该方法收集应用程序的到达率、错误和执行时间。

到达率(Rate)

收到了多少个请求

错误(Error)

应用程序有多少错误

持续时间(Duration)

多久才能收到回复

遥测数据应该用于告警而不是健康监测。在能够动态自我修复的环境中,我们不关注应用程序单个实例的生命周期,更关注的是应用程序的整体 SLO。健康报告对于自动应用程序管理仍然很重要,但不应该用于站点工程师。

不管应用程序是 1 个实例还是 50 个实例不健康,只要满足应用程序的业务需求,我们就可能不会收到警报。Metric 会告诉您是否满足 SLO,应用程序的使用方式以应用程序是否是“正常”。告警有助于您将系统恢复到已知的良好状态。

它移动,我们就追踪。如果没有移动我们就也会画一些图形,以防它突然开始运动。

——Ian Malpass,Measure Anything, Measure Everything

警报(Alert)不应该与日志记录混淆。记录(Logging)用于调试、开发和观察。记录暴露了应用程序的内部功能。Metric 有时可以根据日志(例如错误率)计算,但需要额外的聚合服务(例如 ElasticSearch)和处理。

弹性

有了遥测和监控数据后,还要确保应用程序有故障自适应能力。弹性是基础架构的责任,但云原生应用程序也需要承担部分工作。

基础架构设计之初就是要抵御故障(failure)。硬件通常需要有多个硬盘驱动器、电源以及全天候监控和可更换的部件以保持应用程序可用。云原生应用程序应当正视故障而不是避免故障。

在任何平台上,尤其是云上,可靠性都是其最重要的特性。

——David Rensin,e ARCHITECT Show:来自 Google 的关于云计算的速成课程

光是讲如何设计弹性的应用程序可能就可以写一本书了。我们将在云原生应用程序中考虑弹性的两个主要方面:面向故障设计和优雅降级。

面向故障设计

唯一永远不会故障的系统是那些与您的生命安全息息相关的系统(例如心脏植入物和刹车系统)。如果想要让服务永远运行,您需要花费太多时间设计服务来抵御故障,那样就没有足够的时间增加业务价值。SLO 确定服务需要运行多长时间。您花费在工程设计上超出 SLO 的正常运行时间的任何资源都将被浪费掉。

每项服务您可以测量两个值,平均无故障时间(MTBF,Mean Time Between Failure)和平均恢复时间(MTTR,Mean Time To Recovery)。通过监控和 metric 可以知道是否达到 SLO,但运行应用程序的平台是保持高 MTBF 和低 MTTR 的关键。

在任何复杂的系统中,都会有故障。您可以管理硬件中的某些故障(例如,RAID 和冗余电源),以及某些基础架构中的故障(例如负载平衡器)。但是因为应用程序知道他们什么时候健康,所以他们也应该尽可能地管理自己的故障。

设计一个以故障期望为目标的应用程序将比假定可用性的应用程序更具防御性。当故障不可避免时,将会有额外的检查,故障模式和日志内置到应用程序中。

没人可以预料应用程序所有可能的故障。假设所有东西都可能会故障,这是一种云原生应用程序的模式。

应用程序的最佳状态是健康状态。第二好的状态是故障状态。其他一切都是非二元的,难以监控和排除故障。Honeycomb 首席执行官 Charity Majors 在她的一篇题为“Ops: It’s Everyone’s Job Now”的文章中指出:“分布式系统永远不会起作用;它们处于部分退化服务的持续状态。接受故障,面向设计设计,保护和缩小关键路径。“

无论发生什么故障,云原生应用程序都应该是可适应的。它们预期故障,所以他们在检测到时进行调整。

有些故障不能也不应该被设计到应用程序中(例如,网络分区和可用区故障)。该平台应自主处理未集成到应用程序中的故障域。

优雅降级

云原生应用程序需要有一种方法来处理过载,无论是应用程序还是负载下的相关服务。处理负载的一种方式是优雅降级。 “站点可靠性工程”一书中描述了应用程序的优雅降级,因为它提供的响应在负载过重的情况下“不如正常响应准确或含有较少数据的响应,但计算更容易”。

减少应用程序负载的某些方面由基础架构处理。智能负载均衡和动态扩展有助于减轻应用程序的负载,但有的时候,应用程序可以承受的负载比它可以处理的负载更多。云原生应用程序应知道这种必然性并作出相应的反应。

优雅降级的重点是允许应用程序始终返回请求的响应。如果应用程序没有足够的本地计算资源,并且依赖服务没有及时返回信息,则这是正确的。如果一个服务依赖于一个或多个其他服务,即使依赖的服务无应答,该应用程序也应该可以应答。还有种解决方案是,当服务降级时,返回部分应答或使用本地缓存中的旧信息应答。

尽管优雅的降级和故障处理都应该在应用程序中实现,但是平台的多个层面也应该提供帮助。如果采用微服务,则网络基础架构将是在提供应用弹性方面发挥积极作用的关键组件。有关构建弹性网络层的更多信息,请参阅附录 A。

可用性数学

云原生应用程序需要在基础架构之上建立一个平台,以使基础架构更具弹性。如果您希望将现有应用程序“提升并转移”到云中,则应检查云提供商的服务级别协议(SLA),并考虑在使用多个服务时会发生什么情况。

如果在云上运行应用程序,我们来看下可用性会是怎样。

计算基础架构的典型可用性是每月 99.95%的正常运行时间。这意味着您的实例每天可能会停机 43.2 秒,这仍在您的云服务提供商的 SLA 中。

另外,实例的本地存储(例如 EBS 卷)也具有 99.95%的正常可用时间。如果幸运的话,他们都会同时出现故障,但最糟糕的情况是他们可能会在不同的时间停机,让您的实例只有 99.9%的可用性。

您的应用程序可能还需要一个数据库,而不是自己安装数据库,可能的停机时间为 1 分 26 秒(99.9%可用性)的情况下,选择可靠性为 99.95%的更可靠的托管数据库。这使您的应用程序的可靠性达到 99.85%,或者每天可能发生 2 分钟 9 秒的停机时间。

将可用性乘到一起可以快速了解为什么应以不同方式处理云。如果云提供商不符合其 SLA,会退还您账单中一定比例的费用。

虽然您不必为停机支付费用,但您的业务必须能够容忍云计算的信用保证。如果云平台的可用性保证无法满足您的应用程序的可用性需求,那么您应该考虑是否该在云上运行这个应用程序。

声明式,非反应式

由于云原生应用程序设计为在云环境中运行,因此它们与基础架构和支持应用程序的交互方式与传统应用程序不同。在云原生应用程序中,与任何事物进行通信都是通过网络进行的。很多时候,网络通信都是通过 RESTful HTTP 调用完成的,也可以通过其他接口,如远程过程调用(RPC)来实现。

传统的应用程序会通过消息队列,写在共享存储上的文件或触发 shell 命令的本地脚本来自动执行任务。通信方法对发生的事件作出反应(例如,如果用户单击提交,运行提交脚本)并且通常需要存在于同一物理或虚拟服务器上的信息。

Serverless

Serverless 平台是云原生化的,面向事件响应而设计。通过 HTTP API 进行通信使得它们在云中工作得很好,是单用途函数,在它们的函数调用中声明。该平台还可以通过在云中进行扩展和访问来提供帮助。

传统应用程序中的反应性通信常常是通过增强弹性。如果应用程序在磁盘或消息队列中写入文件,然后应用程序崩溃,则消息或文件的结果仍可能完成。

这并不是说不应该使用像消息队列这样的技术,而是说不应该将它们作为动态和不断发生故障的系统中的唯一弹性层。从根本上讲,应用程序之间的通信应该在云原生环境中改变 —— 不仅因为还有其他方法来构建通信弹性(请参阅附录 A),还因为在云中复制传统通信方法往往需要更多工作。

当应用程序可以信任通信的弹性时,应该停止使用反应式并开始使用声明式。声明式通信相信网络将传递消息,也相信应用程序将返回成功或错误。这并不是说应用程序监视变化并不重要。Kubernetes 的控制器正是这样做到 API Server。但是,一旦发现变更,它们就会声明一个新的状态,并相信 API Server 和 kubelet 会做必要的事情。

声明式通信模型由于多种原因而变得更加健壮。最重要的是,它规范了通信模型,并且它将功能实现从应用程序转移到远程 API 或服务端点,从而让实现某种状态到达期望状态。这有助于简化应用程序,并使它们彼此的行为更具可预测性。

云原生应用程序如何影响基础架构?

希望您已经了解云原生应用程序与传统应用程序不同。云原生应用程序不能直接在 PaaS 上运行或与服务器的操作系统紧密耦合。它们期望在一个拥有大多数自治系统的动态环境中运行。

云原生基础架构在提供自主应用管理的 IaaS 之上创建了一个平台。该平台建立在动态创建的基础架构之上,以抽象出单个服务器并促进动态资源分配调度。

自动化与自治不一样。自动化允许人类对控制系统采取更多行动。

云原生是关于不需要人类做出决定的自治系统。它仍然使用自动化,但只有在决定了所需的操作之后。只有在系统不能自动确定正确的事情时才应该通知人。

具有这些特征的应用程序需要一个能够实际监控,收集度量标准并在发生故障时做出反应的平台。云原生应用程序不依赖于人为设置 ping 检查或创建 Syslog 规则。它们需要从选择基本操作系统或软件包管理器的过程中提取自助服务资源,并依靠服务发现和强大的网络通信来提供丰富的功能体验。

结论

运行云原生应用程序所需的基础架构与传统应用程序不同。基础架构的许多责任已经转移到应用程序中。

云原生应用程序通过分解为更小的服务来简化其代码复杂性。这些服务提供直接构建到应用程序中的监控、指标和弹性。需要新的工具来自动管理服务数量的激增和应用的生命周期。

现在基础架构负责整体资源管理、动态协调、服务发现等等。需要提供一个平台,使服务不依赖于单个组件,而是依赖于 API 和自治系统。第 2 章将更详细地讨论云原生基础架构功能。