专注数据才能发现逻辑
英文有句话:Focus on the data, not on the logic. The logic will emerge when you understand the data( 专注于数据,而不是逻辑。当你理解了数据,逻辑将出现)。 从这里看出数据和逻辑的显隐关系,这大概也是50年的数据库系统构建 版本控制系统和面向对象语言能够告诉我们的。
随着Docker与DevOps的兴起,开发人员与运维人员正在融合,而业务日志应该是研发人员与运维人员的桥梁,也是每个研发人员必须掌握的数据抽象。来自LinkedIn的Kreps发布了其具有程序员史诗般的博文:日志是每个软件工程师关心的统一数据抽象
Kreps首先指出日志以前都是用来记录数据库交易的记录,以防止出现错误或应用崩溃后,能够撤销之前的更改操作,或者在磁盘等媒介出问题后重新执行这种更改操作,以及用来做简单的审计和附加信息的修订。
他很有见地提出分布式状态机对于分布式系统设计的重要性:
“你可以把用多台机器一起执行同一件事情缩减为为这些进程输入分布式一致性的日志数据。这里使用日志的目的是把所有非确定性的东西排除在输入流之外,这样来确保每个复制都能够同步地处理输入。”
其中将非确定性排除出输入流之外非常亮眼。因为这点非常容易被忽视。
Kreps在考量了各种各样的历史信息系统的使用,提出如下观点:
“这可能会引起你对源代码版本管理的联想。源代码管理和数据库之间有密切关系。版本管理解决了一个大家非常熟悉的问题,那也是分布式数据系统需要解决的--- 时时刻刻在变化着的分布式管理。版本管理系统通常以补丁的发布为基础,这实际上可能是一个日志。您可以直接对当前源代码 类似于表一样做出一份"快照"。你会注意到, 与其他分布式状态化系统类似,版本控制系统在 当你更新源码时会复制到日志,当你提交新代码时,你只是将更新应用到你的当前快照中而已。 ”
这个观点实际指出关于系统的历史业务数据非常有价值的,我们只能在数据库中获得某个当前的状态,而无法知道是通过如何操作得到当前的状态。而业务日志则保存了系统的历史操作数据。
一个日志处理系统和版本控制系统之间是有差异的,日志处理系统只记录一个时间表,在版本控制系统允许您有多个行历史。版本控制系统提供基本分支和合并功能,这使得它们比数据库系统更复杂和更强大。
Kreps提出了数据表与事件是一对情侣,它们相互印证:
“这些日志有点类似借贷清单和银行的流程,数据库表记录的是当前的盈余表。如果你有大量的操作日志,你就可以使用这些操作从而创建可以捕获当前状态的表”
这个观点和我们在领域事件/CQRS架构倡导的状态和事件分离是一致的,从某种程度上将,我们使用EventSourcing来记录领域事件然后播放,也是为了获得系统某个时刻的状态快照,这种原理与数据库内部的日志作用是同样的,因此,可以看出我们使用DDD + CQRS + EventSourcing实际是将打开数据库这个盒子,直接用面向对象编程语言实现一个基于内存数据库系统而已。
更重要的是,Kreps提出三种日志的用途。
1.数据集成—能让一个公司的所有数据容易集成存储和处理。
2.实时流数据处理—以数据流方式计算
3.分布式系统设计—以日志为中心的设计能简化实践中的分布式系统。
具有几十年从业经验的人说:我是从数据库系统开始我的职业,我一直致力于传统的日志恢复工作中,还有设计实现类似的系统,然后将我的职业的三分子时间花在分布式系统上,花费了我大量时间在服务的复制上,使用异步的日志以确保数据的一致性。这意味着我过去三十年都是在和日志打交道。
如果你是一个软件工程师,你会在你的公司中听到开发人员谈论日志、复制、日志传送等类似的话题,如果你想了解更多,你应该花一些更多时间阅读Kreps这篇程序员史诗般的文章:
日志是每个软件工程师关心的统一数据抽象