快捷搜索:

说说大型网站的架构模式即开彩app下载

为什么自动化系统必须配备冗余服务器? 答:冗余服务器是在网络系统中起备用作用的服务器, 当环网系统的主服务器发生故障时,冗余服务器介入并承担 故障服务器的全部功能,从而保证网络系统的正常运行;因 此,自动化系统必须配备冗余服务器。

    本文就设计和开发运营友好的服务的话题进行总结,得出一系列最佳实践。设计和部署大规模服务是一个高速发展的领域,因而随着时间的流逝,任何最佳实践集合都可能成熟并完善。我们的目的是为了帮助人们:

◆ 快速交付运营友好的服务;

◆ 避免清早电话铃声的骚扰,帮助备受运营不友好的服务侵扰的客户尽量摆脱窘境。

    这篇论文是我们在过去的20年中在大规模以数据为中心的软件系统和互联网级大规模服务的智慧结晶,包括Exchange Hosted Services团队、Microsoft Global Foundation Services Operations团队以及Windows Live! 平台多个团队的经验。这些贡献经验的服务中,有不少规模已经增长到拥有超过二亿五千万名用户。同时,本论文也大量吸取了加州大学伯克利分校在面向恢复计算 (Recovery Oriented Computing)方面取得的成果和斯坦福大学在只崩溃软件(Crash-Only Software)方面的研究经验。

    Bill Hoffman为本论文贡献许多最佳实践。此外,他还提出三条简单原则,值得大家在进入正题之前进行考量:

1.做好发生故障的心理准备。

2.保持简单化。

3.将所有的工作自动化。

这三条原则形成了贯穿后续讨论的主轴。

    本文的十个小节涵盖了设计和部署运营友好服务所必须做到的各个方面。它们是:整体服务设计;以自动化和预置(Provisioning)为目标进行设计; 依赖关系管理;发布周期及测试;硬件的选择和标准化;运营和容量规划;审核、监控和警报;体面降级和管理控制;客户及媒体沟通计划;以及客户自我预置和自 我帮助。

整体服务设计

    一直以来,人们都相信80%的运营问题源于设计和开发,因此本节关于整体服务设计的内容篇幅最长,也最重要。系统出故障时,人们很自然倾向于首先去审视运 营工作,因为这是问题实际产生的地方。不过,绝大多数运营问题都可以归因于设计和开发,或者最适合在设计和开发中解决。

    随后的内容凸显一个共识,即在服务领域,将开发、测试和运营严格分离不是最有效的方式。在环顾众多服务之后,我们发现了这样一个趋势——管理的低成本与开发、测试和运营团队间协作的紧密程度密切相关。

    除了在这里讨论的服务设计最佳实践以外,随后一节“以自动化管理和预置为目标进行设计”对服务设计也有实质性的影响。有效的自动化管理和预置通常以一个受 限的服务模型来实现。简单是高效率运营的关键,这是贯穿本文重复出现的主题。在硬件选择、服务设计和部署模型上的理性约束,是降低管理成本和提高服务可靠 性的强心针。

    在运营友好的基础原则中,为整体服务设计带来最大影响的几条包括:

◆ 设计时为故障做好准备(Design for failure)。在开发包含多个协同运作的组件的大型服务时,这是一条核心概念。这些组件会有故障发生,而且故障的产生很频繁。它们之间不会总是稳定地 协作,也不会单独出现故障。一旦服务的规模达到10,000台以上的服务器和50,000块以上的磁盘,每天就会有多次故障发生。如果一有硬件故障产生就 得采取紧急措施来应对,那么服务就无法以合理的成本可靠地伸缩。整个服务必须有承受故障而无须人工干预的能力。故障恢复的步骤必须非常简单,而且这些步骤 应当进行频繁测试。斯坦福大学的Armando Fox 主张说,对故障恢复步骤进行测试的最佳方法,就是绝对不要用正常方式使服务停机,用粗暴的方式让它停转就可以了。乍听起来怎么做是违背直觉的,但是如果没 有频繁使用故障步骤,那么它们在真正临阵时就可能溃不成军 。

