抖音技术能力大揭密!钜惠大礼、深度体验,尽在火山引擎增长沙龙,就等你来! 立即报名>>
写点什么

如何系统性地学习分布式系统?-金马国际

    2020 年 9 月 07 日

    本文的缘起是回答知乎圆桌会议「分布式系统之美」的问题「如何系统性地学习分布式系统?」,后面稍微整理了一下,形成了这一篇文章(知乎 id:kylin)。


    前言

    学习一个知识之前,我觉得比较好的方式是先理解它的来龙去脉:即这个知识产生的过程,它解决了什么问题,它是怎么样解决的,还有它引入了哪些新的问题(没有银弹),这样我们才能比较好的抓到它的脉络和关键点,不会一开始就迷失在细节中。


    所以,在学习分布式系统之前,我们需要解决的第一个问题是:分布式系统解决了什么问题?


    分布式系统解决了什么问题?

    第一个是单机性能瓶颈导致的成本问题,由于摩尔定律失效,廉价 pc 机性能的瓶颈无法继续突破,小型机和大型机能提高更高的单机性能,但是成本太大高,一般的公司很难承受;


    第二个是用户量和数据量爆炸性的增大导致的成本问题,进入互联网时代,用户量爆炸性的增大,用户产生的数据量也在爆炸性的增大,但是单个用户或者单条数据的价值其实比软件时代(比如银行用户)的价值是只低不高,所以必须寻找更经济的方案;


    第三个是业务高可用的要求,对于互联网的产品来说,都要求 7 * 24 小时提供服务,无法容忍停止服务等故障,而要提供高可用的服务,唯一的方式就是增加冗余来完成,这样就算单机系统可以支撑的服务,因为高可用的要求,也会变成一个分布式系统。


    基于上面的三个原因可以看出,在互联网时代,单机系统是无法解决成本和高可用问题的,但是这两个问题对几乎对所有的公司来说都是非常关键的问题,所以,从单机系统到分布式系统是无法避免的技术大潮流。


    分布式系统是怎么来解决问题的?

    那么,分布式系统是怎么来解决单机系统面临的成本和高可用问题呢?


    其实思路很简单,就是将一些廉价的 pc 机通过网络连接起来,共同完成工作,并且在系统中提供冗余来解决高可用的问题。


    分布式系统引入了哪些新的问题?

    我们来看分布式系统的定义:分布式系统是由一组通过网络进行通信、为了完成共同的任务而协调工作的计算机节点组成的系统。在定义中,我们可用看出,分布式系统它通过多工作节点来解决单机系统面临的成本和可用性问题,但是它引入了对分布式系统内部工作节点的协调问题。


    我们经常说掌握一个知识需要理解它的前因后果,对于分布式系统来说,前因是「分布式系统解决了什么问题」,后果是「它是怎么做内部工作节点的协调」,所以我们要解决的第二个问题是:分布式系统是怎么做内部工作节点协调的?


    分布式计算引入了哪些新的问题?

    先从简单的情况入手,对于分布式计算(无状态)的情况,系统内部的协调需要做哪些工作:


    1.怎么样找到服务?

    在分布式系统内部,会有不同的服务(角色),服务 a 怎么找到服务 b 是需要解决的问题,一般来说服务注册与发现机制是常用的思路,所以可以了解一下服务注册发现机制实现原理,并且可以思考服务注册发现是选择做成 ap 还是 cp 系统更合理(严格按 cap 理论说,我们目前使用的大部分系统很难满足 c 或者 a 的,所以这里只是通常意义上的 ap 或者 cp);


    2.怎么样找到实例?

    找到服务后,当前的请求应该选择发往服务的哪一个实例呢?一般来说,如果同一个服务的实例都是完全对等的(无状态),那么按负载均衡策略来处理就足够(轮询、权重、hash、一致性 hash,fair 等各种策略的适用场景);如果同一个服务的实例不是对等的(有状态),那么需要通过路由服务(元数据服务等)先确定当前要访问的请求数据做哪一个实例上,然后再进行访问。


    3.怎么样避免雪崩?

    系统雪崩是指故障的由于正反馈循序导致不断扩大规则的故障。一次雪崩通常是由于整个系统中一个很小的部分出现故障于引发,进而导致系统其它部分也出现故障。比如系统中某一个服务的一个实例出现故障,导致负载均衡将该实例摘除而引起其它实例负载升高,最终导致该服务的所有实例像多米诺骨牌一样一个一个全部出现故障。


    避免雪崩总体的策略比较简单,只要是两个思路,一个是快速失败和降级机制(熔断、降级、限流等),通过快速减少系统负载来避免雪崩的发生;另一个为弹性扩容机制,通过快速增加系统的服务能力来避免雪崩的发生。这个根据不同的场景可以做不同的选择,或者两个策略都使用。


    一般来说,快速失败会导致部分的请求失败,如果分布式系统内部对一致性要求很高的话,快速失败会带来系统数据不一致的问题,弹性扩容会是一个比较好的选择,但是弹性扩容的实现成本和响应时间比快速失败要大得多。


    4.怎么样监控告警?

    对于一个分布式系统,如果我们不能很清楚地了解内部的状态,那么高可用是没有办法完全保障的,所以对分布式系统的监控(比如接口的时延和可用性等信息),分布式追踪 trace,模拟故障的混沌工程,以及相关的告警等机制是一定要完善的;


    分布式存储引入了哪些新的问题?

    接下来我们再来看分布式存储(有状态)的内部的协调是怎么做的,同时,前面介绍的分布式计算的协调方式在分布式存储中同样适用,就不再重复了:


    1.分布式系统的理论与衡权

    acid、base 和 cap 理论,了解这三个主题,推荐这一篇文章以及文章后面相关的参考文献:


    英文版本:


    中文版本:


    2.怎么样做数据分片?

    单机的存储能力是不可能存储所有的数据的,所以需要解决怎么将数据按一定的规则分别存储到不同的机器上,目前使用比较多的方案为:hash、consistent hash 和 range based 分片策略,可以了解一下它们的优缺点和各自的应用场景;


    3.怎么样做数据复制?

    为什么满足系统的高可用要求,需要对数据做冗余处理,目前的方案主要为:中心化方案(主从复制、一致性协议比如 raft 和 paxos 等)和 去中心化的方案(quorum 和 vector clock)了解一下它们的优缺点和各自的应用场景,以及对系统外部表现出来的数据一致性级别(线性一致性、顺序一致性、最终一致性等);


    4.怎么样做分布式事务?

    对于分布式系统来说,要实现事务,首先需要有对并发事务进行排序的能力,这样在事务冲突的时候,确认哪个事务提供成功,哪个事务提交失败。对于单机系统来说这个完全不是问题,简单通过时间戳加序号的方式就可以实现,但是对于分布式系统来说,系统中机器的时间不能完全同步,并且单台机器序号也没用全局意义,按上面的方式说行不通的。不过整个系统选一台机器按单机的模式生产事务 id 是可以的,同城多中心和短距离的异地多中心都没有问题,不过想做成全球分布式系统的话,那么每一次事务都要去一个节点去获取事务 id 的成本太高(比如中国杭州到美国东部的 rtt 为 200 ms ),google 的 spanner 是通过 gps 和原子钟实现 truetime api 来解决这个问题从而实现全球分布式数据库的。


    有了事务 id 后,通过 2pc 或者 3pc 协议来实现分布式事务的原子性,其他部分和单机事务差别不大,就不再细说来。


    进阶学习阶段

    到这里,对分布式系统脉络上有了基本的概念,接下来开始进入细节学习阶段,这也是非常幸苦的阶段,对于分布式系统的理解深入与否,对细节的深入度是很重要的评价指标,毕竟魔鬼在细节。这里可以往两个方面进行系统的学习:


    1.从实践出发

    研究目前比较常用的分布式系统的设计,hdfs 或者 gfs(分布式文件系统)、kafka 和 pulsar(分布式消息队列),redis cluster 和 codis(分布式缓存),mysql 的分库分表(传统关系型数据库的分布式方案),mongodb 的 replica set 和 sharing 机制集以及去中心化的 cassandra(nosql 数据库),中心化的 tidb 和去中心化的 cockroachdb(newsql),以及一些微服务框架等;


    2.从理论出发

    从理论出发,研究分布式相关的论文,这里推荐一本书「designing data-intensive applications」(中文版本:数据密集型应用系统设计),先整体看书,对比较感兴趣的章节,再读一读该章节中涉及到的相关参考文献。


    总结

    本文从分布式系统解决的问题开始,再讨论它是怎么样来解决问题的,最后讨论了它引入了哪些新的问题,并且讨论这些新问题的解决办法,这个就是分布式系统大概的知识脉络。掌握这个知识脉络后,那么就可以从实践和理论两个角度结合起来深入细节研究分布式系统了。


    参考








    2020 年 9 月 07 日 19:545798

    评论 2 条评论

    发布
    paxos是中心化?base paxos才是吧?
    2020 年 09 月 14 日 11:37
    回复
    这个确实是比较有争议的地方,文章想表达的是每一次数据复制的时候,是否需要一个中心化的协调者(比如 leader 或者 proposer,不过却是 paxos 算法也有 egalitarian paxos 这样 leaderless 的算法,只是目前基本没有被使用,所以文章就没有讨论了),如果是站在同一时刻是否有多个协调者来说,那可以说 multi-paxos 确实不是中心化的
    2020 年 09 月 14 日 16:31
    回复
    没有更多了
    • 做分布式系统最大的坑就是,需要具备一个成本巨高无比的技术栈,看着就都头晕。要投入大量的人力、物力和时间才能实现。

      2017 年 12 月 19 日

    • cap理论

      2020 年 7 月 15 日

    • 本次分享介绍百度云利用braft快速搭建高性能分布式系统的经验。

    • 今天,我主要与你分享了什么是cap理论,以及如何根据自己的场景选择合适的cap策略。

      2019 年 11 月 18 日

    • 根据墨菲定律,我们需要用最悲观的态度来看待分布式系统中可能出现的问题,本文将对这些问题进行总结。

      2020 年 12 月 21 日

    • 柔性事务的一致性指的是最终一致性。

    • 本文中推荐的资料基本涵盖了所有与系统架构相关的技术,足够这世上90%以上的公司用了。

      2018 年 7 月 10 日

    • 这次,我们来聊一聊在保证对外高可用的同时,憋出的“内伤”该如何通过「补偿」机制来自行消化。

    • 在 k8s 中的用户权限系统是使用 rbac 模式的,rbac 是 role-based ac 的缩写,全称:基于角色的访问控制。

      2021 年 6 月 17 日

    • osgi联盟企业专家组的主席,iona technologies的前ctoeric newcomer在文章中回答了这个问题:“restful事务与web service事务的区别是什么?”

    • 与许多人认为的不同,微服务的概念已有相当长的历史,soa(面向服务的体系架构)也不是90年代才被提出的。在最近举办的伦敦微服务大会上,greg young就微服务核心概念的前世今生进行了演讲。其中他表示,在过去的50年间,我们一直在使用服务这一概念背后的核心思想。

    • 左耳06网站:弹力设计篇之“认识故障和弹力设计”

    • 这节课主要讲解适用于基于事件溯源的架构应该如何做动态分库,大部分重要的金融系统和数据系统都能适用这个方案。

      2021 年 2 月 5 日

    • 站在全局角度看,分布式系统的本质是什么?其实说白了,就是两点:“分治”和“冗余”。分治和冗余使得分布式系统具备了核心价值,那么它的价值是什么?

    • 在数据分布式系统中,出现了一些与以前的关系型数据库不一样的新问题:

      2020 年 7 月 12 日

    • influxdb企业版一年的license费高达1.5万美刀,为什么它值这个价钱?就是因为技术带来的高性能和成本优势。

      2020 年 3 月 18 日

    • 在近期举办的qcon london大会上,ben stopford在他的演讲中极力主张拥抱去集中化的思想、构建基于服务的系统,并通过流处理工具解决分布式状态所引起的问题。

    • 区块链的共识算法的整体思路就是让攻击者的攻击成本远远大于收益。

      2018 年 4 月 18 日

    • 分布式系统的技术栈巨大无比,所以我要推荐的学习资料也比较多,会在后面的文章中陆续发出。在今天这篇文章中,我将推荐一些分布式系统的基础理论和一些不错的图书和资料。

    • 与近期与infoq的一次对话中,vaughn vernon分享了一些他在开发分布式系统方面的心得。他特别指出,在分布式系统中,有可能会出现局部故障此类问题。对于这种类型的问题以及一些其它挑战来说,最佳的应对方式是做好一切准备,而不是无助地祈祷它不要出现。vaughn还推荐了jeff hodges所撰写的一篇博客文章,这篇文章为分布式系统给出了一些落到实处的设计方式,并提出了一些实用的建议,非常适合于在分布式系统方面经验尚浅的开发者。

    发现更多内容

    study go: from zero to hero

    study go: from zero to hero

    金马国际
    网站地图