系统设计笔记 一
一个好的系统离不开好的设计,那么如何进行系统设计呢?
系统设计分为7个步骤:
- 明确需求
- 系统接口定义
- 评估系统规模
- 定义数据模型
- 高层次设计
- 细节设计
- 找到并解决瓶颈
接下来一个一个来解释。
1、明确需求
在设计一个系统前,必须要完全明确需求,以及系统的重点部分。
比如设计一个类Twitter服务,需要思考以下几个问题:
- 我们服务的用户是否能够推送tweet消息并且关注其他人?
- 我们是否应该设计创建和展示用户时间线的功能?
- tweet信息中包含图片和视频吗?
- 是否我们只需要关注后端?还是前端也要关注?
- 用户能够搜索tweet信息吗?
- 我们需要展示热点话题吗?
- 新tweet和重要tweet会有消息提醒吗?
2、系统接口定义
定义系统的API接口,这样可以进一步梳理需求,防止漏掉某些功能。
例:
postTweet(user_id, tweet_data, weet_location, user_location, ...)
generateTimeline(user_i, current_time, user_location, ...)
markTweetFavorite(user_id, tweet_id, timestamp, ...)
3、评估系统规模
我们在设计系统之前需要评估系统的规模,这可以帮助我们设计系统和数据的分割、负载均衡、缓存等策略。我们需要思考以下几个问题
- 期望中系统有多大的规模?(新tweet的数量、tweet的访问量等)
- 需要多大的存储空间?(若果tweet中可以加入图片和视频,则需要更大的存储空间)
- 需要多大的网络带宽?这是决定我们如何进行负载均衡的关键
4、定义数据模型
更早的定义数据模型可以使我们清晰数据在系统中各模块之间是如何流动的。这也可以帮助我们进行数据的切分和管理。
下面是一些类推特服务的实体:
- User: UserID, Name, Email, DoB, CreationData, LastLogin.
- Tweet: TweetID, Content, TweetLocation, NumerOfLikes, TimeStamp.
我们还要考虑到使用哪种类型的数据库存储这些数据,以及存储图片和视频的文件存储系统。
5、高层次设计
系统层面上的设计,可以通过画图来展示整个系统的高层次设计。对于一个类Twitter服务,我们需要多台服务器来进行读写的负载均衡,根据不同情况,例如读多写少,进行服务器分配。并且图片和视频的存放也可以考虑使用分布式文件存储系统。
6、细节设计
设计不只有一种方案,对于一些细节问题,可能有多种解决方案,要分析出他们的优缺点,进行权衡。我们需要思考以下问题:
- 在存储大量的数据后,我们应该如何将数据切分成多个部分存放在不同的数据库中?应该将一个用户所有的数据存放在同一个数据库中吗?这会造成什么问题?
- 我们如何处理那些发了很多tweet或者关注了很多人的活跃用户?
- 在哪里可以使用缓存来提升速度?
- 如何设计负载均衡?
7、找到并解决瓶颈
尝试发现一些瓶颈部分,并思考优化方案。
- 在系统中是否会出现某些点失效的情况?如何避免或减少其造成的影响?
- 当一些服务器宕机后,系统是否有备份数据来服务我们的用户?
- 相同的,我们是否运行足够的服务来避免一点小问题导致整个系统崩掉?
- 我们如何监控服务的状态?会在关键模块出错或者效率变低时发出警告吗?
参考:Grokking the System Design Interview