◆ 冗余和错误恢复(Redundancy and fault recovery)。大型机模型是指购买一台价高块头大的服务器。大型机拥有冗余的电源供应,CPU可以热交换,而且总线架构也超乎寻常,使得这样一个紧 密耦合的系统能够有可观的I/O吞吐量。这样的系统,最明显的问题就是它们的成本;而且即便有了所有这些费用高昂的设计,它们仍然不够可靠。为了达到 99.999%的可靠性,冗余是必须存在的。实际上,在一台机器上实现4个9的可靠性都是相当困难的。这个概念在整个业界都耳熟能详,不过,将服务构建在 脆弱而又非冗余的数据层之上的现象,到目前为止都屡见不鲜。

要保证设计的服务其中的任何系统可以随时崩溃(或者因为服务原因被停止)但又仍然能符合服务水平协定(Service Level Agreement,简称SLA),是需要非常仔细的设计的。保证完全遵守这项设计原则的严格测试(acid test)步骤如下:首先,运营团队是否有意愿并且有能力随时让任意一台服务器停机并且不会让负载被榨干?如果答案是确定的,那么肯定存在同步冗余(无数 据丢失)、故障侦测和自动接管。我们推荐一条普遍使用的设计方法,用于查找和纠正潜在的服务安全问题:安全威胁建模(Security Threat Modeling)。在安全威胁建模中,我们要考虑每一条潜在的安全威胁,并且相应实现恰当的缓和方案。同样的方法也适用于以错误适应和恢复为目标的设 计。

    将所有可以想象到的组件故障模式及其相应组合用文档记录下来。要保证服务在每个故障发生后都能继续运行,且不会在服务质量上出现不可接受的损失;或者判断 这样的故障风险对于这样一个特定的服务是否可以接受(例如,在非地理冗余的服务中损失掉整个数据中心)。我们可能会认定某些非常罕见的故障组合出现的可能 性微乎其微,从而得出确保系统在发生这种故障之后还能继续运行并不经济的结论。但是,在做这样的决定时请谨慎从事。在运行数以千计的服务器的情况下,每天 都会有几百万种组件故障产生的可能,这时那些事件的“罕见”组合亮相的频繁程度,足以让我们瞠目结舌。小概率组合可能变成普遍现象。

◆ 廉价硬件切片(Commodity hardware slice)。服务的所有组件都应当以廉价硬件切片为目标。例如,存储量轻的服务器可以是双插槽的2至4核的系统,带有启动磁盘,价格在1,000至 2,500美元之间;存储量大的服务器则可以是带有16至24个磁盘的类似服务器。主要的观察结果如下:

▲ 大型的廉价服务器集群要比它们替代的少数大型服务器便宜得多;

▲ 服务器性能的增长速度依然要比I/O性能的增长速度快很多,这样一来,对于给定容量的磁盘,小型的服务器就成为了更为稳定的系统;

▲ 电量损耗根据服务器的数量呈线性变化,但随系统时钟频率按立方级别变化,这样一来性能越高的机器运营成本也越高;

▲ 小型的服务器在故障转移(Fail over)时只影响整体服务工作负荷的一小部分。

◆ 单版本软件(Single-version software)。使某些服务比多数打包产品开发费用更低且发展速度更快的两个因素是:

▲ 软件只需针对一次性的内部部署。

▲ 先前的版本无须得到十年的支持——针对企业的产品正是如此。

相对而言,单版本软件更容易实现,附带客户服务,特别是无须费用的客户服务。但是在向非客户人员销售以订阅为基础的服务时,单版本软件也是同样重 要的。企业通常习惯在面对他们的软件提供商时拥有重要的影响力,并且在部署新版本时(通常是个缓慢的过程),他们会习惯性想去掌握全部的控制权。这样做会 导致他们的运营成本和支持成本急剧上升,因为软件有许多版本需要得到支持。

    最经济型的服务是不会把对客户运行的版本的控制权交给他们的,并且通常只提供一个版本。要把握好单一版本软件的产品线,必须:

▲ 注意在每次发布之间不要产生重大的用户体验变更。

▲ 愿意让需要相应级别控制能力的客户可以在内部托管,或者允许他们转向愿意提供这类人员密集型支持服务的应用服务提供商。

