架构设计指南 如何成为架构师

Posted 抓手

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了架构设计指南 如何成为架构师相关的知识,希望对你有一定的参考价值。

一:技术选型

创业初期架构方案怎么选型?

(1)要考虑业务的需求与特点,初期往往“快速实现”更重要,此时系统的特点是请求量小,数据量小,服务器资源也非常有限;

(2)这个阶段最重要的选型依据是:合伙人熟悉什么技术栈,使用什么技术栈

(3)第一版往往采用ALL in one架构

(4)这个阶段研发主要在写CURD业务逻辑,引入DAO和ORM能极大提高工程效率;

画外音:什么是ALL in one架构?。

如果硬要问我,会选择什么技术栈,我会二选一:

php体系(Linux,Apache,mysql,PHP)

或者

Java体系(Linux,Tomcat,MySQL,Java)

使用开源框架组件还是自研?

我的观点是:

(1)早期不建议自研

(2)随着规模的扩大,要控制技术栈

(3)要浅浅的封装一层

(4)适当的时候,造一些契合业务的轮子;

画外音:为什么要控制技术栈?为什么要封装一层?

什么情况下要进行容量评估?

至少在三种情况下,要进行容量评估:

(1)新系统上线

(2)临时运营活动

(3)系统容量有质变性增长

系统层面,要评估哪些重要指标?

主要评估网络带宽、CPU、内存容量、磁盘容量、磁盘IO等资源指标,系统层面主要看吞吐量指标。

画外音:容量设计五大步骤是啥?

创业初期,系统层面存在瓶颈的时候,优化原则是什么?

(1)最低成本,初期最大的成本是时间成本;

(2)用“钱”和“资源”快速解决系统问题,而不是过早的系统重构;

(3)将ALL in one架构升级为伪分布式架构,是此阶段的最佳实践;

伪分布式的核心是什么?

伪分布式的本质是单机变多机,但又不是真正的高可用,其核心是垂直拆分:

(1)业务垂直拆分;

(2)代码垂直拆分;

(3)数据库垂直拆分;

(4)研发团队垂直拆分;

画外音:伪分布式的优化细节是啥?

二:接入层架构

如何解决接入层的扩展性问题?

引入反向代理。

最常见的反向代理是什么?

nginx

引入反向代理之后,要解决什么新的问题?

(1)集群负载均衡;

(2)反向代理高可用;

画外音:有哪些常见的负载均衡方法?如何保证反向代理高可用?

站点流量从小到大,接入层架构如何演进?

整体可以分为五个阶段

(1)有反向代理技术之前,单体架构要解决扩展性问题,可使用DNS轮询架构

(2)有反向代理技术之后,初期可以使用反向代理解决扩展性问题;

(3)然后,需要升级为高可用反向代理架构

(4)多级反向代理,引入LVS&F5进一步扩充性能;

(5)想要无限性能,必须用DNS轮询架构

画外音:每个阶段的逻辑与细节到底是怎么样的?

Session,是接入层架构非常关注的问题,如何保证Session一致性?

通常有四种方案

(1)客户端层解决;

(2)反向代理层解决;

(3)web-server层解决;

(4)后端服务层解决

画外音:每种方案细节又是怎么样的?

CDN,是接入层不得不谈的问题,CDN架构有哪些要了解?

引入CDN架构,至少要考虑这五个问题

(1)什么样的资源适合静态加速;

(2)CDN的架构是怎么样的;

(3)CDN是怎么实现“就近访问的”;

(4)如何保证源站和镜像站数据的一致性;

(5)资源更新,是推还是拉?

画外音:学CDN,千万不要去百度“斯塔尔报告”。

TCP接入,架构上要考虑哪些问题?

至少要考虑这四个架构设计点

(1)TCP如何快速实现接入;

(2)TCP如何快速实现扩展,以及高可用;

(3)TCP如何快速实现负载均衡;

(4)TCP如何保证扩展性与耦合性的平衡;

画外音:有没有综合方案,系统性解决负载均衡 + 高可用 + 可扩展 + 解耦合等一系列问题?

三:急速性能优化

在互联网公司发展早期,为了产品快速迭代,最常使用的架构是什么?

ALL in one架构。

如果此时业务发展很快,系统成了瓶颈,架构优化的方向是什么?

用最短时间,以对代码最小的冲击,极速扩充系统性能

早期如何快速的扩充系统性能?

使用三大分离的性能优化方法。

早期系统容易“白屏”,如何快速的提升用户体验,消除白屏?

动静分离

什么是动静分离?

动静分离,是“静态页面与动态页面,分开不同的系统访问”的架构设计方法。

画外音:如何来实施?分别对应怎样的技术点?

如果静态页面访问这么快,动态页面访问这么慢,能否将“原本需要动态生成的页面,提前生成静态页面”?

