美文网首页
系统设计题 Design Twitter/Facebook/We

系统设计题 Design Twitter/Facebook/We

作者: Sonass | 来源:发表于2017-08-29 07:26 被阅读0次

    X扯闲篇

    系统设计题目就是一个大坑 没有一个标准答案的意思就是面试官如果真跟你过不去随便挂人 跟玩儿似的。说答案的时候,总的来说,最注意把控的就是平衡细节的知识和大局的构架。什么意思?一,别有太多细节你自己说出来了你自己答不上,比如你说要用redis 结果redis数据放哪不知道。那就gg了。二, 别说一个细节说了十分多钟忘了之前到哪了。工程师就不能跟我一样,丢三落四的,就算你面试过了也一定做不了多好。勤看表不是问题,但是一定要有一个大概的感觉你每一个部分大概说多久,然后什么时候到哪了一定 一定 一定要有数。

    结构 (我这四十几分钟要说什么)

    有个培训机构叫太阁 他们用的方法是SNAKE 原则。啥意思啊?

    Scenario - Necessary - Application - Kilobit - Evolve 

    先说哪里用得到,再说我们需要解决问题多大规模。然后说基本解里头Application里面都有啥,然后说说相对应的数据放哪里怎么放。最后这些都说完了(20-25分钟左右)来具体谈怎么让我的基本解在哪些方面做的更好。

    还有个培训机构叫九章, 他们用的方法是4S原则,啥意思啊?

    Scenario - Service - Storage - Scale

    先说哪里用得到 要解决什么问题,然后说我们一个大系统对吧,怎么写出对应的micro services, 然后再说我们的数据放哪里怎么放,最后(也是20-25分钟后)说我们怎么样向上scale

    这两个大家想明白了其实就是一回事。这俩都有版权 我都不能用,如果各位是随便过来看到的,也推荐大家两个都上一下 相辅相成很有用。

    Scenario 场景

    1. 问清楚自己要做哪些功能(也就是说,45分钟内不聊哪些功能)

    2. 问清楚或者说清楚自己要handle多大用户量,面试官起码得给你确认这么几个信息,否则聊不下去。

    - 一个是你平均每天handle多少用户

    - 一个是你峰值(最多?不太精确但是形容一下)每天handle多少用户

    3. 自己把自己要算的东西都算出来, QPS啊,存储size啊,不非得一口气全部算完,但是记住最基本的用户量,然后再说然后的。

    Implementation 实现

    4. 搭架子,我的系统要干嘛,为了做这件事情,我们需要什么组件,怎么安排。这里一切最简单,保证这个东西可以work,不要有明显的优化还不做。

    5. 按照架子一个一个实现具体功能,如果发现有问题了,改改架子。记住。改架子的时候一定要想想别的东西动没动,动了,赶紧拿个纸记下来。数据放哪可以这里说可以分开说,这都不要紧。

    6. 架子流程实现完了想想数据放哪里怎么放,那么些个数据库呢,好好挑挑。

    Enhancement  提高

    7.根据确认的问题或者优化点慢慢优化。这里的话,不懂就说不懂。为啥?基本分已经有了,大好局面来之不易,千万不要不懂装懂暴露问题。比如你之前说的都挺好,然后到优化了把load balancer放到dispatch service还要靠前端的地方,这不扯么?

    具体结构怎么安排我等到自己练熟了以后我专门写一篇 我今天只写社交网络相关, 希望被我无耻强推连接的好友在评论里面多提意见,我也多改进。

    场景 Scenario

    上来我们第一个问题,没啥说的,

    用户在twitter/facebook/weibo上面都干啥?

    社交网络是吧,定义一下,是每个用户(人)对社交群体(人)的信息(帖子)分享。

    人和帖子,俩基本点,所以说呢?

    1. 好友关系,加好友,删好友, (改好友),查好友

    2. 帖子关系,加帖子,删帖子,改帖子,查(谁的)帖子

    具体点呢?

    增删帖子

    timeline (所有好友/单个好友的最近N个帖子。为啥N个?一屏放不下,数据发不完)

    新闻(理解成厂家小编名义发送的帖子,是为新闻 news feed)

    好友管理(增删改查,想到什么了没)

    用户管理(登陆、注册、profile)

    第二个问题,也没啥说的,

    我需要考虑多大的数据量?

    《=多大用户量以及用户都怎么用的?

    具体下来是这么几个:

    1. 日活用户多少啊?(How many daily active user(DAU) should I expect)

    根据不完全调查,一般来说:

    twitter: DAU 10M

    facebook: DAU 1.2B

    weibo: MAU 340M, DAU 11M

    2. 每天每个用户要expect多少个新帖子啊,多少次阅读啊?(How many daily new posts/reads should I expect per user)

    大坑预警: 不是直接问总共多少个,咱不是产品经理,问每人多少个

    twitter/facebook/weibo: 20min *25 read/min = 500 reads per user per day. (亲测差不多)  5 writes per user per day(亲测比这个少,但是自己跟朋友平均下来,这个数字也靠谱)

    3. 知道这几个数字了,能算QPS了不?

    大坑预警:QPS的S是啥?DAU的D是啥?两者啥关系?

               一天多少秒?24*60*60 = 86400秒

    就先拿weibo来算好了,中国人关注中国企业

    Read QPS:   500 * 11,000,000/ 86,400 .= 70K 

    Write QPS:   5 *11,000,000/86,400 = 700 QPS

    啥概念?咱一会儿说 别忘了哈!

    实现 Implementation

    来 先画图  

    我的架子怎么搭?


    关键点是?  人和帖子?

    人需要几个service? 好友管理和用户登陆

    帖子需要几个service?帖子管理和大文件存储

    所以一共?四个service


    User service

    每个用户的基本资料

    注册 登陆

    Posting Service

    每个帖子的内容和资料

    大坑预警:可别在这里放图片/文件/视频哈,说挂立刻就挂!!  那要放放哪?attachment service 能让别人打架绝不自己动手:)

    Friendship Service

    放每个用户的好友关系


    facebook 你是我好友 我肯定是你好友 双向保存也可以,单向保存也可以

    twitter/weibo不一定哦 分关注和被关注,这里到底是保存关注,保存被关注,还是都需要保存,就看具体实现了,设计的时候要有意识


    Attachment service 统一存放所有的大文件(图片,视频,pdf 等)

    如果多个人有同一个文件 正好!

    下一个问题: 

    数据怎么放?

    首先 基本概念,每个service考虑自己的就行。

    为啥?做成SOA(Service Oriented Architecture) 不就是为了每个service可以自己做事情么 而且每个service的数据存储模式是不一样的。既然不一样,那就分开放。

    下一个问题: 那你倒是放呀?

    好好 不着急不着急。。。


    User Info:  读远大于写,经典的SQL应用。

    Post Info: 内容不定,读写频繁,除时间外无法排序,适合NoSQL

    Attachment Info:  大文件 这就没啥可说的,只能放在文件系统里面。

    Friendship info: 关系确定(好友呗,最多再分一个类),有时排序,读远大于写。这个就不好说了。你想存SQL也行,你想存NoSQL也行。


    关于这几个数据库之间的关系,什么时候该用哪一个。我就将来另写一篇文章说这个问题了。感觉谁都会用到的。

    下一个问题: 该有的有了 该存的存了,

    流程啥样?

    用户注册:没啥可说的,user table里加一个entry

    用户注销: 别愣着直接删,标记不活跃就可以了

    用户登陆:关键字,不要原样传输密码,不要原样储存密码

    发帖:发帖。。。

    讲究就大了

    单纯发帖好说,post table里面加一个entry。如果有大文件,entry里面自动添加链接,attachment table里面加一个节点或者重用已有文件。

    可是我要怎么让关注我的人(不管是单向的还是双向的知道我发帖了呢)?

    首先 要想到有两种做法(想到一种不是你的错,但是认为没有别的路就是你要准备好被挂了)

    1. Push model: 用户发帖以后更新自己的记录以外,遍历所有follow自己的人,把这条帖子推送给他们对应的user service。user service 保存推送来的消息,用户显示朋友圈的时候,在接收到的消息里面选取topK个显示。

    2. Pull model: 用户发帖以后更新自己的记录。用户显示朋友圈的时候,把遍历所有自己follow的人拿topN个显示(N和K的关系可以另外算),截取topK个显示。

    所有培训机构的图都是有版权的不能用。我给大家放一个不完全准确的图。简单说,这里面都有一个遍历关系。

    push:遍历所有follow自己的人,每个人推送自己的更新

    pull:遍历所有自己follow的人,每次显示朋友圈的时候询问更新

    那我要怎么选择呢?上课都会讲怎么选择的,我们先从各自的优缺点开始。

    push:如果follow自己的人不多,省!

    pull:如果自己follow的人不多,省!

    push:如果自己follow的人不都活跃,省!

    pull:如果follow自己的人不都活跃,省!

    push:会带来一个特定的问题,叫做惊群效应 就是如果今天王宝强发了一个帖子,我的天爷,大家是不是纷纷点赞纷纷转发纷纷评论,这个如果用push的话,fanout结束怎么也得好几个小时吧?

    这个问题为啥难,因为所有的人修改的都是同一个帖子。什么caching,sharding,根本都不管用。我贴的链接不是关于网络系统设计的,是关于计算机系统设计的。这个问题不分软件固件,大家都能碰到。解决的办法说起来也只有慢慢fanout了,只要在用户的视角里面显示自己评论就可以了。

    pull:这个问题就不是特定了,为啥,因为王宝强少,看王宝强的人多。不论已婚与否,我们今天基本上男性劳苦大众都是关注的人比被关注的多。所以我们的问题就现打不赊着,如果不做任何优化,我们每次更新都要很慢,因为每次看朋友圈都要二重循环

    以上是基本解的实现。说了这么多,我想我都累了。面试官应该不会挂了吧(有问题指出来,要不我还是得挂!)。接下来就要说说一些相对比较高级的功能了。

    提高 Enhancement

    我自己这个破记性 能够把基本点记下来就不容易了,接下来你说要提高,那我们从提高开始,要记住什么要点呢?

    就从奥林匹克精神开始吧。更高咱先不说,先说后面两个

    更快:前面分析完了并发性 现在可以开始说说速度了,怎么样更快得到结果,让前端尽可能的不要等?

    更强:就是面对可能出现的各种问题是否有更好的准备和更好的解决办法。

    接下来我们就一个一个说我这里可能会想到的问题。

    我们先说更快,因为基本解来说,更快还是相对比较容易做到的。

    我们之前在基本解说了这么多,我们自己每天也都在用社交网络,我们要优化东西,就要牺牲东西。可以牺牲的东西一定是我们不太看重,或者不太感觉得到的东西,对吧?那么我们什么可以牺牲?什么不那么重要?

    答案:实时性(Real-time-ness)

    为啥?你今天分析你一个交恶的原密友发的不利于你的消息。你就关心他消息是什么时候发出来的,对不对?什么时候到你这里的,只要别太慢,你自己也没感觉,对吧?

    所以,只要保证时序性(最先发出来的帖子,最后在用户这里显示是显示在前面的),可以允许有些消息先显示出来,然后等到别人的消息来了再整理就好了。

    这样,对于pull来说,就有一个特别好的消息了。 我可以用缓存了。

    我先把缓存里面的信息先放出来,然后有消息来了我一点一点加进去(大家用微信看消息是不是就是这个感觉?消息在一点一点的更新?这就是pull+cache的用户体验)

    那push呢?

    王宝强级别的明星必须用pull,没说的。否则没有别的任何招数。普通人可以用push,反正不伤。

    那是吧,我们结合一下,如果明星用pull,普通人用push,是不是就两全其美了呢?

    不能说不是,但是会带来新的问题。叫摇摆效应。啥叫摇摆效应?

    比如说吧,咱划个线,粉丝一万以上叫明星,一万以下叫普通人

    要是有人本来10001个粉丝,今天掉了两个粉,我怎么办?如果明天又涨回来两个粉,我又怎么办?

    后台可以在这俩之间切来切去,但是这样不是要反复通知上下游的其他service吗?

    解决这个问题的办法来说,比较容易想到的就是设置一个过渡期,先默认是明星,如果普通人变成了明星,立刻改,如果明星变成了普通人,等待一段时间。

    下一个问题,取关怎么处理?

    还是那句话,你取关谁你看不见就行!

    所以我们就可以异步操作,先立刻删除缓存,在本机禁止显示关于被取关好友的消息,然后再异步发送给服务器来删除服务器上的好友记录。

    下一个话题, 更强, 也就是不能有东西挂掉

    单点failure怎么办?(有一台数据中心或者服务器down了)

    一,数据要复制,一份数据不能只放在一个地方(replica)

    二,数据要分散,不能所有的数据只放在一个地方(sharding)

    如何识别虚假用户?

    一,用户举报机制

    二,这是一个典型的supervised learning/classification, 用machine learning辅助判断

    然后今天就先说道这里。就像开头说的,系统设计想挂人还不容易,稍微在他进行的时候打断他两下问他两个细节,很多人就都不行了。所以。一定要记住大框架,然后时刻记住自己说道哪里了。


    相关文章

      网友评论

          本文标题:系统设计题 Design Twitter/Facebook/We

          本文链接:https://www.haomeiwen.com/subject/ycbndxtx.html