◆多重租赁(Multi-tenancy)。多重租赁是指在同一个服务中为该服务的所有公司或最终用户提供主机服务,且没有物理上的隔离;而单一 租赁(Single-tenancy)则是将不同组别的用户分离在一个隔离的集群中。主张多重租赁的理由基本上和主张单版本支持的理由一致,且它的基础论 点在于提供从根本上成本更低、构建在自动化和大规模的基础之上的服务。

回顾起来,上面我们所展示的基本设计原则和思考如下:

◆ 设计时为故障做好准备

◆ 实现冗余和错误恢复

◆ 依靠廉价硬件切片

◆ 支持单一版本软件

◆ 实现多重租赁

    我们约束服务设计和运营的模型,以此最大化自动化的能力,并且减少服务的总体成本。在这些目标和应用服务提供商或IT外包商的目标之间,我们要划一道清楚的界限。应用服务提供商和IT外包商往往人员更加密集,并且更乐于运行面向客户的复杂配置。

    设计运营友好的服务更具体的最佳实践包括:

◆ 快速服务健康测试。这是构建验证测试的服务版本。这是一个嗅探型测试,可以快速在开发者的系统上运行,以保证服务不会以独立方式出错。要保证所有的边界条件都被测试到,是不可能的,但如果快速健康测试通过的话,那么代码就可以检入了。

◆ 在完整的环境中开发。开发人员不但应当对他们的组件进行单元测试,而且还要对出现组件变更的整个服务进行测试。要高效实现这个目标,必须得有单服务器的部署,以及前一条最佳实践——快速的服务健康测试。

◆ 对下层组件的零信任。设想下层组件会出现故障,并且确保组件会有能力恢复并继续提供服务。恢复的技巧和服务相关,但常见的技巧包括:

▲ 在只读模式中依靠缓存的数据继续运转;

▲ 在服务访问故障组件的冗余拷贝的短暂时间内,继续向用户群一小部分的所有人提供服务。

◆ 不要把同一个功能构建在多个组件中。预见未来的交互是一件极其困难的事情,如果不慎引入冗余的代码,那么将来就不得不在系统的多处做修复。服务的增长和发展是很快的,稍不留神代码的质量就会很快恶化。

◆ 不同的集群之间不能互相影响。大多数服务由小型集合或者系统的子集群组成,它们之间相互协作,共同提供服务,其中每个小型集合都可以相对独立地运作。每个 小型集合应达到接近100%的独立程度,且不会有跨群的故障。全局服务,甚至包括冗余,是故障的中心点。有时候,这样的问题是不可避免的,但还是要设法保 证每个集群都拥有各自所需的资源。

◆ 允许(少量)在紧急情况的人工干预。常见场景是在灾难性事件或者其他紧急情况下移动用户数据。把系统设计成完全无须人工交互,但也要清楚小概率事件可能会 发生,其中组合的故障或者未预期的故障都会需要人工交互。这些事件是会发生的,而在这些情况下,操作员的错误往往是导致灾难性数据丢失的常见来源。一名在 半夜2点顶压工作的运营工程师可能会犯错误。将系统设计成一开始在多数情况下无须运营干预,但请和运营团队协作制定在他们需要进行干预时的恢复计划。比起 将这些计划写进文档,变成多步骤易出错的过程,更好的办法是把这些规则写成脚本,并在生产环境中进行测试,以确保它们正常工作。没有经过产品环境试验的代 码是不可行的,因此运营团队应当定时指挥使用这些工具进行“防火演习”。如果演习的服务可用性风险非常高,那么可以认为之前在工具的设计、开发和测试上的 投资不足。

◆ 保持一切简单健壮。复杂的算法和组件交互会给调试和部署带来成倍困难。简单到近乎傻瓜式的结构在大规模服务中几乎总是更胜一筹,因为在复杂的优化工作交付 之前,交互中故障模式的数量早就足以磨灭人们的信心。通常我们的惯例是,能够带来一个数量级以上改善的优化工作才值得考虑,而只有百分之几或者甚至于只是 低系数级别的提升,就不值得了。

