ItFans

ItFans

 

2011年12月14日

2011 年最重要的 10 个开源软件

2011 年即将过去,是该对这即将过去的这一年做一个总结,这么一个标题如何去确定其实是很难的,而且也可能会比较片面。那么什么叫做“重要”呢,什么样的开源软件算是“重要”呢?首先,并不是使用的人多就算是“重要”,否则每一年选出来的项目估计都差不多。 所以要判断一个开源软件是否重要,首先要有影响力,以及或者在某个新领域的佼佼者。换句话说,重要的项目必须引起大家更多的关注。依据这么一个判别条件,我们挑出了2011年最重要的开源软件,你或许不认可但请别喷,你可以整理你自己的2011 Top 10 :)

Hadoop

首先出场的是Hadoop,毫无疑问这个来自 Apache 基金会的分布式计算平台当得起“重要”二字,在过去的一年中这个由 Yahoo 发起的项目正在为包括 Amazon、IBM、Twitter、Facebook 等公司所使用。

尽管不是一个新项目,但 Hadoop 已经成为事实上的分布式计算标准。

Git

Git 已经无所不在了,不是吗? Linus Torvalds 不只是对 Linux 操作系统有贡献,他也让更多的开源项目变得流行起来,在分布式版本控制上,使用 Git 会比其他解决方案更可靠。

Git 不只是一个受欢迎的工具,还有一个基于 Git 的开源软件社区 GitHub,这跟包括 Gitorious、SF、Google Code 项目托管平台类似,但远不止于此。

Cassandra

Cassandra 获得了 2011 最佳 NoSQL 解决方案奖项,Apache Cassandra是一套开源分布式Key-Value存储系统。它最初由Facebook开发,用于储存特别大的数据。Facebook目前在使用此系统

LibreOffice

在过去一年中,LibreOffice 团队做了大量的工作,让你在 Sun 被 Oracle 收购之后仍有一个放心的兼容 OpenOffice 的办公软件可使用。LibreOffice 不断的发布新版本,这不只是新功能的发布,还让 LibreOffice 越来越稳定和可靠。

OpenStack

云计算可算是2011最热的技术领域之一了,OpenStack 是由 Rackspace 和 NASA 共同开发的云计算平台,帮助服务商和企业内部实现类似于 Amazon EC2 和 S3 的云基础架构服务(Infrastructure as a Service, IaaS)。

OpenStack 包含两个主要模块:Nova 和 Swift,前者是 NASA 开发的虚拟服务器部署和业务计算模块;后者是 Rackspack 开发的分布式云存储模块,两者可以一起用,也可以分开单独用。OpenStack 是开源项目,除了有 Rackspace 和 NASA 的大力支持外,后面还有包括 Dell, Citrix, Cisco, Canonical 这些重量级公司的贡献和支持,发展速度非常快,有取代另一个业界领先开源云平台 Eucalyptus 的态势。

Nginx

Nginx 终于在今年发布了 1.0 版本,同时也完成了商业化过程。而且根据最新的 Netcraft 的统计报告,Nginx 的市场份额已经达到 8.85% ,已经俨然成为 Web 服务器中的老三,而且发展迅速。

有很多大网站在使用 Nginx 作为Web服务器,包括 Facebook、WordPress.com、DropBox 等等。

Nginx 的特点是:小而快。

jQuery

现在已经比较难找到一个不使用 jQuery 的 Web 开发人员了,已经成为最受欢迎的 JavaScript 了,而且 jQuery 有着其他 JS 难以超越的地方就是它有一个庞大的插件库,有大量的开发人员在为 jQuery 编写扩展和插件。

Node.js

这绝对是一个新项目,而且在短时间内得到了众多开发者的青睐,目前本站正在进行 Node.js 的高手问答,请看这里。

Node.js是一套用来编写高性能网络服务器的JavaScript工具包。

Puppet

有了 Puppet,您可以集中管理每一个重要方面,您的系统使用的是跨平台的规范语言,管理所有的单独的元素通常聚集在不同的文件,如用户, CRON作业,和主机一起显然离散元素,如包装,服务和文件。

Puppet的简单陈述规范语言的能力提供了强大的classing制定了主机之间的相似之处,同时使他们能够提供尽可能具体的必要的,它依赖的先决条件和对象之间的关系清楚和明确。

Linux

今年是 Linux 20周年,同时发布了首个 3.0 版本,而后版本一直飙升,大量的商业公司参与内核开发。20周年、3.0 版本,这两点让 Linux 当选 2011 年最重要的开源软件之一,应该没有什么质疑。

10 个项目已经结束,可是我不知道要不要算上 Android,很难说在 2011 年中 Android 不重要,但是有个问题是,不少人质疑 Android 的开源性质,质疑的人称 Android 是一个代码开放的项目,而不是一个开源项目。