可以,这是“页面静态化技术,能够100倍提升访问速度。

画外音:这个技术适用怎么样的业务场景?

早期系统的主要瓶颈,最容易出现在哪里?

数据库读性能扛不住。

如何快速提升数据库读性能?

读写分离,使用数据库分组架构,一主多从,主从同步,读写分离。

画外音:读写分离,水平切分都是使用数据库集群,有什么异同?

后台运营系统,复杂的SQL语句对数据库性能影响较大,怎么办?

前台与后台分离

画外音:前后端分离,前台后台分离,是一回事么?如何快速实施前台与后台分离?

四:微服务架构

系统初期,哪类技术栈最为流行?

(1)PHP语言的LAMP栈;;

(2)Java语言的LiToMyJa栈;

业务快速发展,三层架构可能存在哪些问题?

(1)代码频繁拷贝;

(2)底层复杂性扩散;

(3)公共库耦合;

(4)SQL质量不可控,数据库性能急剧下降;

(5)数据库耦合,无法实现增加实例扩容;

可以通过什么架构方案解决上述1-5问题?

微服务架构

如果要落地微服务架构,服务粒度可以如何选择?

常见的有以下四种粒度:

(1)统一服务层;

(2)按业务划分服务;

(3)按库划分服务;

(4)按接口划分服务(需要轻量级进程等语言层面支持);

微服务架构,可能带来什么问题?

可能带来的潜在问题有:

(1)系统复杂性上升;

(2)层次间依赖关系变得复杂;

(3)运维,部署更麻烦;

(4)监控变得更复杂;

(5)定位问题更麻烦;

不要以为,引入一个RPC框架就是“微服务架构”了,微服务架构要解决很多问题。

微服务架构要解决哪些问题?

至少要解决高可用无限性能扩展负载均衡等众多架构基础问题。

如何解决高可用的问题?

每一层解决高可用问题的方案不一样,涉及虚IP,反向代理,集群,连接池,数据库分组,缓存冗余,故障转移等诸多技术。

画外音:高可用的方法论是什么?

如何解决无限性能扩展的问题?

每一层解决高可用问题的方案不一样,涉Scale upScale out,DNS轮询,反向代理,连接池,水平切分等诸多技术。

画外音:无限性能的方法论是什么?

如何解决负载均衡的问题?

负载均衡分为两类:

(1)同构均匀分摊;

(2)异构按能力分摊;

异构服务器负载均衡,常见的这么几种方案:

(1)静态权重法;

(2)动态权重法,涉及“保险丝”算法;

同时,动态权重法还可以实现服务器的过载保护

画外音:什么是“保险丝”算法?什么是过载保护?

哪一个组件,和高可用,无限性能扩展,负载均衡相关?

连接池。

连接池的核心是什么?

两个核心数据结构:连接数组,锁数据;

三个核心接口:初始化,拿出连接,放回连接;

画外音:如何快速掌握连接池内核?

五:数据库架构

工程上,数据库要设计一些什么?

(1)根据“业务模式”设计表结构

(2)根据“访问模式”设计索引结构

架构上,数据库还必须考虑什么?

(1)读性能提升;

(2)高可用;

(3)一致性保障;

(4)扩展性;

(5)垂直拆分;

画外音:我C,我居然从来没考虑过这些问题。

提升系统读取速度,有哪几种常见方法?

(1)建立索引;

(2)增加从库;

(3)增加缓存;

一个数据库分组集群,主从同步,读写分离,能不能在主库和从库建立不同的索引?

可以,例如:

(1)主库只响应写请求,不建立索引;

(2)线上从库,建立线上访问索引;

(3)后台从库,建立后台访问索引;

如何保证数据库的高可用?

核心思想是:冗余+故障自动转移

(1)写库高可用,冗余写库;

(2)读库高可用,冗余读库;

数据冗余会带来什么副作用?

会引发一致性问题:

(1)两个写库数据可能不一致;

(2)主库和从库数据可能不一致;

写库高可用,两个写库相互同步数据,自增ID可能冲突导致数据不一致,有什么优化方案?

(1)为每个写库指定不同的初始值,相同的增长步长;

(2)生成不同的ID;

(3)一个写库提供服务,一个写库作为高可用影子主;

主从延时,有什么优化方案?

(1)业务容忍;

(2)强制读主;

(3)在从库有可能读到旧数据时,选择性读主(非常帅气的方案);

底层表结构变更,水平扩展分库个数发生变化,底层存储引擎升级,数据库如何平滑过度?

如果业务能够接受,可以停服扩展。

否则,可以使用以下三种方法:

(1)追日志平滑扩容法,平滑过度;

(2)双写平滑扩容法,平滑过度;