◆ 全面推进准入控制。所有良好的系统会在设计时开门见山地引入许可控制,这样符合一条长期以来为人们所认可的原则,那就是避免将更多的工作引入一个已经过载 的系统,要比持续接受工作然后开始翻来覆去地检查好一些。在服务入口引入某些形式的节流或者准入控制是很常见的做法,但在所有的主要组件边界上都应该有准 入控制。工作性质的变更最终会导致子组件的过载,即使整体服务仍然运行在可接受的负载级别。总体的惯例就是尝试采用优雅降级的方式,而不用在统一给所有用 户低质量服务之前进行硬停机并阻断服务的入口。

◆ 给服务分区。分区应当可以无限调整,并且高度细粒度化,并且不受任何现实实体(人、集合等)的限制。如果按公司分区,那么对于大的公司,就有可能超过单个 分区的规模;而如果按名称前缀进行分区,那么例如所有以P打头的最终一台服务器就可能会装不下。我们推荐在中间层使用一张查询表,将细粒度的实体,通常是 用户,映射到其数据相应被管理的系统上。这些细粒度的分区随后就可以自由在服务器之间移动。

◆ 理解网络的设计。提早进行测试,了解机柜内的服务器之间、跨柜的服务器之间以及跨数据中心之间有哪些负载。应用程序开发人员必须理解网络的设计,且设计应当尽早交给来自运营团队的网络专员审核。

◆ 对吞吐量和延迟进行分析。应当对核心服务的用户交互进行吞吐量和延迟的分析,从而了解它们的影响。结合其他运营操作,比如定期数据库维护、运营配置(加入 新用户,用户迁移)和服务调试等,进行吞吐量和延迟的分析。这样做对于捕捉由周期性管理任务所带动的问题是颇有裨益的。对于每个服务,都应当形成一个度量 标准,用于性能规划,比如每个系统的每秒用户访问数,每个系统的并发在线人数,或者某些将关联工作负载映射到资源需求的相关度量标准。

◆ 把运营的实用工具作为服务的一部分对待。由开发、测试、项目管理和运营所产生的运营实用工具应当交给开发团队进行代码审查,提交到主源码树上,用同一套进度表跟踪,进行同样的测试。最频繁出现的现象是,这样的实用工具对于任务有至关重要的影响,但几乎都没有经过测试。

◆ 理解访问模式。在规划新特性时,一定要记得考虑它们会给后端存储带来哪些负载。通常,服务模型和服务开发人员与存储抽象得非常开,以至于他们全然忘记了它 们会给后端数据库带来的额外负载。对此的最佳实践把它作为规范建立起来,里面可以有这样的内容:“这项功能会给基础结构的其他部分带来什么样的影响?”然 后在这项特性上线之后,对它进行负载的测量和验证。

◆ 让所有工作版本化。做好在混合版本的环境中运行的准备。我们的目标是运行单版本的软件,但是多个版本可能会在首次展示和生产环境测试的过程中并存。所有组件的n版和n 1版都应当能够和平共存。

◆ 保持最新发布版的单元/功能测试。这些测试是验证n 1版本的功能是否被破坏的重要方法。我们推荐大家更进一步,定期在生产环境中运行服务验证(后面会详细介绍)。

◆ 避免单点故障。单点故障的产生会导致整个服务或者服务的某些部分停工。请选择无状态的实现。不要将请求或者客户端绑定在特定的服务器上,相反,将它们负载 均衡在一组有能力处理这样负载的服务器上。静态哈希或者任何静态的服务器负载分配都会时不时遭受数据和/或查询倾斜问题的困扰。在一组机器可以互换时,要 做到横向伸展是非常容易的。数据库通常会发生单点故障,而数据库伸缩仍然是互联网级大规模服务的设计中最为困难的事情之一。良好的设计一般会使用细粒度的 分区,且不支持跨分区操作,以在多台数据库服务器之间进行高效伸展。所有的数据库状态都会进行冗余存储(至少在一台)完全冗余的热待机服务器上,并且在生 产环境中会频繁进行故障转移测试。

