要想在系统设计方面脱颖而出,深入理解一些基本的系统设计概念很有必要,比如:负载平衡、缓存、分区、复制、数据库和代理等。
根据我的自身经历,我总结出了 16 个关键概念,这些概念可以大大提高你解决系统设计问题的能力。这些概念包括了解 API 网关的复杂性、掌握负载平衡技术、掌握 CDN 的重要性以及理解缓存在现代分布式系统中的作用。读完本文,你将对这些基本概念有一个全面的了解,并有信心在下一次面试中应用它们。
系统设计面试本质上是非结构化的。在面试过程中,你很难掌握事情的脉络,也很难保证你已经掌握了设计的所有重要方面。为了简化这一过程,我开发了一个系统设计主模板,它可以指导你回答任何系统设计面试问题。请看下图,深入了解系统设计中可能涉及的关键组件。
系统设计主模板
在主模板的指导下,我们将探讨 16 个基本的系统设计概念。
#01
域名系统(DNS)
域名系统(DNS)是互联网基础设施的基本组成部分,负责将便于人们记忆的域名翻译成相应的 IP 地址。它的功能就像互联网的电话簿,允许用户通过输入易于记忆的域名(如:www.designgurus.iorather),而不是输入计算机用来相互识别的数字 IP 地址(如:192.0.2.1)来访问网站和服务。
当你在网络浏览器中输入域名时,DNS 负责查找相关的 IP 地址,并将你的请求导向正确的服务器。在此过程中,计算机首先向递归解析器发送查询,然后解析器会搜索一系列 DNS 服务器,从根服务器开始,依次是顶级域(TLD)服务器,最后是权威名称服务器。一旦找到 IP 地址,递归解析器就会将其返回到你的计算机,使你的浏览器能够与目标服务器建立连接并访问所需的内容。
DNS解析器
#02
负载均衡器
负载平衡器是一种网络设备或软件,可将进入的网络流量分配给多个服务器,以确保最佳的资源利用率、减少延迟并保持高可用性。它在扩展应用程序和有效管理服务器工作负载方面发挥着重要作用,尤其是在流量突然激增或服务器之间请求分配不均的情况下。
负载平衡器使用不同的算法来决定如何分配进入的流量。常见的算法包括:
- 轮循:以循环方式在所有可用服务器上按顺序均匀分配请求。
- 最少连接:负载平衡器将请求分配给活动连接最少的服务器,优先选择较空闲的服务器。
- IP 哈希值:对客户端的 IP 地址进行散列,所得值用于确定请求应指向哪台服务器。这种方法可确保特定客户端的请求始终被路由到同一台服务器,从而有助于保持会话的持久性。
负载均衡器
#03
API 网关
API 网关是一种服务器或服务,它充当外部客户端与应用程序内部微服务或基于 API 的后端服务之间的中介。它是现代架构的重要组成部分,尤其是在基于微服务的系统中,它简化了通信过程,并为客户访问各种服务提供了单一入口。
API 网关的主要功能包括:
- 请求路由:它根据预定义的规则和配置,将客户端传入的 API 请求引导到适当的后端服务或微服务。
- 身份验证和授权:API 网关可以处理用户身份验证和授权,确保只有经过授权的客户端才能访问服务。它可以在将请求路由到后端服务之前验证 API 密钥、令牌或其他凭证。
- 速率限制和节流:为保护后端服务免受过度负载或滥用的影响,API 网关可根据预定义策略强制执行速率限制或客户端请求节流。
- 缓存:为减少延迟和后端负载,API Gateway 可以缓存经常使用的响应,将其直接提供给客户端,而无需查询后端服务。
- 请求和响应转换:API Gateway 可以修改请求和响应,如转换数据格式、添加或删除标头,或修改查询参数,以确保客户端和服务之间的兼容性。
API 网关
#04
CDN
CDN 是一个由服务器组成的分布式网络,用于存储并向地理位置较近的用户分发图片、视频、样式表和脚本等内容。CDN 旨在提高向终端用户传输内容的性能、速度和可靠性,而不论其相对于原始服务器的位置如何。
以下是 CDN 的工作原理:
- 当用户从网站或应用程序请求内容时,该请求会被定向到最近的 CDN 服务器,也称为边缘服务器。
- 如果边缘服务器缓存了所请求的内容,它就会直接向用户提供内容。由于内容的传输距离更短,这就减少了延迟并改善了用户体验。
- 如果边缘服务器上没有缓存内容,CDN 就会从原服务器或附近的其他 CDN 服务器获取内容。内容获取后,会缓存在边缘服务器上,然后提供给用户。
- 为确保内容保持最新,CDN 会定期检查源服务器上的变化,并相应更新其缓存。
#05
正向代理与反向代理
正向代理,又称 “代理服务器” 或简称 “代理”,是一种服务器,它位于一台或多台客户机之前,充当客户机与互联网之间的中介。当客户机向互联网上的资源发出请求时,该请求首先被发送到正向代理。然后,正向代理代表客户机将请求转发到互联网,并将响应返回给客户机。
反向代理是位于一个或多个网络服务器前面的服务器,充当网络服务器和互联网之间的中介。当客户端向互联网上的资源发出请求时,请求会首先发送到反向代理。然后,反向代理将请求转发给其中一个网络服务器,后者将响应返回给反向代理。然后,反向代理将响应返回给客户端。
正向代理和反向代理
#06
缓存
缓存是位于应用程序和原始数据源(如数据库、文件系统或远程网络服务)之间的高速存储层。当应用程序请求数据时,首先会在缓存中进行检查。如果在缓存中找到数据,就会返回给应用程序。如果缓存中找不到数据,就会从原始数据源检索数据,将其存储在缓存中,以备将来使用,然后再返回给应用程序。
在分布式系统中,缓存可以在多个地方进行,例如客户端、DNS、CDN、负载平衡器、API 网关、服务器、数据库等。
#07
数据分区
在数据库中,水平分区(也称为分片)是指将表中的行分成较小的表,并将它们存储在不同的服务器或数据库实例上。这样做是为了在多个服务器之间分配数据库的负载,提高性能。
另一方面,垂直分区涉及将表中的列划分到不同的表中。这样做的目的是减少表中列的数量,提高只访问少量列的查询性能。
数据分区
#08
数据库复制
数据库复制是一种用于在不同服务器或地点维护同一数据库多个副本的技术。数据库复制的主要目的是提高数据可用性、冗余性和容错性,确保系统在硬件故障或其他问题发生时仍能继续运行。
在复制数据库设置中,一台服务器作为主(或主)数据库,其他服务器作为副本(或从)数据库。这个过程涉及主数据库和副本之间的数据同步,因此它们都拥有相同的最新信息。数据库复制有以下几个好处:
- 提高性能:通过在多个副本之间分配读取查询,可以减少主数据库的负载,提高查询响应时间。
- 高可用性:在主数据库发生故障或停机的情况下,副本可以继续提供数据,确保不间断地访问应用程序。
- 增强数据保护:在不同地点拥有多个数据库副本有助于防止因硬件故障或其他灾难造成的数据丢失。
- 负载平衡:副本可以处理读取查询,从而更好地分配负载,减轻主数据库的总体压力。
#09
分布式消息系统
分布式消息系统能以可靠、可扩展和容错的方式,在多个可能分散在不同地理位置的应用程序、服务或组件之间交换消息。它们通过解耦发送方和接收方组件来促进通信,使其能够独立发展和运行。分布式消息系统在大规模或复杂的系统中特别有用,例如在微服务架构或分布式计算环境中。Apache Kafka 和 RabbitMQ 就是这样的系统。
#10
微服务
微服务是一种架构风格,在这种风格中,应用程序被构造成一个小型、松散耦合、可独立部署的服务集合。每个微服务负责应用程序中的特定功能或领域,并通过定义明确的应用程序接口与其他微服务通信。这种方法有别于传统的单体架构,在单体架构中,应用程序是作为一个单一、紧密耦合的单元构建的。
微服务的主要特点有:
- 单一责任:每个微服务都专注于特定的功能或领域,遵循单一责任原则。这使得服务更易于理解、开发和维护。
- 独立性:微服务可以独立开发、部署和扩展。这就提高了开发过程的灵活性和敏捷性,因为团队可以同时开发不同的服务,而不会影响整个系统。
- 分散:微服务通常是分散的,每个服务都拥有自己的数据和业务逻辑。这鼓励了关注点的分离,使团队能够做出决定并选择最适合其特定要求的技术。
- 通信:微服务之间使用 HTTP/REST、gRPC 或消息队列等轻量级协议进行通信。这促进了互操作性,使集成新服务或替换现有服务变得更容易。
- 容错性:由于微服务是独立的,一个服务的故障不一定会导致整个系统的故障。这有助于提高应用程序的整体弹性。
#11
NoSQL 数据库
NoSQL 数据库或 “Not Only SQL” 数据库是一种非关系型数据库,旨在存储、管理和检索非结构化或半结构化数据。它们为依赖结构化数据和预定义模式的传统关系数据库提供了一种替代方案。NoSQL 数据库因其灵活性、可扩展性和处理大量数据的能力而广受欢迎,非常适合现代应用、大数据处理和实时分析。
NoSQL 数据库可分为四大类型:
- 基于文档:这些数据库以类似文档的结构(如 JSON 或 BSON)存储数据。每个文档都是独立的,可以有自己独特的结构,因此适合处理异构数据。基于文档的 NoSQL 数据库包括 MongoDB 和 Couchbase。
- 键值对:这些数据库以键值对的形式存储数据,其中键是唯一标识符,而值则保存相关数据。键值数据库在进行简单读写操作时效率很高,而且可以轻松分区和横向扩展。键值 NoSQL 数据库的例子包括 Redis 和 Amazon DynamoDB。
- 列族型:这些数据库将数据存储在列族中,列族是相关列的组。它们设计用于处理写入量大的工作负载,并能高效查询已知行和列键的数据。列族 NoSQL 数据库的例子包括 Apache Cassandra 和 HBase。
- 基于图形:这类数据库设计用于存储和查询具有复杂关系和互连结构的数据,如社交网络或推荐系统。图形数据库使用节点、边和属性来表示和存储数据,从而更容易执行复杂的遍历和基于关系的查询。基于图的 NoSQL 数据库包括 Neo4j 和 Amazon Neptune。
NoSQL 数据库的类型
#12
数据库索引
数据库索引是一种数据结构,可提高数据库中查询操作的速度和效率。其工作原理类似于书籍中的索引,允许数据库管理系统(DBMS)快速查找与特定值或特定值集相关的数据,而无需搜索表中的每一行。通过提供更直接的路径来获取所需数据,索引可以大大缩短从数据库中检索信息所需的时间。
索引通常建立在数据库表的一个或多个列上。最常见的索引类型是 B 树索引,它以分层树结构组织数据,允许快速搜索、插入和删除操作。还有其他类型的索引,如位图索引和哈希索引,每种索引都有其特定的使用情况和优势。
虽然索引能显著提高查询性能,但它们也会有一些权衡:
- 存储空间:索引会消耗额外的存储空间,因为它们会在创建和维护原始表数据的同时创建和维护单独的数据结构。
- 写入性能:在表中插入、更新或删除数据时,必须同时更新相关索引,这会降低写入操作的速度。
数据库索引
#13
分布式文件系统
分布式文件系统是一种存储解决方案,旨在管理和提供对多个服务器、节点或机器(通常分布在网络上)上的文件和目录的访问。它们使用户和应用程序能够访问和操作文件,就像文件存储在本地文件系统上一样,即使实际文件可能实际存储在多个远程服务器上。分布式文件系统通常用于大规模或分布式计算环境,以提供容错、高可用性和更高的性能。
#14
通知系统
用于向用户发送通知或警报,如电子邮件、推送通知或短信。
#15
全文搜索
全文搜索使用户能够在应用程序或网站中搜索特定的单词或短语。当用户查询时,应用程序或网站会返回最相关的结果。
为了快速高效地完成这项工作,全文搜索依赖于倒排索引,这是一种将单词或短语映射到出现这些单词或短语的文档的数据结构。Elastic Search 就是此类系统的一个例子。
#16
分布式协调服务
分布式协调服务是一种系统,旨在以可靠、高效和容错的方式管理和协调分布式应用程序、服务或节点的活动。它们有助于保持一致性、处理分布式同步,以及管理分布式环境中各种组件的配置和状态。
分布式协调服务在大规模或复杂系统中特别有用,例如微服务架构、分布式计算环境或集群数据库中的系统。此类服务的例子有 Apache ZooKeeper、etcd 和 Consul。
作者:乔鹏飞 来源:https://t.1yb.co/JVQb