译者 | 李睿
审校 | 重楼
美国汽车服务应用程序开发商Jerry公司使用人工智能(AI)和机器学习(ML)来简化汽车保险和汽车贷款的比较和购买过程。随着数据的增长,该公司在使用AWS Redshift时遇到了一些问题,例如速度缓慢且价格昂贵。在该公司改用ClickHouse之后加快了查询性能,并大幅地降低了成本,但这也带来了磁盘故障和数据恢复等存储方面的挑战。
为了避免大量的维护工作,Jerry公司采用了高性能的分布式文件系统JuiceFS,创新地使用其快照功能来实现ClickHouse的主-副本架构。该架构保证了数据的高可用性和稳定性,同时显著提高了系统性能和数据恢复能力。一年多来,JuiceFS一直在持续运行,并且没有发生停机和复制错误,提供了预期的性能。
本文将深入探讨Jerry公司采用的应用程序面临的挑战、采用的解决方案以及未来实施的计划。希望这篇文章能为初创公司和大公司的开发团队提供有价值的见解。
数据架构:从Redshift到ClickHouse
最初,Jerry公司选择Redshift进行分析查询。然而,随着数据量的增长,遇到了严重的性能和成本挑战。例如,当生成漏斗和A/B测试报告时,面临着长达数十分钟的加载时间。即使在规模合理的Redshift集群上,这些操作也太慢了,这使得该公司的数据服务不可用。
因此,Jerry公司急需寻求一个更快、更经济的解决方案,因此选择了ClickHouse,尽管它在实时更新和删除方面存在局限性。而切换到ClickHouse带来了显著的好处:
- 报告加载时间从几十分钟减少到几秒钟,能够更有效地处理数据。
- 总支出被削减到不超过原来的25%。
Jerry公司的设计以ClickHouse为中心,使用Snowflake作为ClickHouse无法处理的1%数据处理的备份。这个设置实现了ClickHouse和Snowflake之间的无缝数据交换。
图1 Jerry公司的数据架构
ClickHouse的部署和挑战
Jerry公司最初保持独立部署有以下几个原因:
- 性能:独立部署避免了集群的开销,并且在相同的计算资源下表现良好。
- 维护成本:独立部署的维护成本最低。这不仅包括集成维护成本,还包括应用程序数据设置和应用程序层的公开维护成本。
- 硬件功能:目前的硬件可以支持大规模独立ClickHouse部署。例如,Jerry公司现在可以在AWS上获得具有24TB内存和488个vCPU的EC2实例。这在规模上超过了许多已经部署的ClickHouse集群。这些实例还提供了满足计划容量的磁盘带宽。
因此,考虑到内存、CPU和存储带宽,独立的ClickHouse是一个可接受的解决方案,在可预见的未来将是有效的。
然而,ClickHouse方法也存在一些固有问题:
- 硬件故障可能导致ClickHouse长时间停机,这将威胁到应用程序的稳定性和持续性。
- ClickHouse的数据迁移和备份仍然是艰巨的任务,它们需要可靠的解决方案。
在部署ClickHouse之后,Jerry公司遇到了以下问题:
- 扩展和维护存储:由于数据的快速扩展,保持适当的磁盘利用率变得困难。
- 磁盘故障:ClickHouse旨在积极利用硬件资源,以提供最佳的查询性能。因此,读写操作频繁发生。它们经常超出磁盘带宽。这增加了磁盘发生硬件故障的风险。当这种故障发生时,数据恢复可能需要几个小时到十个多小时。这取决于数据量。其他用户也有类似的经历。虽然数据分析系统通常被认为是其他系统数据的副本,但这些故障的影响仍然很大。因此,需要为任何硬件故障做好准备。数据迁移、备份和恢复是非常困难的操作,需要花费更多的时间和精力才能成功完成。
Jerry公司的解决方案
Jerry公司采用JuiceFS来解决其痛点,原因如下:
- JuiceFS是唯一可以在对象存储上运行的POSIX文件系统。
- 无限容量:自从开始使用JuiceFS以来,就不必担心存储容量。
- 显著的成本节约:与其他解决方案相比,使用JuiceFS的费用显著降低。
- 强大的快照功能:JuiceFS在文件系统级别有效地实现了Git分支机制。当两个不同的概念如此无缝地融合在一起时,它们通常会产生极具创造性的解决方案。这使得以前具有挑战性的问题更容易解决。
构建ClickHouse的主-副本架构
Jerry公司提出了将ClickHouse迁移到基于JuiceFS的共享存储环境的想法。《探索ClickHouse的存储和计算分离》一文提供了一些见解。
为了验证这种方法,Jerry公司进行了一系列测试。结果表明,在启用缓存之后,JuiceFS的读取性能接近本地磁盘的读取性能,这与本文中的测试结果类似。
虽然写入性能下降到磁盘写入速度的10%到50%,但这是可以接受的。
Jerry公司对JuiceFS安装所做的调整如下:
- 为了异步写入和防止可能的阻塞问题,启用了回写功能。
- 在缓存设置中,将attrcacheto设置为“3,600.0秒”,将缓存大小设置为“2,300,000”。启用了元缓存功能。
- 考虑到JuiceFS上的I/O运行时间可能比本地磁盘驱动器上的更长,引入了块中断特性。
提高缓存命中率是Jerry公司的优化目标。使用JuiceFS云服务将缓存命中率提高到95%。如果需要进一步改进,会考虑添加更多的磁盘。
ClickHouse和JuiceFS的结合大幅减少了Jerry公司的运营工作量,并且不再需要频繁地扩展磁盘空间。与其相反,Jerry公司专注于监控缓存命中率。这显著地缓解了磁盘扩展的紧迫性。此外,在发生硬件故障时不需要进行数据迁移。这显著地降低了可能的风险和损失。
Jerry公司从JuiceFS快照功能提供的简单数据备份和恢复选项中受益匪浅。借助快照,可以查看数据的原始状态,并在将来的任何时候恢复数据库服务。这种方法通过在文件系统级别实现解决方案来解决以前在应用程序级别处理的问题。此外,快照功能非常快速和经济,因为只存储数据的一个副本。JuiceFS社区版的用户可以使用克隆功能来实现类似的功能。
此外,在不需要数据迁移的情况下,停机时间显著减少。Jerry公司可以快速响应故障或允许自动系统将目录挂载到另一台服务器上,从而确保服务的连续性。值得一提的是,ClickHouse的启动时间只有几分钟,这进一步提高了系统恢复速度。
此外,读性能在迁移后保持稳定,Jerry公司的员工都没有发现任何差异。这证明了该解决方案的性能稳定性。
最后,Jerry公司的成本大幅下降。
为什么要设置主-副本架构
在迁移到ClickHouse之后遇到了几个问题,促使Jerry公司考虑构建主-副本架构:
- 资源争用导致性能下降。在Jerry公司的设置中,所有任务都运行在同一个ClickHouse实例上。这导致了提取、转换和加载(ETL)任务和报告任务之间的频繁冲突,从而影响了整体性能。
- 硬件故障导致停机。Jerry公司需要随时访问数据,所以长时间的停机是不可接受的。因此寻求一种解决方案,这使Jerry公司找到了主-副本架构的解决方案。
JuiceFS支持在不同位置的多个挂载点。Jerry公司尝试在其他地方挂载JuiceFS文件系统,并在同一位置运行ClickHouse。然而,在实施过程中遇到了一些问题:
- 通过文件锁定机制,ClickHouse限制一个文件只能由一个实例运行,这带来了挑战。幸运的是,通过修改ClickHouse源代码来处理锁定,这个问题很容易解决。
- 即使在只读操作期间,ClickHouse也保留了一些状态信息,例如write-time缓存。
- 元数据同步也是一个问题。当在JuiceFS上运行多个ClickHouse实例时,一个实例写入的一些数据可能无法被其他实例识别。而解决这个问题需要重新启动实例。
因此,Jerry公司使用JuiceFS快照来设置主-副本架构。这种方法的工作原理类似于常规的主备份系统。主实例处理所有数据更新,包括同步和提取、转换和加载(ETL)操作。副本实例主要关注查询功能。
图2 ClickHouse主-副本架构
如何为ClickHouse创建副本实例
(1)创建快照
使用JuiceFS快照命令从主实例上的ClickHouse数据目录创建快照目录,并在该目录上部署ClickHouse服务。
(2)暂停Kafka消费者队列
在启动ClickHouse实例之前,必须停止使用来自其他数据源的有状态内容。这意味着暂停Kafka消息队列,以避免与主实例竞争Kafka数据。
(3)在快照目录下执行ClickHouse命令
在启动ClickHouse服务之后,注入了一些元数据,向用户提供有关ClickHouse创建时间的信息。
(4)删除ClickHouse数据突变
在副本实例上,删除了所有数据突变,以提高系统性能。
(5)执行连续复制
快照只保存创建时的状态。为了确保它读取最新的数据,Jerry公司定期用副本替换原始实例。这种方法使用简单且高效,因为每个副本实例都以两个副本和指向其中一个副本的指针开始。即使需要10分钟或更长时间,通常也会每小时运行一次以满足Jerry公司的需求。
Jerry公司的ClickHouse主-副本架构已经稳定运行了一年多,完成2万多次无故障复制操作,证明了其高可靠性。工作负载隔离和数据副本的稳定性是提高性能的关键。在没有任何应用层优化的情况下,Jerry公司成功地将总体报告可用性从不到95%提高到99%。此外,该架构支持弹性扩展,极大地增强了灵活性。这使Jerry公司能够根据需要开发和部署新的ClickHouse服务,而无需复杂的操作。
Jerry公司未来的计划
- 将开发一个优化的控制界面来自动化实例生命周期管理、创建操作和缓存管理。
- 还计划优化写性能。从应用层来看,考虑到对Parquet开放格式的强大支持,可以直接将大多数负载写入ClickHouse外部的存储系统中,以便于访问。这允许Jerry公司使用传统的方法来实现并行写入,从而提高写入性能。
- Jerry公司注意到chDB这个新项目,它允许用户直接在Python环境中嵌入ClickHouse功能,而不需要运行ClickHouse服务器。结合CHDB和目前的存储解决方案,可以实现一个完全无服务器的ClickHouse。这是Jerry公司目前正在探索的方向。
原文标题:Why and How We Built a Primary-Replica Architecture of ClickHouse,作者:Tao Ma