自动管理和预置

    许多服务编写的目的是为了在故障时向运营部门发出警报,以得到人工干预完成恢复。这种模式凸显出在24 x 7小时运营人员上的开支问题;更重要的是,如果运营工程师被要求在充满压力的情况下做出艰难的决定,那么有20%的可能他们会犯错误。这种模式的代价高 昂,容易引入错误,而且还会降低服务的整体可靠性。

    然而,注重自动化的设计会引入明显的服务模型约束。比如说,当前某些大型服务依靠的数据库系统,会以异步方式复制到次级备份服务器,因为复制以异步方式完 成,在主数据库无法服务请求后,故障转移到次级数据库会引起部分客户数据丢失。然而,不把故障转移到次级数据库,则会引起数据被储存在故障服务器上的用户 面临服务停工。在这种情况下,要自动化故障转移的决策就很困难了,因为这个决策依赖于人为判断,以及对数据损失量和停机大致时长相比的准确估计。注重自动 化设计出的系统会在延迟和同步复制的吞吐量开销上付出代价。在做到这一步以后,故障转移变成了一个很简单的决策:如果主服务器宕机,将请求转到次服务器 上。这种方式更适用于自动化,而且被认为更不容易产生错误。

    在设计和部署后将服务的管理过程自动化可能是一件相当具有难度的工作。成功的自动化必须保证简单性,以及清晰并易于确定的运营决策;这又要依靠对服务的谨 慎设计,甚至在必要时以一定的延迟和吞吐量为代价作出牺牲,让自动化变得简单。通常这样的折中方案并不容易确定,但是对于大规模服务来说在管理方面的节约 可能不止数量级。事实上,目前根据我们的观察,在人员成本方面,完全手动管理的服务和完全自动化的服务之间的差别足足有两个数量级。

注重自动化的设计包含以下最佳实践:

◆ 可以重启动,并保持冗余。所有的操作都必须可以重新启动,并且所有持久化状态也必须冗余存储。

◆ 支持地理分布。所有大规模服务都应当支持在多个托管数据中心运行。我们所描述的自动化和绝大多数功效在无地理分布的情况下仍是可行的。但缺乏对多服务中心 部署方式的支持,会引起运营成本显著提升。没有了地理分布,很难使用一个数据中心的空闲容量来减缓另外一个数据中心所托管的服务的负载。缺乏地理分布是一 项会导致成本提高的运营约束。

◆ 自动预置与安装。手动进行预置和安装是相当劳民伤财的,故障太多,而且微小的配置差异会慢慢在整个服务中蔓延开来,导致问题的确定越来越困难。

◆ 将配置和代码作为整体。请确保做到:

▲ 开发团队以整体单元的形式交付代码和配置;

▲ 该单元经过测试部门的部署,并严格按照运营部门将会部署的方式;

▲ 运营部门也按照整体单元的方式部署。

通常说,将配置和代码作为一整个单元处理并且只把它们放在一起修改的服务会更可靠。

◆ 如果配置必须在生产环境中变更,那么请保证所有的变更都要产生审核日志记录,这样什么东西被修改,在什么时候被修改,哪些服务器受到影响,就一目了然了。 频繁扫描所有的服务器,确保它们当前的状态与预期状态相符。这样做对捕获安装和配置故障颇有裨益,而且能在早期侦测到服务器的错误配置,还能找到未经审核 的服务器配置变更。

◆ 管理服务器的角色或者性质,而不是服务器本身。每个系统的角色或性质都应当按需要支持尽可能多或少的服务器。

◆ 多系统故障是常见的。请做好多台主机同时发生故障的准备(电源、网络切换和首次上线)。遗憾的是,带有状态的服务必须得注意它们的拓扑分布。有相互联系的故障一直以来都是不可避免的。

◆ 在服务级别上进行恢复。在服务级别处理故障,相比软件底层来说,其中的服务执行上下文更加完整。例如,将冗余纳入服务当中,而不是依靠较低的软件层来恢复。

◆ 对于不可恢复的信息,绝对不要依赖于本地存储。保证总是复制所有的非瞬时服务状态。

◆ 保持部署的简单性。文件复制是最理想的方式,因为这样能带来最大的部署灵活性。最小化外部依赖性;避免复杂的安装脚本;避免任何阻止不同组件或者同一个组件不同版本在同一台机器运行的情况。

◆ 定期使服务停转。停掉数据中心,关闭柜式服务器,断掉服务器电源。定期进行受控的关闭操作,能够主动暴露出服务器、系统和网络的缺陷。没有意愿在生产环境 中测试的人,实际上是还没有信心保证服务在经历故障时仍能继续运转。此外,若不进行生产测试,在真正出事时,恢复不一定能派上用场。

