[转贴]当年的山寨开心网首页分析和kaixin001的架构分析

jackxiang 2010-4-23 16:39 | |
1. Javascript文件直接写在了网页当中
2. 网页没有开启gzip
3. Javascript没有做任何处理
4. 图片文件过大

1. 首页处理得比较到位,虽然javascript也没有压缩,但总大小只有108k

  2. 文件请求数较少,这个和开心网本身有关,开心网本来就不是一个网页结构复杂的网站,所以文件数自然会比较少了

  3. 静态文件和网页分开部署

  4. Javascript注释比较好,但不应该发到客户端

  重要建议:

  1. 开启gzip压缩

  2. 压缩javascript及css,并将这些文件缓存起来






开心网是一个人气蛮高的sns社区,虽然在走下坡路了,在国内依然算是顶尖了,今天我们就来分析一下开心网的设计架构是怎样的。因为手头没有这方面的资料,也没有和开心网的程序员有过什么交流,所以今天所写的一切都是自己的猜测而已。不能对号入座。

关于开心网的系统架构分析

一.入口篇
   从http://www.kaixin001.com/,从这个页面可以看到,开心网的图片,是放在http://img.kaixin001.com上的,做了程序与图片的分离(http://www.kaixin001.com/i...这个不知为什么没有分离)。
   下面来看一下开心网前端的服务器情况,nslookup一下,可以看到,一共有下面的17个IP
220.181.66.138,123.103.12.24,123.103.12.25,123.103.12.26,123.103.12.27
123.103.12.28,123.103.12.36,123.103.12.37,123.103.12.38,123.103.12.39
123.103.101.98,123.103.101.107,123.103.101.116,123.103.102.130,220.181.66.131
220.181.66.135,220.181.66.136
   (图片服务器用了ChinaCache的CDN,这个不是重点就不详细说了)
  以上可以看出,开心网的前端用了DNS轮询。
  再来分析一下前端服务器是什么呢?根据用httpwatch查询的结果可以看出,他使用的是apache作为服务器,max-age=1,等于设置缓存,并且开启了gzip压缩。目前只能看到这些了。

  开心网的web没有用squid或者lvs让我有些意外。从我们做中金博客的经验来说,仅仅依赖DNS轮询是一个非常不保险的东西,DNS轮询分配的压力非常不平均,或许跟开心网的应用都需要登录有关吧。