前面我说过了,这 10 个软件可能会很片面,如果你觉得还有更重要(而不是使用人最多的)的软件,请大声说出来。

posted @ 2011-12-14 13:30 ItFans 阅读(167) | 评论 (0)编辑 收藏

2011年12月8日

分布式数据流分析框架(一)

概述

       重要:全文内容都是参照这个源码地址内容所写,因此两边对着看会更清晰明了:https://github.com/cenwenchu/beatles

 

这篇小记主要处于两方面考虑:首先,希望打破一提到海量数据分析,就只有hadoop基础上的一系列工具,更多的时候很多企业需要的是更轻量的设计 (办喜酒杀猪杀鸡未必都要用一把刀),因此将开放平台基础分析组件重构版本beatles的设计写出来,给出更多的思考空间。其次,也是希望推广一种思 想,所有的系统,框架设计简化(可扩展),小部件精致化,这样才能让很多项目能够整体灵活,细节给力。

 

建议

这篇小记一共分成4部分,概述,整体设计,局部设计,待续。如果你只想了解个背景,那么看完概述即可,如果对于流式分析的大框架设计感兴趣(看看省 略了分布式计算集群的什么?核心设计是怎么样的),请仔细看完整体设计。如果还对代码优化有兴趣,那请看局部设计(细到代码功能级别)。最后留下的待续, 将会增加后续的一些扩展,及同学看完后提出问题的解答(比较通用的一些问题,例如容灾啊,啥啥啥很多被认为很重要的东西)

 

背景

       07年底开始做开放平台,当时每天访问量在4kw左右,考虑到开放平台的数据透明化需求,开始考虑如何做统计分析,当时需求是一天出一次结果即可,因此自 己摸索搭建Hadoop迷你集群,开始了分析之路。09年公司调整加入淘宝开放平台,当时每天服务调用量2亿,数据分析要求比较散,从服务的系统数据统计 到业务趋势统计都有涉及,而且统计需求变化较多,因此开始筹备自己写简单的统计抽象模型来规避MapReduce类,提高适应变化的能力,同时出于简化系 统设计维护的要求,直接将每日分析数据放置到集中服务器上,每日拉取,切割,分析(统计分析引擎抽象完成)。2010年开放平台基础体系开始建立,对于服 务质量,应用行为,用户安全都提到了较高的要求上来,分析结果从原来的统计分析,扩展到了监控告警,每日分析转变为增量分析(频度1小时左右),简化的任 务调度模型抽象出来,同时服务调用量增涨到了9亿。2011年平台数据统计分析及时性要求更高,同时开始开放统计数据给外部开发者(系统可用性和效率要求 更高),整体框架和局部设计不断优化和改进,截至今年11月,单日最大服务调用量19亿,增量统计实时性要求在2分钟内(包含数据分析和数据产出,低峰期 1分钟,高峰期1分半),系统可用性要求高于99.6%,而投入的服务器比起动则几十台甚至上百上千的Hadoop系统来说,就是一个迷你集群(一台 Master实体机(16核,16g内存),12台虚拟机(虚后5核,8g内存,实际为4台实体机)),每天负责600g增量数据分析,产出1.5g数 据。

       很多时候很多开发人员会问到说在业务和代码结构优化冲突的时候怎么办,老板要结果,而程序员要的是看起来不恶心的代码,但很多时候,我们就是在摸索中做 事。上面描述的背景就好比开始买的是件夏天穿的短袖,然后天气不断变冷,开始给短袖加袖子,然后在身上贴补丁,但最后真的要到冬天的时候,应该怎么办,在 秋天和冬天之间,作为核心代码负责人,就应该保证系统可用性的情况下做好另一手准备(简单来说,时间不是别人给的,而是自己给的,天晴补漏,雨天不愁)。 因此年末的两周将2年中断断续续走过的路,重新整理了一遍,取名为beatles(甲壳虫),因为甲壳虫虽小,但聚集起来能够吃掉一大片叶子(业务系统各 种需要分析的数据),因此这个框架首先是个很小的内核(希望有更多扩展和参与者),其次不是一个从头开始的项目,而是一个两年多断断续续演进产品的积累。

       Beatles不是一个万能的技术产品,它出生和发展就为它适合的场景做了定义,因此使用和扩展的时候需要明确的了解是否合适,避免勿用,下面两个图会大志说一下它的特点和适用场景。




       上面这张图左边部分是Beatles可以局部牺牲的,右边部分是场景要求的。由于是对流式数据的增量分析,因此对于历史数据的全量挖掘无能为例(这部分完 全可以用Hadoop这种离线分析系统来做)。数据精确性要求所有数据在分析的任何一个环节都要做好保护(数据输入,分析过程,数据输出),而这种强完整 性要求势必会使得系统的效率和可用性降低(和右边实时性矛盾),因此会被放低一些要求(类似于计费结算等就直接一天走一次分析即可)。在左面所看重的三个 部分大致分布的场景为:监控告警(业务,系统,用户,平台透明化),业务即时分析对比(ABtest),系统灰度发布对比,用户实时统计展示(非金额等数 据一致性要求较高的内容展示)。

 

