解决方案架构师技巧 - 解读 AWS 无服务器设计原则
如果你曾以任何身份与 AWS 合作过,你可能已经了解到他们有一套独特的做事方式。他们开会时会先默默地阅读文件,启动新项目时会采用逆向思维,而且无论做什么,他们都会严格贯彻自己的领导原则。
亚马逊之所以能几乎掌控全球市场,是有原因的。他们的经营模式行之有效。
他们提供的众多帮助企业构建一流软件的资料中,就包括他们的通用设计原则。如果您曾经参加过AWS 的架构完善性审查,那么您就会对这些原则了如指掌(这是好事)。
如果你热衷于构建无服务器应用程序,AWS 有一套完全不同的设计原则你应该遵循。他们以架构完善模型的核心支柱为基础,并从无服务器应用程序的角度来审视这些支柱。
今天我们将了解全部 7 项原则,并讨论作为解决方案架构师,这些原则如何转化为你的设计。
1. 快速、简单、单一
函数简洁、简短、用途单一,其运行环境能够满足其请求生命周期的需求。事务高效且成本意识强,因此优先选择更快的执行速度。
这意味着——函数(在本例中是 Lambda 函数)应该专注于特定任务。它们启动、执行任务,然后停止运行。
尽可能缩短执行时间。尽可能利用异步工作流。将任务放入 SQS 队列进行进一步处理,并停止发起该任务的 Lambda 函数的执行。尽量避免在同一个 Lambda 函数内部调用另一个 Lambda 函数。
函数应遵循单一职责原则。如果需要执行两个不同的操作,请考虑使用两个单独的函数。
2. 考虑并发请求,而不是请求总数
无服务器应用程序利用并发模型,并在设计层面上根据并发性来评估各种权衡取舍。
这意味着——不要花费大量时间试图弄清楚如何优化流程,使其请求数量尽可能少。那不是重点。
这条原则至关重要,因为它告诉解决方案架构师,在高峰时段要依靠无服务器应用程序的横向扩展能力。如果遵循第一条设计原则,你的函数就会简洁高效,响应时间仅需几百毫秒。
高峰时段,您的应用程序将自动横向扩展。即使每分钟处理 10 万个请求,最终用户也只会感觉自己是唯一的用户,速度非常快。软件能够轻松应对高负载。
考虑到这一点,不必过于担心请求数量。设计系统时,应充分利用 AWS 的自动扩展能力。
如果可以将一个耗时较长的任务拆分成多个部分,那就去做。这条设计原则强调的是横向扩展而非纵向扩展。通过将一个庞大而繁重的任务分解成一个个独立的小任务,可以提高软件的性能,同时降低成本。
 拍摄,来自 [Unsplash](https://unsplash.com/s/photos/not-sharing?utm_source=unsplash&utm_medium=referral&utm_content=creditCopyText)](/upload/0-jvqg.jpg)
照片由Annie Spratt拍摄,来自Unsplash
3. 不分享任何东西
函数运行时环境和底层基础设施生命周期较短,因此无法保证临时存储等本地资源的可用性。状态可以在状态机执行生命周期内进行操作,因此对于高持久性需求,持久化存储是更佳选择。
这意味着——假设函数是无状态的。每次需要操作实体状态时,都访问数据库。不要依赖全局变量。
优化 Lambda 性能的一个技巧是全局实例化 SDK 客户端(参见第 19 页幻灯片),但仅此而已。由于 Lambda 函数会全天频繁启动和关闭,你永远无法预知哪些客户端会存在,哪些客户端会不存在。
每次执行都像对待全新程序一样,每次都加载所需内容。
4. 假设不存在硬件亲和性
底层基础设施可能会发生变化。例如,CPU 标志可能无法始终可用,因此请使用与硬件无关的代码或依赖项。
这意味着——您选择无服务器架构是有原因的:为了避免处理硬件问题。无服务器函数旨在比 CPU 标志或其他硬件命令更高层级地运行。
设计系统时,不要考虑服务器端硬件。使用环境变量进行配置,并在实现之后对函数进行性能优化。
5. 使用状态机而不是函数来编排你的应用程序。
在代码中串联 Lambda 函数来编排应用程序的工作流会导致应用程序变得臃肿且耦合度过高。相反,应该使用状态机来编排事务和通信流程。
这意味着——如果您遵循了原则 1 和 2,您应该已经设计出一个健壮的模块化系统。一条命令可能需要 4 到 5 个 Lambda 函数才能完成。请记住,这是一件好事。您已经使系统能够横向扩展,并在此过程中实现了更高的吞吐量和性能。
不要从其他 Lambda 函数内部调用其他 Lambda 函数。这样做速度更慢,AWS 将其视为反模式,而且成本更高。成本更高的原因是,您需要为内部 Lambda 函数的执行时间和调用 Lambda 函数的等待时间付费。
Step Functions 的设计初衷就是为了解决这些问题。它们能为您提供易于理解的工作流程状态机图,以及无与伦比的执行过程可追溯性。
如果 Step Function 对您的系统来说有点吃力,您可以尝试使用Express 工作流,它更轻量级,吞吐量/并发性更高,收费与 Lambda 类似。
6. 使用事件触发交易
诸如写入新的 Amazon S3 对象或更新数据库等事件允许根据业务功能执行事务。这种异步事件行为通常与消费者无关,并驱动即时处理,从而确保精简的服务设计。
这意味着——异步操作是你的好帮手。你的客户无需等待系统中发生的一切。拥抱事件驱动架构吧。
这是软件工程师的自然思维方式。如果这件事发生了,那么另一件事也应该发生。
无服务器应用程序本质上是分布式系统。为了使各个组件协同工作,可以使用一些基本事件,例如新文档上传完成时触发的事件,或者数据库写入后触发的DynamoDB 流,以便执行后续操作。
软件不再需要同步运行
设计系统时,要以尽可能减少用户等待时间为目标。
7. 设计时要考虑故障和重复情况
由请求/事件触发的操作必须是幂等的,因为可能会发生故障,并且同一个请求/事件可能会被多次传递。下游调用应包含适当的重试机制。
这意味着——异常情况时有发生。有时,由事件触发的 Lambda 函数会随机失败。作为解决方案架构师,您必须设计一个能够处理相同请求并执行相同结果的系统。
这就是幂等性。
你应该在应用程序中(几乎)每个 Lambda 函数中都设计幂等性和重试机制。Step Functions 提供了一种简便的方法,可以在出现问题时使用可配置的退避率来重试 Lambda 函数。
由于无法可靠地保证请求会按正确的顺序到达,或者只会到达一次,因此在设计系统时考虑到这一点至关重要。
结论
AWS 在这方面确实非常专业。在设计无服务器解决方案时,最好把这些信息记在心里。
我们都希望系统快速、可靠且经济高效。遵循 AWS 无服务器设计原则就能确保实现这些目标。
所以记住,要保持专注。保持规模小。设计时要考虑并发执行。不必过于担心调用次数(在一定程度上)。使用托管服务进行编排。设计时要考虑到可重放性。
无服务器架构有时可能会让人望而生畏,甚至有些吓人,但它需要实践才能掌握。优秀的解决方案架构师能将复杂的问题转化为复杂的解决方案,而卓越的解决方案架构师则能将复杂的问题简化为简单的解决方案。
力求卓越。正确使用工具。
干杯。
文章来源:https://dev.to/aws-builders/solutions-architect-tips-decoding-the-aws-serverless-design-princples-413n
,作者为 [Joseph Mucira](https://pixabay.com/users/jmexclusives-10518280/?utm_source=link-attribution&utm_medium=referral&utm_campaign=image&utm_content=5614048)。](/upload/1-dgsi.jpg)