(3)秒级平滑扩容法(非常帅气的方案);

画外音:如何在秒级,实现读写实例加倍?容量加倍?

数据库垂直拆分的最佳实践是什么?

数据库垂直拆分,尽量把:

(1)长度短;

(2)访问频率高;

(3)经常一起访问;

的数据放在主表里。

六:缓存架构

工程上,缓存一般有几种使用方式?

(1)进程内缓存

(2)进程外缓存,也就是缓存服务

如果有多个服务使用进程内缓存,如何保证一致性?

常见的有三种方法:

(1)服务节点同步通知;

(2)MQ异步通知;

(3)牺牲少量一致性,定期后端更新;

绝大部分情况,还是应该使用缓存服务,缓存的使用,有什么注意点?

以下几点,应该要注意:

(1)服务与服务之间不要通过缓存传递数据;

(2)如果缓存挂掉,可能导致雪崩,此时要做高可用缓存,或者水平切分;

(3)调用方不宜再单独使用缓存存储服务底层的数据,容易出现数据不一致,以及反向依赖;

(4)不同服务,缓存实例要做垂直拆分,不宜共用缓存;

互联网缓存操作细节,最佳实践是什么?

Cache Aside Pattern

Cache Aside Pattern的细节是什么?

它分为读缓存最佳实践,以及写缓存最佳实践。

读缓存最佳实践是:先读缓存,命中则返回;未命中则读数据库,然后设置缓存。

写缓存最佳实践是:

(1)淘汰缓存,而不是修改缓存;

(2)先操作数据库,再操作缓存;

画外音:为什么呢?

缓存的本质是“冗余了数据库中的数据”,可能存在什么问题?

缓存与数据库数据不一致

什么场景下容易出现不一致?

写后立即读业务场景。

画外音:为什么呢?

出现不一致时,优化思路是什么?

及时把缓存中的脏数据淘汰掉。

具体要怎么淘汰,保证缓存与数据库中数据的一致性呢?

(1)服务同步二次淘汰法;

(2)服务异步二次淘汰法;

(3)线下异步二次淘汰法;

画外音:二次淘汰法,是很常见的一种实践。

目前缓存服务最常用的是什么?

Redis和memcache。

什么时候选择使用Redis?

以下场景优先使用Redis:

(1)需要支持复杂数据结构;

(2)需要支持持久化;

(3)需要天然高可用;

(4)value存储内容比较大;

如果只是纯KV,可以使用memcache。

画外音:纯KV场景,为什么memcache会更快呢?

七:架构解耦

配置文件,是互联网架构中不可缺少的一环。依赖(调用)某个下游服务集群,将下游集群信息放在自身配置文件里是一种惯用做法,该做法可能导致什么问题?

可能导致上下游严重耦合:

(1)上游痛:扩容的是下游,改配置重启的是上游;

画外音:架构设计中典型的反向依赖。

(2)下游痛:不知道谁依赖于自己,难以实施服务治理,按调用方限流;

为了解决上述问题,常见的配置架构演进是怎么样的?

(1)“配置私藏”架构;

(2)“全局配置文件”架构;

(3)“配置中心”架构;

除了配置中心,消息总线MQ也是互联网架构中的常见解耦利器。

一般来说,什么时候不使用MQ?

上游实时关注执行结果时,通常不使用MQ,而使用RPC调用。

什么情况下,可以使用MQ来解耦?

以下四种情况,可以使用MQ来解耦:

(1)数据驱动的任务依赖;

(2)上游不关心执行结果;

(3)上游关注结果,但执行时间很长,例如跨公网调用第三方服务;

(4)削峰填谷,流量控制,保护下游;

上下游IP耦合,可以如何解耦?

使用内网域名来代替内网IP。

多个模块,因为公共库而耦合在一起,可以如何解耦?

粗暴方案:代码各自拷贝一份(不太推荐)。

优化方案:

(1)垂直拆分,个性业务代码“上浮”;

(2)服务化,共性业务代码“下沉”;

多个模块,因为数据库而耦合在一起,可以如何解耦?

数据库耦合,需要对架构进行调整:

(1)第一步,公共数据访问服务化,数据私藏;

(2)第二步,个性数据访问,自己家的数据自己管理;

画外音:数据库耦合,当数据库成为瓶颈时,增加数据库实例也难以拆分扩容,非常头疼。

以上是关于架构设计指南 如何成为架构师的主要内容,如果未能解决你的问题,请参考以下文章

架构师必读:微服务架构设计指南

顶尖架构师也该掌握的微服务架构设计指南

成为架构师课程系列怎样进行系统详细架构设计?

聊聊架构设计做些什么来谈如何成为架构师

什么是架构师和如何成为一个架构师

阿里Java架构师谈谈架构和如何成为一个Java架构师