整体设计

       要满足上面所说的场景,实时流式数据分析需要做哪些功能?




任务调度抽象




       Beatles的任务调度十分简单,遵循两个原则:1.按需分配(Slave的多少及Slave自身执行任务的快慢自然促成的分配方式)2.任务粒度细 化,粗暴简单的任务重置(通过透明化监控任务可能出现的问题,避免集群陷入一个任务的纠结中)。优势:简单,高效,易扩展(Slave随时来,随时走)。 劣势:对于任务执行可控度较弱(通过任务细粒度和粗暴重置状态的方式来降低风险,增加的只是节点重复计算的浪费可能性)。



master处理流程

 

       可以看到Master整体就两部分工作,对内部任务的管理维护,对外部slave请求的处理(请求获取任务,返回处理后的结果(Slave也可以不返回结 果,根据Job定义来判断,防止Master变重))。Master单点并不可怕,只要遵循两个原则:现场可快速恢复,分析流程可追赶。因此做到 Master所有状态定期外移和实时监控,即可满足这种简单的Master可用性需求。




slave处理流程

       Slave更为单纯,整个生命周期就是获取任务,分析任务,返回任务结果的一个环,内置一个分析引擎和交互组件,根据任务的定义来无差别化的处理各种分析 工作(Job定义了数据的输入来源,输出目标地址,分析规则)。Slave的设计主要考虑如何做到无业务规则侵入和数据来源限制,满足了这些需求的情况下 才能够实现节点处理无差别性,各种分析任务可以跑在一个集群上(实现计算节点可复用)。

 

任务抽象

 

       任务抽象设计比较简单,主要结合任务调度设计,实现计算节点的无差别化。




       Job是一类分析的定义(例如对gc的日志分析,对服务调用日志分析可以定义为两个Job),Job中的Task表示对于这一类数据分析再次拆分任务,来 分解海量数据处理,Task中继承了Job中的输入和输出,支持多种模式的数据来源和数据输出。Rule就是分析统计模型抽象部分主要分 成:Alias(对于分析数据的列别名定义),Entry的MapReduce的定义,Report是Entry整合成用户可接受的Report的定义。

 

统计模型抽象

统计模型抽象主要分为两部分:统计模型抽象和统计流程抽象。统计模型抽象就是将MapReduce的Key-Value统计,转化成为传统意义上的报表结构。

 

       分析的输入:(弱业务含义的大表)

       c1,c2,c3,c4,c5,c6

       c1,c2,c3,c4

       c1,c2,c3,c4,c5,c6,c7

       ……

 

 

       MapReduce可以处理的:

      


      

       如下图,传统报表的一行可以看作是多个相同key但不同统计字段组合的结果。



      

       例如:输入的数据结构如下:

       服务名称,服务类型,服务上行数据流量,服务处理结果(错误码),服务耗时

           真实日志如下:(分隔符可在分析时指定,这里用逗号作演示)

           taobao.user.get,read,100,0,20

           taobao.product.add,write,1000,0,50

           ……

 

       那么定制如下MapReduce组合:

       Key:服务名称,Value:服务上行数据流量总和。

       Key:服务名称,Value:服务耗时总和。

       Key:服务名称,Value:服务平均耗时。

   Key:服务名称,Value:服务最大耗时。

       Key:服务名称,Value:服务最小耗时。

 

       那么将这些MapReduce处理后的Key-value在组合一次就可以得到:

       Key:服务名称,Value:服务上行数据流量总和,服务耗时总和,服务平均耗时,服务最大耗时,服务最小耗时。

       简单来说其实就是类似于SQL中的Groupby的方式,将一堆<key,value> groupby  key。

 

分析流程抽象如下:




分析流程抽象

流程中可以扩展的在第三步和第四步,第三步影响了Key的生成(当简单的列组合成字符串无法满足生成key的情况下可扩展),第四步影响value 的生成。(当map的value生成以及Reduce无法满足需求的情况下可扩展),要使用min,max…以外的reduce,可以直接在 ReduceClass中作处理,然后使用plain输出实现。

