流式数据库的诞生是十多年数据处理和服务演变的结晶。这一演变根植于数据库管理系统、数据处理以及数字时代不断变化的需求的广泛历史之中。为了深入理解这一演变,让我们回顾那些塑造了流式数据库发展的关键历史里程碑。
在20世纪末,互联网的兴起和数字数据的爆炸性增长催生了对更具可扩展性和灵活性的数据管理解决方案的需求。数据仓库和Hadoop等面向批处理的处理框架应运而生,以应对这个时代数据规模的挑战。
“大数据”一词不仅指数据的庞大体量,也涵盖了存储和处理超大数据集的所有解决方案。大数据无法存储在单一计算机或服务器上,需要将其分割成更小、等大小的部分,并在多台计算机中存储。Hadoop和MapReduce之所以流行,是因为它们支持分布式存储和处理。
随着分布式流(distributed streaming)的概念兴起,大量数据被移动到Hadoop中。Apache Kafka,一种旨在处理大数据的消息传递服务,不仅提供了数据从一个系统到另一个系统的传输方法,还提供了实时访问动态数据的途径。这一进步激发了对实时流媒体用例的新需求。
新技术如Apache Flink和Apache Spark应运而生,以满足这些新期望。作为支持批处理和流式传输的分布式框架,它们能在多台服务器上处理数据并提供分析结果。当与Kafka结合使用时,这三者共同提供了一种能够支持实时流式分析用例的解决方案。我们将在第2章中更详细地探讨流处理器。
到了2010年代中期,流媒体领域出现了更简单、更高效的范式,以扩大实时数据处理的规模。这包括了两个新的流处理框架:Apache Kafka Streams(KStreams)和Apache Samza。KStreams和Samza是首批实现物化视图(meterialized view)的框架,它们使得流媒体看起来和感觉更像数据库。
Apache Kafka Streams 是构建在 Apache Kafka 之上的客户端库,专门用于构建高吞吐量、低延迟的实时流处理应用程序。它允许开发者以一种易于扩展和复制的方式处理记录流。Kafka Streams 提供了一系列易于使用的 API,包括高级的 DSL(特定领域语言)和低级的处理器 API,它们可以相互配合使用。 Kafka Streams 的关键特性包括:
- 易用性:提供简洁的 API,便于开发者构建复杂的流处理应用。
- 无需单独的处理集群:作为常规 Java 应用运行,无需维护专门的处理集群。
- 状态处理能力:支持状态化处理,通过 RocksDB 实现状态的持久化和容错。
- 时间窗口处理:支持不同类型的时间窗口操作,如滑动窗口、跳跃窗口和会话窗口。
- 流式表格双模型:将流处理结果视为动态更新的表格,提供直观的数据理解方式。
- 可扩展和容错:基于 Kafka,继承了其可扩展性和高可用性。
Kafka Streams 通过处理拓扑(Processing Topology)来定义应用程序的处理逻辑,它由一系列节点和边组成,每个节点执行特定的处理操作,如过滤、映射、聚合等。此外,Kafka Streams 还支持全局状态存储,允许应用程序跨多个流处理任务共享状态。
Apache Samza 是由 LinkedIn 开发并贡献给 Apache 基金会的开源分布式流处理框架。它以高度可靠的方式支持低延迟的数据流处理,并广泛应用于各种大数据应用场景。 Samza 的核心特性包括:
- 高性能:提供极低延迟和高吞吐量,适用于大量数据的实时分析。
- 水平扩展能力:能够随着数据量的增长而动态扩展计算资源。
- 容错机制:采用内置的故障恢复策略,确保数据的一致性和完整性。
- 灵活的部署选项:可以在 YARN 集群或作为独立库的形式进行部署。
- 状态管理:支持持久化的状态存储,便于复杂的业务逻辑处理。
Samza 的架构设计围绕着 Kafka 消息队列展开,利用 Kafka 的功能实现流式的实时数据处理。它还依赖于 Apache Hadoop YARN 来提供资源管理和任务调度的能力。
Samza 支持统一的 API,允许开发者用简单的 API 描述应用逻辑,同时支持批处理和流式数据。Samza 可作为嵌入式库轻松集成到现有应用中,提供灵活的部署选项,包括公共云、容器化环境和裸机硬件。
Kafka Streams 和 Samza 都是强大的流处理框架,但 Kafka Streams 更加专注于 Kafka 生态系统内部的集成,而 Samza 提供了更广泛的数据源和存储选项,以及更灵活的部署方式。
物化视图(Materialized View)是一种数据库对象,它存储了查询结果的物理副本,这与普通视图(仅保存SQL查询逻辑)不同。物化视图可以提高查询性能,尤其是对于复杂或计算密集型的查询,因为它预先计算并存储了结果。
物化视图特别适合于数据仓库系统,用于预先计算和存储表连接或聚集等耗时较多的操作结果,从而加快查询速度。此外,物化视图还支持查询重写(Query Rewrite),这意味着当对物化视图的基表进行查询时,数据库会自动判断是否可以通过查询物化视图来得到结果,如果可以,则避免了聚集或连接操作,而直接从已经计算好的物化视图中读取数据。
物化视图的类型主要分为三种:
- 包含聚集的物化视图,如聚合函数SUM、AVG等。
- 只包含连接的物化视图,用于预计算连接操作。
- 嵌套物化视图,其查询定义中引用了其他物化视图。
Martin Kleppmann进一步将数据库与流媒体相结合。在2015年的演讲《Turning the Database Inside-Out(翻转数据库)》中,他描述了一种实现流处理的方法,该方法采用数据库的内部功能并将其外部化为实时流。这种方法促成了更具可扩展性、弹性和实时性的流处理系统。
流处理的一个挑战(现在仍然是)是它比批处理更难以使用。抽象概念较少,技术层面更深。为了实现流处理用例,数据工程师现在必须考虑数据顺序、一致性、容错性、弹性和可扩展性等因素。这些成为阻碍数据团队尝试使用流媒体的障碍。因此,许多人选择继续使用数据库来转换数据,尽管这可能以牺牲性能为代价。