PS:开心网的首页竟然是一个动态的php。http://www.kaixin001.com/i...
    
    二.程序篇
   另外服务器既然有多台进行轮询,就必须考虑一个session共用的问题,session共用现在有几种方式:
  1.写入数据库(将数据文件放在内存中,读取速度还是很快的,而且统计时候方便,缺点就是访问量超大的时候,数据库链接有时会满掉。中金博客目前用的就是这种方式)

  2.写入使用nfs挂载,将一块空间专门划分出来挂载在每台服务器上,存放session文件,以前李杰说17173的bbs好像是通过这样的方式,2年前的事了,不知现在是否改了没有,这个方式主要依赖于网络状况,网络断开或者挂载的服务器挂掉就会出现问题了,这个方案同样可以划出一部分内存来做nfs,避免硬盘的io

    3.写入memcache,将session写到memcache中是一个很好的方案,他解决了1,2优点,虽然依赖网络,但是可以做一个群组,不会有单点故障,且不会出现连接数满掉的情况,但是它也有一个麻烦的地方,就是无法进行统计操作(或许用dbcache可以解决)。原本中金博客是要用这个方法的,后来因为种种原因没有上线。

   上面三种是较常见的session保存方式,相信开心网也是用这三种之一。顺便提一句,不共用session的话,一般情况下,对于用户访问不会出什么问题,因为用户浏览器会缓存dns的结果,在一定的时间内,用户访问到的实际上还是同一台服务器的。

  登录到开心网以后,每个模块的网址类似:
  http://www.kaixin001.com/!...应该是没有经过rewrite,而是用文件夹放置不同的模块,这个地方没有什么疑问的。

  而每个模块都是php的页面,不可能每次都去直接连接数据库,肯定都用了缓存,相信缓存很有可能是用memcache,因为文件缓存的同步是一个复杂且容易出错的方式,对于有几十台Web服务器的应用,实在不适合用本地文件缓存的方式。

   下面我们以争车位这个模块来说明memcache缓存是如何实现的(当然是猜想的)。

   首先,进入模块后,会显示我家的停车情况,点击好友,会显示好友家的停车情况。
   而这个操作实际上是从一个地址http://www.kaixin001.com/p...获得的。这个地址返回的内容是类似php序列化的一个字符串,这些由js去解析,并展示出来。那程序应该如何操作呢?程序(user.php)接到post请求后,根据id,首先从memcache(假定此时缓存用memcache)中寻找是否有匹配的记录,若没有,则向数据库请求获取数据,重写回memcache,并返回数据。

   而停车的情况呢,程序即写一个停车的队列,表示某某时间A将二手奥拓停放在B的第2号车位,并更新memcache的缓存,此时并不会更新数据库的状态,而这个队列,将通过定时的脚本更新至数据库。

   顺便说一下我为什么会认为写入的流程是这样的:有一次我去停车,点击了我的车到某个车位上,页面刷了一下,我惊奇的发现竟然没停上去,当时我想是开心网出啥问题了,那就等等呗。过了大约一个小时,发现竟然车子好端端的停在那个车位上了。这个情况在那个阶段大约隔几天就会出现一次,按照我说的模式,点击停车,没有停上去(更新缓存失败了),过了一会又去看,发现已经停在上面了(缓存过期,队列已经更新到数据库)。 所以大概都是这样的方式。当然有的模块可能是将数据直接写入数据库的。但是读出的时候,肯定是有做缓存的。或许又有人说程序可能不直接链接数据库,而是通过类似WebService的东西去实现数据库操作,是的,有可能,可是大概是做了中金项目的后遗症吧,我对于WebService及Soap的使用的理解是对于需要开发给外部调用的功能才使用,而本身应用完全没有必要绕这个圈子,会降低很大的性能。所以我宁可相信开心网自己的应用是没有使用WebService去连接数据库的。

   每个模块的实现就不去谈那么多了,这里说的是系统架构,就我的经验来说web前端最重要的就是缓存及其同步问题,若处理的好,整个应用的性能会大幅度提高。


   三.数据库  
   数据库方面的变化相对较少,使用php的网站,90%都会用mysql。开心网的用户数没有官方的数字,我估计不低于500W,而其他的用户相关的记录,如“我看过的电影”之类的,恐怕只会多,不会少,如此大量的数据放在一张表里面,肯定会出问题,所以必须采用分表存储,这样就涉及到用哪种规则来分表,一般情况下有2种。用id和日期来分,对于用户,大多还是会用用户id作为规则来分的。
  
   当然,开心网还有一个特殊性,他是由用户中心,及一个一个模块组成的,所以,数据库的组成应该是用户中心为一个库,其他每个模块为独立的库。而每个库都可以做成master/slave的模式,实现读写分离和备份,考虑到若读操作很大量,则可以在slave前放置一个lvs实现负载均衡(mysql proxy似乎可以实现类似的功能,但是我没用过),以保证数据库的稳定性。当然虽然是独立的库,但是服务器有可能是在同一台,相信开心网还没阔到每个应用都用独立的数据库服务器的地步。

作者:jackxiang@向东博客 专注WEB应用 构架之美 --- 构架之美,在于尽态极妍 | 应用之美,在于药到病除
地址:https://jackxiang.com/post/2991/
版权所有。转载时必须以链接形式注明作者和原始出处及本声明!


最后编辑: jackxiang 编辑于2010-4-23 16:48
评论列表
发表评论

昵称

网址

电邮

打开HTML 打开UBB 打开表情 隐藏 记住我 [登入] [注册]