这种流程比传统的MapReduce的写法好处在于可以对输入只读取一次(海量的日志文件为了多种条件分析,反复读取本身就是最大的损耗)。可以看 到在文件IO操作上,不会随着分析模型配置的增多而增长,中间数据也不会随着报表组合的不同而过快膨胀(只要报表复用Entry足够多)。

 

整体组件和流程设计




角色定义

       Beatles内部业务组件如上图。

Master包含两个子组件,JobManager用于管理任务,MasterConnector用于与Slave通信。

Slave包含三个组件,SlaveConnector用于与服务端通信,AnalysisEngine用于数据分 析,JobResultMerger可选,用于在客户端分担服务端汇总结果的压力,同时让Slave可以多线程并行执行任务。(当然单机可以跑多个 Slave的实例)。

Job&Task已经提到过用于任务抽象,支持Slave的Analysis Engine的分析无差别性。

Input&output用于扩展整个框架的各种数据来源,例如job构建的来源,job的输入和输出等。


 


整体流程

 

1.    Master利用jobManager通过JobBuilder来构建服务端的任务集合。

2.    Slave向Master发起要任务的请求。

3.    通过Master和Slave的Connector来做交互。

4.    MasterConnector向MasterNode内部的事件处理模块提交事件。

5.    JobManager检查内部任务状态后返回未完成且符合条件的任务返回给Slave。

6.    SlaveNode收到任务后调用内部分析引擎并行执行任务分析。

7.    分析引擎获得任务的数据来源,开始分析数据。

8.    如果是多个任务并行执行,合并同一个Job的多个Task的结果。

9.    导出分析后的结果

10. 如果是需要汇总到Master的话,利用SlaveConnector返回给Master。

11. MasterConnector获得返回的分析结果数据。

12. MasterNode类似走事件流程,然后调度到合并组件合并结果。

13. 当Job任务全部完成就调用JobExporter导出数据。

 