文/James Hamilton   译/赖翥翔

(来自:《程序员》杂志 )

1 分层

在横向维度上把系统划分为 3 层,每一层负责相对单一的职责,通过上层对下层的依赖与调用来构成一个完整的系统。

分层 描述
应用层 负责具体业务与视图展示。
服务层 为应用层提供服务支持。
数据层 提供数据访问服务。

只要维持调用的接口不变,各层就可以根据具体问题,独立演化发展。

在设计阶段,必须合理的规划各层之间的边界和接口。在开发阶段,必须严格遵循分层之间的约束,禁止跨层次调用(如应用层调服务层)以及逆向调用(如数据层调应用层)。

在实践中,这些分层还可以进一步细分。比如应用层再分为视图层与业务逻辑层;服务层分为数据接口层与逻辑处理层。

分层架构是逻辑上的划分,所以可以部署在同一台物理服务器上。但随着业务的发展,必须会对这些层进行分离部署,即把这些层分别部署在不同的物理服务器上。

分层架构对于以后支持高并发并朝着分布式方向发展很重要,所以在早期,就应该采用分层架构哦O(∩_∩)O~

引言

2 分割

分割指的是从纵向方面进行划分。

把不同的业务服务包装成高内聚低耦合的模块单元,这样不仅可以有助于开发和维护,也便于实现分布式部署。

6 异步

异步指的是把一个业务分为多个阶段,每个阶段通过共享数据进行协作工作。

单个服务器内可以通过多线程共享内存队列的方式实现异步;而在分布式系统中,多个服务器集群是通过分布式消息队列实现异步的。

异步架构就是典型的生产者/消费者模式。它们不直接调用,只是共享数据结构。

异步消息队列有这些特性:

  1. 提高系统可用性 - 消费者服务器发送故障,数据会在消息队列服务器存储堆积,但生产者服务器可以继续处理业务,系统整体表现为正常。待消费者服务器恢复后,就可以继续处理消息处理队列中的数据。

  2. 加快响应速度 - 生产者服务器处理完业务请求后,就把数据写入消息队列,无须等待消费者服务器响应即可返回。

  3. 消除并发访问高峰 - 消息队列服务器可以吸纳高峰期突然增加的访问请求数据,然后由消费者服务器依次处理,这样不会对整个负载造成太大的压力。

注意:异步方式会对用户体验和业务流程造成影响,所以需要得到产品设计方面的支持。

7 冗余

服务器随时可能出现故障,特别是服务器的规模比较大时,某台服务器出现宕机几乎是必然事件。所以为了保证服务与数据,就必须有一定数量的服务器冗余运行,数据冗余备份,这样当某台服务器宕机时,可以把其上的服务与数据转移到其他机器上。

即使是访问与负载很小的服务,也必须至少部署两台服务器构造一个小的集群,这样才能实现服务的高可用。数据库除了冷备份(定期备份、存档保存)外,还要对数据库进行主从分离,做热备份。

为了防范地震等不可抗力导致服务瘫痪的情况,一些大型网站会对整个数据中心进行备份,在全球范围内部署灾备数据中心。程序与数据会实时同步到多个灾备数据中心。

5 缓存

缓存指的是把数据存放在距离计算最近的位置以加快处理速度,它是改善性能的第一手段。有这些缓存方法:

  1. CDN - 内容分发网络,用户的请求会送达距离他最近的网络服务商,这里缓存了网站的一些静态资源,如果用户的请求是这些资源,那么就可以很快地响应啦O(∩_∩)O~

  2. 反向代理 - 是前端架构的一部分,它部署在前端,当用户的请求到达网站时,会最先访问反向代理服务器,这些也缓存了网站的一些静态资源,所以也会很快响应用户的啦O(∩_∩)O~

  3. 本地缓存 - 缓存着热点数据,应用程序可以直接从本机内存中读取数据。

  4. 分布式缓存 - 如果网站的数据量非常庞大,那么即使只是缓存一小部分,所需要的内存也不是单机能够承受的。为了解决这一问题,我们可以建立分布式缓存集群,应用程序通过网络来访问缓存数据。


