在分布式系统的世界里,一些显著的变化正在悄然发生。对象存储正逐渐成为数据的基石,传统的事务处理和分析工具正融合为一,新的编程模型承诺带来更安全、可移植、应用状态管理简化或效率提升。这些变化不仅影响着系统的编程方式,还影响着它们的运营模式。尽管我渴望接纳这些创新,但选择前进的道路并非易事。
如果新技术只是提供微小的增量价值,大多数人会质疑投资的必要性。即使一项技术看似能带来突破性的改变,如果没有明确的迁移路径,或者迁移过程风险高,人们往往会选择谨慎。许多交易和分析系统转向使用对象存储,因为这带来了明显的价值提升,而选项的存在降低了风险。然而,对于新的编程模型,我们如何选择前进的道路仍显得模糊。如果人们无法理性地理解投资的价值,他们可能会继续沿用已知的技术,毕竟“没人会因为买了IBM而被解雇”。
我早就预见到事务处理和分析系统会发生变革,特别是关于对象存储和编程模型,但这并非因为我特别聪明或预测能力强,而是因为我有幸亲身体验了其中的一些。虽然我不能预知未来,但我愿意分享我的思考。
单扇门决策与双扇门决策
在莱克斯·弗里德曼的播客中,杰夫·贝佐斯阐述了如何通过单扇门决策和双扇门决策来管理风险。单扇门决策是最终决定,或是需要大量时间和精力才能改变的。这类决策要求我们放慢脚步,确保涉及正确的人,并尽可能收集信息。高层领导应在这些决策中发挥指导作用。
有些决策至关重要,一旦做出就难以回头,这就是单扇门决策。你需要深思熟虑,如果能找到其他分析方法,就应该暂停并执行。
——杰夫·贝佐斯
双扇门决策则相对不那么重要,如果做错了,可以随时调整方向。这类决策应迅速作出,通常由个人或小团队负责。高层不应在双扇门决策上浪费时间,因为这会削弱决策者的自主权。
——杰夫·贝佐斯
组织必须准确区分单扇门和双扇门决策。对双扇门决策应用重型决策流程代价高昂,但更糟的是,当一个原本是双扇门决策的问题被整个组织强制执行多年时,个人或团队可能做出了错误的单扇门决策。许多技术选择本质上是单扇门决策,因为它们需要大量投资,且更换成本高、耗时长。
对象存储
云对象存储已经存在近二十年,尽管它成熟可靠,但创新不断。由于对向后兼容性、系统集成和互操作性的关注,每次对对象存储的投资都像是双扇门决策,这将进一步推动采用、投资和创新的步伐。
多年前,我利用Azure Blob Storage的页面blob构建了一个工业数据共享的持久消息队列。对象存储提供了对象租约、原子写入、持久性和复制,使我们能够构建简单可靠的系统,无需担心领导选举、共识问题、数据复制等复杂性。读取端独立于写入端,无状态,可以独立扩展。尽管我当时所在的公司未能充分利用这一基础设施,但我深知对象存储架构的优势,并期待在未来再次遇到。
如今,从关系数据库、时序数据库到消息队列、数据仓库,甚至事务工作负载,许多系统都在核心架构中使用了对象存储,而不仅仅是分析工作负载或批量处理。此外,对象存储的功能也日益丰富,包括跨区域复制、不可变性、版本控制、分级存储、备份、读写一致性等。这些特性有助于满足行业规定、合规性、成本优化、数据生命周期管理、灾难恢复等需求,并以标准化的方式应用于服务中,无需在每个应用程序中直接实现。因此,对象存储不仅在架构层面吸引人,还简化了操作和一致性。
虽然我无法精确预测对象存储的未来发展,但我预计其在事务和分析系统中的流行度将持续增长。例如,将数据存储在Amazon S3的Parquet文件中似乎是个稳妥的选择。性能方面,随着延迟降低、带宽增加、缓存优化或索引改进,读取速度有望进一步提升,因为这对大量使用S3的应用程序有益。如果出现比Parquet更吸引人的存储格式,如Apache Iceberg或Delta Lake,我可以依赖开放表格式来管理这种演变,如果不想重新处理历史数据,或者在访问时或作为一次性批处理任务进行重处理。我不担心选择哪种开放表格式,因为它们都很优秀,功能趋同,并支持互操作性和迁移。
编程模型
未来十年最具颠覆性的变化可能是我们编程系统的方式,这将深刻改变软件开发和运行的本质,甚至我们对软件和基础设施的理解。大多数人尚未完全理解这一点。许多人看不到价值,几乎所有人都对如何实现这一转变持怀疑态度。虽然最终结果清晰,但前进的道路却充满挑战,因为所有的事物似乎都是单扇门决策,阻碍了采纳。
我多年来一直在期待编程模型的转变,这并非源于我个人的洞察,而是通过使用Akka这样的分布式计算工具,包括演员模型和流处理。我看到这些基本原理如何解决我在工业计算中长期面临的挑战,如流量控制、资源限制、状态管理、并发、分布、扩展和容错,而且是从根本原则出发。例如,演员模型可以用来表示物联网设备,管理状态,但执行和分布留给运行时,以线程安全的方式进行。Reactive Streams提供了一种接口,表达程序逻辑,同时让运行时处理系统动态,确保可靠性。我能预见这些模型逻辑上可以扩展到状态ful函数,甚至更远,正如我在2018年的主题演讲《从快数据到企业关键操作技术》中所描述的那样。
现在,有许多系统从不同角度尝试解决这些挑战,大致可以分为三类。第一类是抽象分布式系统中最困难部分的系统,如状态管理、工作流和部分失败。比如Kalix、Dapr、Temporal和Restate等。这类系统通常需要在你选择的编程语言中采用平台API。第二类除了抽象部分分布式系统难题外,平台还会执行二进制、容器或WebAssembly形式的任意代码。包括wasmCloud、NATS Execution Engine、Spin、AWS Fargate等。最后一类则是难以归类的,因为它们非常独特,如Golem,据我所知,它使用基于栈的WebAssembly虚拟机来持久执行程序,而Unison则是一种全新的编程语言和运行环境。
无论这些解决方案多么吸引人或工程精良,十年后,不是所有的技术或开发它们的公司将依然存在。尽管它们承诺解决重要问题并加速组织,但由于巨大的投资风险,选择技术几乎是不可能的。更重要的是,许多关键因素在于构建、部署、静态分析、调试、性能分析等工具的质量和成熟度,大多数工程师不愿放弃对整个堆栈的控制。此外,还有关于AWS、Azure、Cloudflare等云服务提供商如何通过一体化解决方案进入市场的疑问,目前看来,这似乎是一扇接一扇的单扇门。
在我看来,新的编程模型的最大机会是将应用中的大部分代码迁移到基础设施中,其次是剩余的业务逻辑,即程序的核心,要具有可移植性和安全性。一个具体的例子可以帮助理解我的思考。
现代程序中嵌入的几乎都是HTTP或gRPC服务器处理客户端请求,日志和指标库,数据库接口,对象存储,消息队列等。根据应用程序的更新、构建和部署时间,生产环境中可能运行着多个版本的辅助代码。修复关键安全漏洞时,找到受影响的服务可能是一项艰巨的任务。大多数组织没有成熟的软件清单,即使有,也只是帮助识别服务,还需要更新、构建、测试和重新部署。如果这些辅助代码能下移到基础设施层面,资源可以隔离、安全、监控、扩展、记录和单独打补丁,就像今天在Kubernetes集群下管理服务器一样透明。如果业务逻辑能这样描述和执行,那么在不同环境(如云端和IoT边缘)之间移动代码也变得可能。
为了鼓励采纳,新的编程模型需要将单扇门决策转化为双扇门决策。WebAssembly在这方面可能有所帮助,它提供了一种安全的可移植代码运行方式,WebAssembly组件模型可能是多个平台提供标准接口的基础。平台可能通过降低风险来鼓励采纳,对我来说,最重要的两点是:一是不必重写每一个应用,即提供某种迁移路径,而不仅仅是从零开始;二是如果我想切换到不同的平台,或将工作负载从云端迁移到自己的数据中心,或嵌入到IoT设备中,不会被锁定在一个供应商。
未来何在?
软件行业正在经历重大变革。未来的分布式系统将大不相同。得益于众多双扇门决策,数据库、事务系统和操作技术的分解正逐步融入对象存储。新的编程模型可能极具颠覆性,但由于单扇门决策过多,选择技术的胜者和败者变得异常艰难。保持现状似乎更容易。
在分布式系统中,没有完美的故障检测器。
我们无法隐藏复杂性……我们的抽象会泄漏出来。
——彼得·阿尔瓦罗
编程分布式系统之所以困难,是因为处理部分失败的挑战。可以说,对象存储的部分成功得益于那些不完全隐藏复杂性的抽象。新编程模型在不扭曲自身的情况下处理部分失败的能力还有待观察。然而,这些新系统令人兴奋,因为它们回归基础,只是抽象的界限有所不同。这应该导致系统变得更简单、模块化,关注点分离,更容易构建、运营、维护、安全和扩展。