代码结构体系:sourcecode:(https://github.com/cenwenchu/beatles


 


整体包结构

        整个项目内容不多,根据包名的前缀可以发现主要分成两块:node,Statistics。前者是任务调度及任务抽象,后者是统计分析模型抽象。

       Config中是多个角色各自的config定义,同时这些config会在一个实体里传播,例如MasterConfig就在MasterNode中传 播到jobManager和MasterConnector组件中,SlaveConfig就在SlaveNode传播到分析引擎组件和 SlaveConnector中。

       Node中的结构如下:

       Component:对Node的各个组件接口的实现。

       Connect:Master与Slave交互的接口定义和实现。

       Io:对于Job的输入输出来源的接口定义和默认几个实现。

       Event:定义了Master和Slave这样的Node中需要处理的事件。

       Job:任务抽象定义。

       Map,Reduce:支持当分析引擎无法满足的Map,Reduce的情况。(足够通用的情况下可以被抽象到主框架中)

       Operation:定义了Node结构中需要异步处理事件。(因为当前Node的Event是单线程处理的,因此事件执行如果比较消耗,则需要异步后台执行,或者并行执行)

       Util包是一些工具类和定义类。

       Staitistics是分析引擎接口和实现,其中Data中是分析规则的抽象。

 

      至此为止,整体的结构设计就如上所述了,整体上结构比较简单直接,可扩展性为了支持分析规则扩展,不同计算场景扩展,效率和可靠性扩展。下一个部分将会细化到具体的模块代码设计上来谈优化和代码技巧。

posted @ 2011-12-08 15:22 ItFans 阅读(357) | 评论 (0)编辑 收藏

2011年11月18日

信息检索资源大集合

http://nlp.stanford.edu/IR-book/information-retrieval.html

posted @ 2011-11-18 11:50 ItFans 阅读(162) | 评论 (0)编辑 收藏

地图检索

 看了篇地图检索的文章,挺不错的,先收藏下   http://blogread.cn/it/article.php?id=4598

posted @ 2011-11-18 11:40 ItFans 阅读(162) | 评论 (0)编辑 收藏

2011年6月13日

深入浅出理解索引结构 (转)

     摘要: (一)深入浅出理解索引结构         实际上,您可以把索引理解为一种特殊的目录。微软的SQL SERVER提供了两种索引:聚集索引(clustered index,也称聚类索引、簇集索引)和非聚集索引(nonclustered index,也称非聚类索引、非簇集索引)。下面,我们举例来说明一下聚集索引和非聚集索引的区别:&...  阅读全文

posted @ 2011-06-13 17:52 ItFans 阅读(148) | 评论 (0)编辑 收藏

2011年6月10日

新浪微博技术架构分析

中国首届微博开发者大会在北京举行,这是国内微博行业的首场技术盛宴。作为国内微博市场的绝对领军者,新浪微博将在此次大会上公布一系列针对开发者的扶持政策,以期与第三方开发者联手推动微博行业的整体发展。图为微博平台首席架构师杨卫华演讲。

以下为演讲实录:

大家下午好,在座的大部分都是技术开发者,技术开发者往往对微博这个产品非常关心。最晚的一次,是12点多收到一个邮件说想了解一下微博底层是怎么构架 的。很多技术人员对微博的构架非常感兴趣,就是一个明星他有300万粉丝,这个技术怎么来实现?今天在这里跟大家分享一下微博的底层机构,让大家对微博的 底层技术有更好的了解。另外不管是做客户端、1.0、2.0、论坛、博客都要考虑架构的问题,架构实际上是有一些共性的。今天我通过讲解微博里面的一些架 构,分析一下架构里面哪些共性大家可以参考。

首先给大家介绍一下微博架构发展的历程。新浪微博在短短一年时间内从零发展到五千万用户,我们的基层架构也发展了几个版本。第一版就是是非常快的,我们可 以非常快的实现我们的模块。我们看一下技术特点,微博这个产品从架构上来分析,它需要解决的是发表和订阅的问题。我们第一版采用的是推的消息模式,假如说 我们一个明星用户他有10万个粉丝,那就是说用户发表一条微博的时候,我们把这个微博消息攒成10万份,这样就是很简单了,第一版的架构实际上就是这两行 字。第一版本的技术细节,典型的LAMP架构,是使用Myisam搜索引擎,它的优点就是速度非常快。另外一个是MPSS,就是多个端口可以布置在服务器上。为 什么使用MPSS?假如说我们做一个互联网应用,这个应用里面有三个单元,我们可以由三种部署方式。我们可以把三个单元部署在三台服务器上,另外一种部署 模式就是这三个单元部署在每个服务器上都有。这个解决了两个问题,一个是负载均衡,因为每一个单元都有多个结点处理,另外一个是可以防止单点故障。如果我 们按照模式一来做的话,任何一个结点有故障就会影响我们系统服务,如果模式二的话,任何一个结点发生故障我们的整体都不会受到影响的。

我们微博第一版上线之后,用户非常喜欢这个产品,用户数增长非常迅速。我们技术上碰到几个问题。第一个问题是发表会出现延迟现象,尤其是明星用户他的粉丝 多。另外系统处理明星用户发表时候的延迟,可能会影响到其他的用户,因为其他的用户同一时间发表的话,也会受到这个系统的影响。我们就考虑这个系统怎么改 进。首先是推模式,这肯定是延迟的首要原因,我们要把这个问题解决掉。其次我们的用户越来越多,这个数据库表从一百万到一亿,数据规模不一样处理方式是有差别的。我们第一版单库单表的模式,当用户数量增多的时候,它不能满足就需要进行拆分。第二个是锁表的问题,我们考虑的是更改引擎。另外一个是发表过慢,我们考虑的是异步模式。

第二版我们进行了模块化,我们首先做了一个层,做了拆分,最右边的发表做了异步模式。第二个服务层,我们把微博基础的单元设计成服务层一个一个模块,最大是对推模式进行了改进。首先看一下投递模式的优化,首先我们要思考推模式,如果我们做一下改进把用户分成有效和无效的用户。 我们一个用户比如说有一百个粉丝,我发一条微博的时候不需要推给一百个粉丝,因为可能有50个粉丝不会马上来看,这样同步推送给他们,相当于做无用功。我 们把用户分成有效和无效之后,我们把他们做一下区分,比如说当天登陆过的人我们分成有效用户的话,只需要发送给当天登陆过的粉丝,这样压力马上就减轻了, 另外投递的延迟也减小了。

我们再看数据的拆分,数据拆分有很多方式,很多互联网产品最常用的方法,比如说如可以按照用户的UID来拆分。但是微博用户的一个特点就是说大家访问的都是最近的服务器,所以我们考虑微博的数据我们按照时间拆分,比如说一个月发一张表,这样就解决了我们不同时间的惟度可以有不同的拆分方式。第二个考虑就是要把内容和索引分开存放。假如说一条微博发表的地址是索引数据,内容是内容数据。假如说我们分开的话,内容就简单的变成了一种key-value的方式,key- value是最容易扩展的一种数据。比如说一个用户发表了一千条微博,这一千条微博我们接口前端要分页放,比如说用户需要访问第五页,那我们需要迅速定位 到这个记录。假如说我们把这个索引拆分成一个月一张表,我们记录上很难判断第五页在哪张表里,我们需要索引所有的表。如果这个地方不能拆分,那我们系统上 就会有一个非常大的瓶颈。最后我们想了一个方法,就是说索引上做了一个二次索引,改变我们还是按照时间拆分,但是我们把每个月记录的偏移记下来,就是一个 月这个用户发表了多少条,ID是哪里,就是按照这些数据迅速把记录找出来。

异步处理,发表是一个非常繁重的操作,它要入库、统计索引、 进入后台,如果我们要把所有的索引都做完用户需要前端等待很长的时间,如果有一个环节失败的话,用户得到的提示是发表失败,但是入库已经成功。所以我们做 了一个异步操作,就是发表成功我们就提示成功,然后我们在后台慢慢的消息队列慢慢的做完。另外新浪发表了一个很重要的产品叫做MemcacheQ,我们去 年做了一个对大规模部署非常有利的指令,就是stats queue,适合大规模运维。

第二版我们做了这些改进之后,微博的用户和访问量并没有停止,还有很多新的问题出现。比如说系统问题,单点故障导致的雪崩,第二个是访问速度问题因为国内 网络环境复杂,会有用户反映说在不同地区访问图片、js这些速度会有问题。另外一个是数据压力以及峰值,MySql复制延迟、慢查询,另外就是热门事件, 比如说世界杯,可能会导致用户每秒发表的内容达到几百条。我们考虑如何改进,首先系统方面循序任意模块失败。另外静态内容,第一步我们用CDN来加速,另 外数据的压力以及峰值,我们需要将数据、功能、部署尽可能的拆分,然后提前进行容量规划。

另一方面我们还有平台化的需求,去年11月我们就说要做开放平台,开放平台的需求是有差异的,Web系统它有用户行为才有请求,但是API系统特别是客户端的应用,只要用户一开机就会有请求,直到他关闭电脑这种请求一直会不间断的过来,另外用户行为很难预测。

系统规模在持续的增大,另外也有平台化的需求,我们新架构应该怎么做才能满足这些需要?我们看一下同行,比如说Google怎么样考虑这个问题的?Google首席科学家讲过一句话,就是一个大的复杂的系统,应该要分解成很多小的服务。比如说我们在Google.com执行一个搜索查询的话,实际上这个操作会调动内部一百多个服务。因此,我们第三版的考虑就是先有服务才有接口最后才有应用,我们才能把这个系统做大。

现在我们看一下第三版,首先我们把底层的东西分成基础服务,基础服务里面比如说分布式的存储,还有分层,我们做了一些去中心化、自动化的操作。在基础服务 之上有平台服务,我们把微博常用的应用做成各种小的服务。然后我们还有应用服务,这个是专门考虑平台各种应用的需求。最上面我们有API,API就是新浪 微博各种第三方应用都在上面跑。

平台服务和应用服务是分开的,这样实现了模块隔离,即使应用服务访问量过大的话,平台服务不会首先影响。另外我们把微博的引擎进行了改进,实现了一个分层关系。用户的关注关系,我们改成一个多惟度的索引结构, 性能极大的提高。第四个层面就是计数器的改进,新版我们改成了基于偏移的思路,就是一个用户他原来读的一个ID比如说是10000,系统最系的ID是 10002的话,我们和清楚他有两条未读。原来的版本是采用绝对技术的,这个用户有几条未读都是用一个存储结构的话,就容易产生一致性的问题,采用这种偏 移的技术基本上不会出错。

另外基础服务DB冷热分离多维度拆分,在微博里面我们是按照时间拆分的,但是一个大型的系统里面有很多业务需要有不同的考虑。比如说私信这个就不能按照时 间来拆分,这个按照UID来拆分可能更简单。然后我们突出存储还做了一个去中心化,就是用户上传图片的速度会极大的提高,另外查看其他用户的图片速度也会 极大的提高。另外是动态内容支持多IDC同时更新,这个是在国内比较新颖的。

下面给大家介绍一下新浪微博怎么样打造一个高性能架构。到目前为止有五千万用户使用新浪微博,最高发表3000条以上每秒,然后一个明星用户发表的话,会被几百万用户同时读到。这些问题的本质是我们架构需要考虑高访问量、海量数据的情况下三个问题。易于扩展、低延迟、高可用和异地分布。 我们每天有数十亿次外部网页以及API接口的需求,我们知道微博的特点是用户请求是无法cache的。因此面对这个需求我们怎么样扩展?几点思路。第一我 们的模块设计上要去状态,我们任意一个单元可以支持任意节点。另外是去中心化,避免单点及瓶颈。另外是可线性扩展。最后一个是减少模块。

我们要做一个高性能的系统,要具备一个低延迟、高实时性,微博要做到高实时性这是核心的价值,实时性的核心就是让数据离CPU最近,避免磁盘的 IO。我们看淘宝核心系统专家余锋说过的一句话“CPU访问L1就像从书桌拿一本书,L2是从书架拿一本书,L3是从客厅桌子上拿一本书,访问主存就像骑车去社区图书馆拿一书”。 我们微博如果要做到非常实时的话,我们就需要把数据尽量离CPU节点最近。所以我们看一下cache设计里面怎么达到这个目标。首先INBOX,这个数据 我们需要放再一个最快的地方,因为用户随时访问。OutBOX里面的最近发表就是L1cache,还有一个是中期的,这个因为访问少一点,它可以被踢。最 后一部分内容体有三部分。L0是本地的,我们需要把一些经常访问的,比如说明星发表微博的内容体本地化,因为它被访问的概率非常大。然后L1里面存放着最 近发表的,还有一个是中期的。我们通常用L2就可以了,L1我们可以理解成它就是一个存储。

一个好的架构还需要举行高可用性。我们看一下业界的指标,S3是99.9%,EC2是99.5%,我们另外一个同行Face book在这方面它是没有承诺的,就是接口可用写。微博平台目前承诺的是99.95%,就是说一天365天故障率应该小于9的小时。这个怎么达到?第一我 们要做容量规划,地个是要做好监控以及入口的管理,就是说有些服务如果访问量过了的话,我们要有一个开关可以拦住他。我们通过这个图表可以清楚的看到,比 如说我们要做L1的cache,我们剩余空间有多少,比如说80%,就说明这个数据有可能会丢失,有可能会对我们的系统造成影响。

另外一个层面就是接口监控,我们目前有Google维度的接口监控,包括访问错误失败率。然后要做架构,给大家一个很重要的经验分享,就是说监控的指标尽量量化。比如说他延迟30秒是小问题,如果是延迟10分钟我们就要立即采取措施了,就是所有可以量化的指标都要量化。

然后我们看监控怎么样更好的做?我们看亚马逊的VP说过的一句话,就是说监控系统确实特别好,可以立即告诉我们哪里有故障,但是有20%的概率我们人是会出错的。所以我们一个大型系统就应该要为自动化设计,就是说尽可能的将一些运作自动化。比如说发布安装、服务、启用、停止。 我们再看另外一句,Google的工程师是怎么做的。他是这么做的,比如说第一周是处理线上的业务,这一周他处理了很多事情,处理了很多系统的情况,剩下 的系统问题是不需要他做的,他只要把这一周碰到的情况用程序的方法来解决,下次再碰到这种情况很简单的一个按钮就可以处理了。我们目前也在向自动化这方面 努力,就是我们的工具在持续增加。

另外一个异地分布,在国内网络环境下,比如说IDC灾难,机房检修甚至是机房掉电,我们也碰到过中国最好的机房也会掉电,所以要每个服务单元都能支持多机 房部署。另外做多机房部署有一个好处,就是用户的访问速度会提高。多IDC分布静态内容就不说了,基本上大的互联网公司都会做,它非常成熟基本上没有什么 问题,比如说图片等等的静态内容。动态内容的CDN分布是业内的难点,国内很少有公司能够做到非常成熟的多机房动态内容发布的成熟方案,它的核心就是分布 式存储。一款理想的分布式存储产品它有哪些需求呢?首先它要支持海量规模、可扩展、高性能、低延迟、高可用。第二个是需要多机房分布,能够满足国内负责的网络环境,还要具备异地容灾能力。第三个就是要调用简单,具备丰富数据库特性。因此分布式存储需要解决一个多对多的数据复制。

如果要做复制无非是三种策略,第一个是Master/Slave,但是它也两个缺点,第一个是Master是中心化的,如果Master在北京那广州访问 就非常慢。第二个缺点是有单点风险的,比如说Master在北京,能立即迁到广州吗?这样时间窗口就丢失了,而且需要人工的干预,而且日常广州的用户访问 北京的Master是有很大问题的,所以一般来说要做的非常优秀是不会考虑第一种方案的。第二种就是Multi-Master方案,它需要应用避免冲突, 就是我们不能多处改变。这个对于微博来说不会特别难,我们的用户通常只会再一个地方发表微博,很难既在广州又在北京发表或者是修改自己的资料,这样的话我 们应用上就可以避免这种情况。第三个就是Paxos就是可以达到强一致写,就是一条数据如果成功肯定是多个机房都成功了,这个也显而易见就是延迟性非常 大。因此总结一下Multi-Master是最成熟的策略,但是它现在没有成熟的产品,因为确实没有。

我们再来看微博的方案,所以我们自己实现了一个多机房同步的方案。就是我们前端应用将数据写到数据库,再通过一个消息代理,相当于通过我们自己开发的一个技术,将数据广播到多个机房。这个不但可以做到两个机房,而且可以做到三个、四个。具体的方式就是通过消息广播方式将数据多点分布,就是说我们的数据提交给一个代理,这个代理帮我们把这些数据同步到多个机房,那我们应用不需要关心这个数据是怎么样同步过去的。

用这种消息代理方式有什么好处呢?可以看一下Yahoo是怎么来做的?第一个是数据提供之后没有写到db之后是不会消失的,我只要把数据提交成功就可以 了,不需要关心数据怎么到达机房。第二个特点YMB是一款消息代理的产品,但是它唯一神奇的地方是为广域网设计的,它可以把多机房应用归到内部,我们应用 不需要关注这个问题。这个原理跟我们目前自己开发的技术相似。

然后我们再看一下目前即将推出的微博平台的新架构。我们知道API大部分的请求都为了获取最新的数据。API请求有一个特点,它大目前调用都是空返回的, 比如说一款手机的客户端每隔一分钟它都要调用服务器一下,就是有没有新数据,大目前的调用都是空返回,就是说不管服务器有没有数据都要调用一次。这次询问 到下一次询问中间,如果有新的数据来了,你是不会马上知道的。因此我们想API能不能改用推的方式,就是客户端不需要持续的调用,如果有新数据就会推过 去。技术特点,显而易见低延迟,就是从发表到接受1秒内完成,实际上可能用不了1秒。然后服务端的连接就是高并发长连接服务,就是多点都连接在我们的服务 器上,这个比传统的API要大很多。

我们看一下推送架构怎么从架构底层做到实时性的。从左上角的一条微博在我们系统发布之后,我们把它放在一个消息队列里面,然后会有一个消息队列的处理程序把它拿过来,处理以后放到db里面。 假如说我们不做持久化,因为我们推送数据也不能丢失,我们就要写一个很复杂的程序,将S数据异步去存,这样就会非常复杂,而且系统也会有不稳定的因素。从 另外一个角度来说,我们做持久化也是做过测试的。我们推送整个流程可以做到100毫秒和200毫秒之间,就是说我们在这个时间能把数据推送出去。

我们再看一下内部细节,就是我们收到数据之后首先要经过最上面RECEIVER。然后推到我们的引擎里面,这个引擎会做两个事情,首先会把用户的关系拿过 来,然后按照用户关系马上推送给他相应的粉丝。所以我们调研方已经在那儿等待了,我们需要有一个唤醒操作,就是说在接口这儿把它唤醒,然后把它发送过去。 最后是一个高并发的长连服务器,就是一台服务器支持10万以上的并发连接。最右边中间有一个圆圈叫做Stream Buffer,我们需要Stream Buffer是要保存用户最近的数据。因为用户可能会有断线的,比如说他发送数据的时候断线半分钟,我们需要把这半分钟补给他。这就是我们的推送架构。

下面介绍一下平台安全部分。由于我们的接口是完全开放的,所以我们要防范很多恶意行为,有很多人担心我们接口是开放的,是不是有人通过这个接口发垃圾广 告,或者是刷粉丝,我们技术架构怎么来防范这一点呢?这是我们的安全架构,做了三个层面的事情。总上面是我们有一个实时处理,比如说根据频度、内容的相似 性来进行判断,判断你发的是不是广告或者是垃圾内容。中间这个是一个处理器,我们会根据一些行为进行判断,比如说如果我们只是实时拦截的话,有些行为很难 防止,我们做了个离线纠正的模块,比如说他潜伏的几个月开始发广告了,我们可以事后把这些人清除掉,以保证我们平台的健康。最后是通过监控的维度来保证内 容的安全。目前内容安全的架构大概是51的体系,就是说我们的实时拦截可以做到50%的防止,离线分析大概可以做到40%的防止。

微博平台需要为用户提供安全及良好的体验应用,以及为开发者营造一个公平的环境,所以我们的接口需要清晰安全的规则。从一个APP调用我们的接口,需要几 个阶层,需要划分不同的业务模块。第二个是安全层。第三个是权限层。这是我们平台安全的两个维度,一个接口安全,一个是内容安全。

我今天讲的是架构方面的问题,在座大部分是开发者,可能大家都在处理不同的架构问题,架构很多地方是相通的。我们需要做一个软件系统需要解决的本质问题是 什么?微博第一版解决发布规模问题,第二版是解决数据规模的问题,第三版是解决服务化的问题。将复杂的问题简单化之后,我们才可以设计出一个容易扩展的大 规模架构。我今天介绍就这么多,我们微博实际上是很需要各方面的技术人员,大家对我们的架构如果感兴趣的话、对我们的系统感兴趣的话,也希望各方面的人员 参与我们微博的团队,随时可以给我微博上发私信。

posted @ 2011-06-10 15:07 ItFans 阅读(557) | 评论 (0)编辑 收藏

仅列出标题  

导航

统计

常用链接

留言簿

随笔档案

搜索

最新评论

阅读排行榜

评论排行榜