使用缓存的前提条件是:

  1. 数据访问的热点并不均衡,即某些数据会被频繁地访问到,这些数据必须放入内存。
  2. 数据在某一个时间段内是有效的。如果很快过期,然后缓存数据就会因为失效而出现脏读问题。

在建筑领域是这样描述模式的:每一个模式描述了一个在我们周围不断重复发生的问题以及该问题的解决方案核心。我们可以一次又一次地使用这个方案而不必做重复的工作。模式的关键是可重复性,问题和场景的可重复性带来解决方案的可重复性。

3 分布式

分层与分割的目的之一是为了把这些模块进行分布式部署,即把这些模块部署在不同的服务器上,然后通过远程调用协同工作。这就意味着有更多的服务器来提供同样的服务,资源越多,那么支持的并发访问量和数据量就越大,进而可以为更多的用户服务。

但分布式也有一些缺点:

  1. 必须通过网络调用服务,而这可能会对性能造成严重影响。
  2. 服务器越多,宕机的可能性就越大,造成可用性降低。
  3. 保持数据一致性很困难。
  4. 开发、管理与维护困难。

所以要根据实际情况量力而行哦O(∩_∩)O~

目前有这些分布式方案:

  1. 分布式应用与服务 - 可以改善性能和并发性、加快开发与发布速度、减少数据库连接和不同的应用复用共同的服务。

  2. 分布式静态资源 - 动静分离,即把 js/css/图片等静态资源部署在独立域名下,这不仅可以加快浏览器的并发加载速度,而且还可以让负责用户体验的团队独立开发与维护这些静态资源,实现分工合作。

  3. 分布式数据和存储 - 大型网站需要处理以 P 为单位的海量数据,单台计算机无法提供这么大的存储空间,所以才要分布式存储。像各种 NoSQL 产品几乎都是分布式的。

  4. 分布式计算 - 处理在线业务之外,还有很大的一部分是用户直观感受不到的后台业务,诸如构建搜索引擎索引、数据分析统计等。现在普遍使用 Hadoop 和 MapReduce 分布式计算框架进行这一类的批处理计算。它们的特点是移动计算,即把计算程序分发到数据所在的位置以加速计算工作。

4 集群

要对用户访问集中的模块所部署的服务器建立集群,即多台服务器部署相同应用,然后通过负载均衡设备共同对外提供服务。

这样可以提供更好的并发能力,如果因为业务发展有了更多的并发用户的时候,我们只要向集群中增加新机器即可。而且可以提高系统的可用性,所以在早期,也要至少部署两台服务器以构建一个集群,保证可用性。

目前的网站架构有一些共同的模式(思路与解决方案),它们已经被大型网站一再验证,所以可以指导我们的架构设计。

8 自动化

目前的自动化主要集中在发布与运行维护上。

很多故障都出现在发布环节,所以实现发布自动化可以有效地减少故障。包括这些环节:

  1. 自动化代码管理 - 开发者只要提交自己代码,系统就会自动为其创建开发分支,自动进行代码合并。
  2. 自动化测试 - 系统自动把代码部署到测试环境,启动自动化测试用例进行测试,向相关人员发送测试报告,向系统反馈测试结果。
  3. 自动化安全检测 - 对代码进行静态安全扫描并部署到安全测试环境,进行安全攻击测试,评估系统的安全性。
  4. 自动化部署 - 把代码自动部署到线上生产环境。
  5. 自动化监控 - 对服务器进行心跳检测,监控它的各项性能指标和应用程序的关键数据指标。如果发现异常,就进行报警。然后进行失效转移,把失效的服务器从集群中隔离。故障消除后,在进行失效恢复。遇到访问高峰,进行降级,即拒绝部分请求以及关闭一部分不重要的服务。必要时,还需要主动分配资源,把空闲的资源分配给重要的服务。

正确地使用模式,可以用更少的时间开发出更好的系统,而且也使设计者的水平达到一个更高的水平。但要注意:模式受到应用场景的限制,对系统的约束也很多,所以要具体问题具体分析。

只有对问题有着深刻理解的基础上进行创新,才能有好的设计哦O(∩_∩)O~

本文由即开彩app下载发布于冶金矿产,转载请注明出处:说说大型网站的架构模式即开彩app下载

Ctrl+D 将本页面保存为书签,全面了解最新资讯,方便快捷。