放翁(文初)的一亩三分地

  BlogJava :: 首页 :: 新随笔 :: 联系 :: 聚合  :: 管理 ::
  210 随笔 :: 1 文章 :: 320 评论 :: 0 Trackbacks

2009年5月7日 #

     摘要: Beatles小记(三)-分布式数据流分析中Master的横向扩展  阅读全文
posted @ 2012-01-17 13:21 岑文初 阅读(5146) | 评论 (2)编辑 收藏

     摘要: Beatles小记-分布式数据流分析框架(二),局部代码设计和实现分享  阅读全文
posted @ 2011-12-09 16:44 岑文初 阅读(4715) | 评论 (4)编辑 收藏

     摘要: 分布式流式数据分析设计和代码分析  阅读全文
posted @ 2011-12-07 16:46 岑文初 阅读(9559) | 评论 (7)编辑 收藏

     摘要: java优化设计实现细节分享  阅读全文
posted @ 2011-09-23 14:03 岑文初 阅读(5035) | 评论 (1)编辑 收藏

     摘要: 两个开放平台内部组件开放   阅读全文
posted @ 2011-07-12 11:54 岑文初 阅读(3750) | 评论 (2)编辑 收藏

     摘要: 讨论一下并发消息下行的设计方案和实现  阅读全文
posted @ 2011-06-23 12:16 岑文初 阅读(4504) | 评论 (0)编辑 收藏

     摘要: Jetty内部透明简单实现  阅读全文
posted @ 2011-06-22 17:03 岑文初 阅读(3990) | 评论 (0)编辑 收藏

     摘要: 慢连接&LazyParser  阅读全文
posted @ 2011-06-20 23:47 岑文初 阅读(5324) | 评论 (0)编辑 收藏

     摘要: PipeComet测试  阅读全文
posted @ 2011-06-08 23:58 岑文初 阅读(6913) | 评论 (0)编辑 收藏

     摘要: 一段代码,几句话  阅读全文
posted @ 2011-04-13 23:11 岑文初 阅读(4569) | 评论 (1)编辑 收藏

     摘要: 开放平台的技术问题  阅读全文
posted @ 2011-03-31 00:43 岑文初 阅读(4812) | 评论 (4)编辑 收藏

     摘要: Web容器测试模型选择  阅读全文
posted @ 2011-03-31 00:40 岑文初 阅读(3372) | 评论 (0)编辑 收藏

     摘要: 十年  阅读全文
posted @ 2011-03-08 23:46 岑文初 阅读(2902) | 评论 (6)编辑 收藏

     摘要: 模拟登录看前端门外汉学习  阅读全文
posted @ 2011-03-03 23:26 岑文初 阅读(5529) | 评论 (10)编辑 收藏

     摘要: 逻辑划分线程池  阅读全文
posted @ 2011-03-01 00:32 岑文初 阅读(5148) | 评论 (4)编辑 收藏

     摘要: OAuth2的一些改变  阅读全文
posted @ 2011-02-28 23:01 岑文初 阅读(3402) | 评论 (0)编辑 收藏

     摘要: “淘宝的”开放平台  阅读全文
posted @ 2011-02-23 23:39 岑文初 阅读(5073) | 评论 (4)编辑 收藏

     摘要: 交流分享  阅读全文
posted @ 2011-02-20 23:58 岑文初 阅读(4960) | 评论 (7)编辑 收藏

     摘要: ask & answer  阅读全文
posted @ 2011-01-12 23:22 岑文初 阅读(3861) | 评论 (0)编辑 收藏

     摘要: 耗内存应用优化实际案例  阅读全文
posted @ 2010-12-22 23:40 岑文初 阅读(4295) | 评论 (0)编辑 收藏

     摘要: Local Cache的小TIP   阅读全文
posted @ 2010-12-14 22:34 岑文初 阅读(3399) | 评论 (4)编辑 收藏

     摘要: SD开放平台技术分享  阅读全文
posted @ 2010-12-13 20:35 岑文初 阅读(3190) | 评论 (2)编辑 收藏

     摘要: Facebook优化分享后记  阅读全文
posted @ 2010-12-12 19:43 岑文初 阅读(3439) | 评论 (4)编辑 收藏

     摘要: 这篇文章将会从问题,技术背景,设计实现,代码范例这些角度去谈基于管道化和事件驱动模型的Web请求处理。建议从头看,能够从概念上更多的去理解和碰撞,其中的一些描述和例子也许不是很恰当,也希望得到更多的反馈。  阅读全文
posted @ 2010-11-25 14:44 岑文初 阅读(4100) | 评论 (7)编辑 收藏

     摘要: 这篇文章将会从问题,技术背景,设计实现,代码范例这些角度去谈基于管道化和事件驱动模型的Web请求处理。建议从头看,能够从概念上更多的去理解和碰撞,其中的一些描述和例子也许不是很恰当,也希望得到更多的反馈。  阅读全文
posted @ 2010-11-24 01:26 岑文初 阅读(3358) | 评论 (4)编辑 收藏

     摘要: 图片是大纲,先抛出来,后续会有更详细的文章分享  阅读全文
posted @ 2010-11-17 01:00 岑文初 阅读(2639) | 评论 (2)编辑 收藏

     摘要: 如果关注开放平台或者关注平台的一些内容,这篇文章应该有点内容可看  阅读全文
posted @ 2010-10-11 23:42 岑文初 阅读(2913) | 评论 (1)编辑 收藏

     摘要: 美国JavaOne之行内容,需要看直播请关注微博  阅读全文
posted @ 2010-09-22 15:55 岑文初 阅读(1666) | 评论 (1)编辑 收藏

     摘要: 代码背后的点滴,通过一些设计理念来分享技术的积累  阅读全文
posted @ 2010-09-09 02:05 岑文初 阅读(4288) | 评论 (8)编辑 收藏

     摘要: 面试有感  阅读全文
posted @ 2010-09-02 11:31 岑文初 阅读(2393) | 评论 (4)编辑 收藏

     摘要: 对同学性能优化总结的一点回复  阅读全文
posted @ 2010-08-23 16:58 岑文初 阅读(2280) | 评论 (0)编辑 收藏

     摘要: ppt分享  阅读全文
posted @ 2010-08-10 07:48 岑文初 阅读(3629) | 评论 (2)编辑 收藏

     摘要: 在概念篇介绍完以后,开始实际的对TOP开始做技术改造。(这篇东西更像是对短期工作的总结和汇报,写的不是很详实,后续会有一个ppt来深化异步化的一些思想)下面将第一阶段的工作做个总结,第一阶段主要做了以下几个方面的事情  阅读全文
posted @ 2010-08-06 00:38 岑文初 阅读(4206) | 评论 (0)编辑 收藏

     摘要: 淘宝一年陈  阅读全文
posted @ 2010-07-24 00:34 岑文初 阅读(2829) | 评论 (7)编辑 收藏

     摘要: Web服务的重放攻击的一点想法  阅读全文
posted @ 2010-07-07 00:40 岑文初 阅读(3178) | 评论 (0)编辑 收藏

     摘要: Web服务请求异步化介绍  阅读全文
posted @ 2010-06-30 08:41 岑文初 阅读(5224) | 评论 (4)编辑 收藏

     摘要: Web服务请求异步化测试  阅读全文
posted @ 2010-06-13 14:35 岑文初 阅读(4413) | 评论 (9)编辑 收藏

     摘要: 访问TOP链接超时和重置问题  阅读全文
posted @ 2010-06-09 13:34 岑文初 阅读(1706) | 评论 (1)编辑 收藏

     摘要: 对TOP高并发的一点回答  阅读全文
posted @ 2010-06-07 21:22 岑文初 阅读(1754) | 评论 (0)编辑 收藏

     摘要: TOP的价值所在  阅读全文
posted @ 2010-06-01 08:49 岑文初 阅读(3523) | 评论 (5)编辑 收藏

     摘要: 开放平台两三点感悟(下)  阅读全文
posted @ 2010-06-01 02:53 岑文初 阅读(3280) | 评论 (4)编辑 收藏

     摘要: 开放平台两三点感悟  阅读全文
posted @ 2010-05-28 02:29 岑文初 阅读(4360) | 评论 (6)编辑 收藏

http://t.sina.com.cn/fangweng

posted @ 2010-05-24 21:54 岑文初 阅读(1281) | 评论 (0)编辑 收藏

     摘要: ModJK与tomcat消息传递出现的串消息问题  阅读全文
posted @ 2010-05-11 20:00 岑文初 阅读(2762) | 评论 (0)编辑 收藏

     摘要: 异步模式下的Web请求(技术介绍篇)  阅读全文
posted @ 2010-04-20 08:50 岑文初 阅读(4230) | 评论 (1)编辑 收藏

     摘要: Q1技术点滴  阅读全文
posted @ 2010-04-02 02:26 岑文初 阅读(3112) | 评论 (5)编辑 收藏

     摘要: 普通程序员的2009  阅读全文
posted @ 2010-01-29 01:34 岑文初 阅读(2144) | 评论 (4)编辑 收藏

 

优化杂谈

Author :放翁

Bloghttp://blog.csdn.net/cenwenchu79/

         当应用遇到规模化问题的时候,就是考虑性能优化的时候了。今天同事和我聊起了NIO在客户端的使用与BIO有什么优势,也勾起了我前一阵子和其他同学交流优化的一些想法,纯粹个人的一点想法。

CPU利用率和Load

         在过去做压力测试的时候,我们经常会关注两个指标,CPULoad。有同学觉得CPU利用率上去了Load肯定也上去了,Load上去了CPU利用率同样会上去。但是在一些需要优化的场景下,常常会看到Load很高,CPU利用率却可能比较低(多核更是可能出现分配不均的情况)。Load其实就是等待处理的任务队列,当你的应用在等待同步消息返回处理的同时,CPU还是会将时间切片分配给这些线程,而真正需要CPU的线程,却不得不在到了时间片以后暂时放弃工作被挂起。因此在程序设计的时候就要考虑如何利用好CPU的这个资源,如何均匀的将压力分摊到各个CPU上(有时候就一个线程在不断循环,导致单个CPU负荷很高)。

NIO在客户端的使用

         Http消息设置keepalive和采用NIO的方式复用信道、BIO结合连接池的方式,最基本的目的就是降低建立TCP产生握手的成本,最大限度的复用已有的资源,但是否NIO就只有复用信道这点呢?

         NIOBIO在数据传输和处理的模式上有不同,NIO采用的是BufferPacket+Channel的模式,这其实和操作系统本身的传输模式很类似,而BIOStream的模式是Java自己独特的模式。在采用NIO的这种数据传输模式以后,可以充分利用操作系统本身对传输的优化,因此这是一方面好处。另一方面异步和事件机制的使用,可以降低对于昂贵的资源申请,在高并发下提高处理能力。

NIO客户端的编程模型最大特点:依赖反置,松耦合带来性能提升。在请求流程协议中支持“票根”,也就是我们说的回执。例如,你今天面试完了,不需要你在阿里巴巴前台等着结果,直接留个电话,有消息就会直接通知,电话就是通知结果和服务请求者的关联手段。(此时阿里巴巴前台和会议室就会有足够的空间给其他人来面试,这就是资源)

         服务端使用NIO就不多说了,这里主要说一下在客户端的使用场景。两者是否真的有很大的差别,是否NIO有绝对的优势,其实还是和场景有关。简单说来就一个判断标准:应用对于通道的利用率是否够高。下面列了4种场景:

1. 一次请求数据量很少,服务处理速度很快。

2. 一次请求数据量很多,服务处理速度很快。

3. 一次请求数据量很少,服务处理速度很慢。

4. 一次请求数据量很多,服务处理速度很慢。

场景1,传输效率很高,服务处理速度很快,一次请求很快就被完成,采用NIOBIO,在性能优势上除了操作系统对NIO的优化以外,BIO连接池不输于NIO。在易用性上,BIO更加容易处理。(NIO的异步机制,就要求消息传输协议需要有会话码来提供异步处理入口选择如何处理)

场景2,传输过程比较长,消耗时间比较多,服务处理速度很快,因此交互的时间大部分都还是在数据通道传输上,由于NIO在传输过程中依然是串行化的,因此BIO的连接池优于NIO,同时NIO一个客户端只有一个通道,因此BIO开的连接池越大,并行处理能力越强,因此BIO效率比较好一些。

场景3,传输量比较少,服务处理比较慢,很明显这是通道利用率低的表现,NIO有绝对的优势,特别是在高并发下。信道和服务端客户端资源被充分利用。

场景4,传输量比较多,服务处理也比较慢,这时候可以发现信道利用率取决于服务事件和传输消耗时间的比例,这类场景某些情况下BIO也会优于NIO

单线程和多线程

         在使用多线程来优化程序的时候,是否考虑过多线程的使用场景,多线程不是万能药,在某些情况下还可能是毒药。使用多线程的过程中,需要考虑这么几个因素:

1. 资源竞争,复杂度增加。

为什么前面提到的NIO客户端在处理数据流发送和读取的时候都是采用单线程,数据流的发送和读取都是在一个数据通道上的,而读取和发送本身时间消耗是固定的(不论是多线程还是单线程),同时增加了复杂度(需要处理数据包整合问题)。这其实就是在资源上的串行化操作直接导致了任务的串行化,因此任务多线程反而起到了反作用。

2. 是否是关键路径的工作,占关键路径的比例。

首先,在优化以前需要考虑优化的内容是否是关键路径的工作,如果不是,那么增加复杂度实现的多线程模式,就没有价值。其次就是看是否是在关键路径中占有比较大的比例,同样的,还是投入产出比例(多线程带来的复杂度以及在高并发下的一些资源保护措施都需要很多的维护成本)。

3. 任务的合理切分。

NIO的客户端,接受数据的事件将会写得很轻量级,但是接受到数据然后分析数据还原成业务对象,则会通过线程池的方式来分别处理。就好比监听连接到来,和实际的去建立连接分成了两个阶段的任务,让事件型的任务单纯,快速执行,让与业务相关的部分通过多线程并行的方式提高处理效率。总的来说就是把任务划分成为系统性的任务和业务性的任务,前者消耗时间少,设计尽量简单高效,采用单线程处理即可,后者通常情况下在处理流程和资源上不冲突的情况可以通过多线程并行提高效率。

         优化应用关注点:

A.关键路径是否可以优化,关键路径的任务拆分。

B.关键路径上的单个任务是否可以拆分并行执行。(是否有资源竞争,是否会有流程上的前后依赖,是否增加复杂度引入新的不稳定因素)

C.系统资源和依赖外部系统是否会成为瓶颈。(单机的CPU,IO都会在一定的压力下成下降趋势,并行执行反而降低了处理能力)

因此,可以看到不论是MapReduce设计下的Hadoop,还是Erlang语言级别的特性,都尽量的希望任务之间可以并行执行,相互之间低耦合,通过异步事件消息通知方式来交互,同时数据没有共享,防止资源竞争导致无法并行高效处理。系统设计还是要根据场景来判断使用什么方式优化,越简单越好。

posted @ 2010-01-27 01:45 岑文初 阅读(3657) | 评论 (1)编辑 收藏

     摘要: 基于MapReduce的配置型日志分析组件  阅读全文
posted @ 2010-01-12 21:58 岑文初 阅读(3850) | 评论 (5)编辑 收藏

     摘要: TOP团队招贤纳士  阅读全文
posted @ 2009-12-11 15:52 岑文初 阅读(1899) | 评论 (0)编辑 收藏

    中午左右收到一个看我blog的朋友的邮件,最近他在研究mapreduce,然后想用hadoop来做一些工作,不过遇到了一些问题,我这边也贴一下他的几个问题,同时觉得自己把自己的一些看法分享一下,当然只是自己的一些想法,也许对新学习的同学有帮助。

   问题:

  1. 从Map(K,V)的方式来看,难道mapreduce只能做统计?
  2. 目前我想除了日志分析之类的功能外,还想做一个全文检索的功能,类似windows查询一下,通过关键字查询文件的位置即可(可能还要根据匹配度做排序),这个我很迷茫不知道怎么下手,痛苦ing
  3. 你的实践是一个单机模式,如果用户把一个1G的log已经上传到hdfs了,此时分割工作已经完成,只需要从client那里得到文件基本信息和块的location就可以了,那mapreduce怎么进行下去呢?

   我给回复的邮件内容:

   首先,MapReduce的思想和Hadoop的MapReduce的架构不是一个概念,说的具体一点也就是Hadoop的架构设计只是MapReduce的一个子集思想的实现。每个人都可以根据自己对MapReduce的理解去实现业务处理,简单来说多线程处理就是MapReduce的一种最简单的实现,复杂来说多机协调工作就是一种复杂的实现。

   MapReduce的思想里面最值得借鉴的:

   a.问题分而治之。(找到流程的关键路径,优化可以并行处理的工作)

   b.计算靠近数据。(这也是hdfs存在的最重要的特点,计算的转移往往要比数据转移廉价,特别是对海量数据的处理)

   c.数据规模化随着并行处理成数量级递减。

   剩下的内容就是各个框架对于非业务性需求的处理,例如容灾,如何尽量少穿数据协调处理等等。

   针对他提出的三个问题:

    1. Hadoop的mapreduce从架构上来说最适合的就是统计分析计算。做其他方面的工作需要考虑是否适合,而不是为了技术而技术,先有需求再有技术选型。
    2.  对于你这个需求直接用搜索技术实现就可以了,不一定要硬套在mapreduce上。
    3. 对于海量数据是否一定要到hdsf上,或者就简单得数据物理或者逻辑切割来直接处理,根据自己业务场景选择。hdfs的特点就是对文件切割,容灾,数据逻辑存储和物理存储无关性(便于扩容管理,同时也是计算靠近数据的技术保证)。

    是否使用MapReduce框架,HDFS存储关键还是看你是否真的需要,当现有框架对自己来说并不合适的时候可以对小规模问题定制MapReduce的处理,最简化就是你去多线程或者多进程处理问题,需求决定技术选型。

  

posted @ 2009-12-09 13:09 岑文初 阅读(2584) | 评论 (1)编辑 收藏

Author:放翁(文初)
Email:fangweng@taobao.com
Blog:http://blog.csdn.net/cenwenchu79 

 

当前问题:

1.       不小比重的Rest请求都是无效请求,全部接纳数据消耗比较多的时间。

2.       Multipart类型的大文件流请求无法做到合理快速过滤。(参数错误请求,数据文件过多请求,文件大小过大请求)

归结来说,TOP平台处理的服务在解析参数时比较消耗时间和带宽(客户端网络速度慢导致传输字节流比较慢,文件比较大导致带宽占用严重)

处理方式:

通过自行解析字节流方式来lazy化处理请求,减少无效请求对于解析参数时间消耗(导致web容器连接消耗)及带宽消耗。

优化目标:

         Get由于内容长度有限不列入在优化范围。

         优化Post方式的请求(普通的和Multipart),要求优化后:在正常请求处理上两者处理速度不低于传统方式,非正常请求在策略命中情况下(后面会谈到什么情况下优化失效),性能有明显提高。

具体实现:

        由于现在用的是传统IO模式,因此可以用流的方式来lazy解析和处理请求(NIOchannel + buffer package就无法lazy了)。




         一共有三个组件角色:

1. 请求处理配置策略:配置在解析参数时,优先的规则(参数可以从header,uri,post body中获取,相互之间的优先性),异常抛出规则(字节流长度,文件大小,文件个数限制等),字节流解析模块的参数配置(字节流解析的窗口大小,超时时间等)。

2. 线程上下文:用来保存处理过的请求参数。一来复用,二来也是由于请求字节流处理不可逆(不保存字节流副本),必须保留。

3. Http请求字节流解析模块。根据具体的配置以及解析策略来解析字节流,同时将解析结果保存在线程上下文中。主要的实现代码在于对Post消息体逐步解析部分(普通的Postmultipart

压力测试结果:

    正常请求场景( 100并发用户,multipart 文件大小300k,当前业务场景这个值已经满足了):

普通post的处理能力1000TPS。(servlet方式处理差不多,不过有波动)  

  multipart处理能力610TPS。(apache开源项目fileupload,处理能力400TPS左右)

错误请求场景

         异常情况的处理有了很大提高,对于远程客户端传输较慢或者是大流量图片的错误请求都有很大的优化。

优化存在问题:

1. 参数缺失导致优化失效。

2. sign类似的交验,导致获取所有的参数。

3. 当前图片限制在300k,由于考虑处理速度快,就都没有设置超过阀值存储到本地,因此在高并发大流量的情况下也会有内存问题,当然已经做了部分保护。

针对上面的两个问题,作了部分的协议限制,对于API2.0希望将所有的系统参数和业务参数区分开,放入到Http header中或者url中,这样可以避免系统参数缺失导致优化失败,同时大量过滤系统参数出现问题的无效请求。

Sign类似的交验放在流程最后,避免过早获取所有参数。

作安全保护,设定简单丢弃或者io交互来缓解这个问题。

         这部分内容还有很多可以做得工作,其实最初的目的就是为了防止系统对于无效请求的处理消耗,我想在很多系统都会有这样的问题,利用缓存设置黑名单防止攻击也是这样的初衷。因此这点可以考虑在很多系统设计的时候都作一样的优化,对正常的不能优化,起码对错误的可以做一些优化,防止在异常请求高涨的时候,系统被击垮.

posted @ 2009-12-08 01:51 岑文初 阅读(2236) | 评论 (2)编辑 收藏

Author:放翁(文初)
Email:fangweng@taobao.com
Blog:http://blog.csdn.net/cenwenchu79


其实想说这句话很久了
,和很多同事接触,有时候或多或少的都会发现大家会陷入在自己的一亩三分地里面.

         主要表现得症状

1.       PD的需求就是目标,踏实的实现,不懂的就猜。

2.       经验盖过一切,设计系统就是要够完备够复杂。

从开发人员角度来看,第一种人多半比较有自己的想法,同时也有不少的工作经验,同时可能对技术比较着迷。另一种人多半是刚刚工作或者经验不足,要么就是习惯性把工作当任务,而不是爱好,写程序也就是一份赚钱的活。但看起来其实各自都在自己的一亩三分地上捣鼓,忘记了作为一个开发人员最基本的原则:“满足客户需求”。

先说1类型吧,在我们的Team有一个刚毕业一年多的同学,很勤奋,不论从学习以及工作,实实在在,踏踏实实。我们这边来需求,通常大需求我们都会全体过一下,一些小点的需求他就自己考虑一下就作了。那天正要上线,突然说了一下设计修改的内容,发现不仅满足不了PD原有的需求,而且给系统带来了缓存暴增的隐患。然后找来PD一谈,其实他要的功能已经在现有系统中已经实现,只是需要做部分的修改,而不需要新的去建立一套机制。这样的情况其实在前前后后出现了不少次数了,但其实一直没有和他细谈。后来我下班时候和他一起回家的时候说:“很多时候, PD为了让你理解,从开发的角度想要去描述一个需求,但其实最终失去了他自己想要的东西。因此对你来说第一步不是急忙的去考虑如何实现PD的想法或者和他争论他的设计是否合理,而是需要先问他:你想要什么,想要实现的东西最终目的是什么,能满足客户的什么需求?当他能够说清楚他想要什么,也知道要的东西能给客户带来什么价值的时候,我们再回过头来看,究竟应该怎么做?”这其实和我每次和同学分享一些设计的时候步骤是一样的,首先为什么要这么做,然后才是考虑如何从我的目标去寻找行动的方法方式,不然你会发现你和别人讨论了许久的东西,实现出来的时候已经背离了你的目标很远。因此在做任何需求或者设计的时候第一个问题就要问自己为什么要做,作的过程中时刻要记得我的目标是什么。这让我想起了我在离开阿软的那些日子和王坚博士谈话以及听他的一些对于设计的理念,很多时候还没有到规模化的情况下,先解决客户的需求,在解决客户需求以后,逐步的去考虑规模化问题的设计。(当然不是说第一版设计就可以随便作,良好的基础能够提升后续改进的速度)。

二类型的就比较多了,其实是很多开发人员的通病,包括有时候我自己也会陷入这样的误区。通常情况下有两种场景会陷入这样的误区,同时当事人却又不愿意改变。第一种情况就是觉得自己有不少的经验,同时对技术很执着,希望设计出来的都是很完美的,一次发布就可以满足个12年,但其实从这些年的设计角度来看,首先系统都是不断迭代进化的,因此一步到位的说法基本上不靠谱(除非就是一模一样的场景代码重复使用),其次系统的架构要做的足够灵活,通常情况就需要先做核心功能,预留出足够的空间和切入点,这样对未来扩展和需求变化有足够的适应度。从这两点来看,其实设计初期就是要求找到客户最想要的,扩展可以实现客户可能要的,防范客户没有估量到的。但这其实就需要和我们的产品设计师有充分的交流,好的产品设计师不会告诉你你怎么去实现,但是他会告诉你我想要的是什么,这些能给客户带来什么,这时候你可以告诉他我能够通过什么方式来满足你的需求。这样的开发和产品设计交流的结果才是技术化的产品,大家各司其职,同时也通晓对方领域的一些情况,对对方领域的只能给出建议,不是指导,这点在TOP我很庆幸有很好的黑羽同学,我们的交流就是这样产生良性互动。这有点撤远了,刚才说了第一种场景,然后说说第二种场景,就是初期其实大家都没有明确细节,但是在实施过程中开发人员会根据自己的接触面来选择一些技术和架构设计,最后看起来很复杂,很完美,但其实越是复杂的设计背后有越多的隐患。但是此时因为已经设计好了,就不愿意再去简化,也不愿意听任何人的意见,其实这是很危险的。我过去也犯过类似的错误,但是其实当你冷静下来,想想那句话,我们的目标是什么:“满足客户需求”,这时候你就会考虑,这么复杂的系统会不会给客户带来更多的不稳定以及复杂度,其实客户不关心你背后如何实现的,但是你需要满足客户的最基本的需求,用起来方便,高效,实实在在提供了解决问题的手段。

今天下午面试了一个外部的同学,工作年限比我长,看了简历也经历了很多项目,同时在描述的时候写了对高并发,分布式等等都很熟悉和热衷,我开始看了简历就担心,可能我这边不一定要他,因为我怕他开口就是说一大堆如何做高并发和分布式的内容。在我看来如果你没有搞清楚你什么时候要用牛刀,什么时候要用剪刀的人,和你谈论牛刀的构造其实没啥意思,因为在我看来,技术只要你肯花时间去学,没什么学不到的,但是做事方式和项目设计经验却是长时间积累的。幸好今天和他一谈,他对于技术的态度以及架构设计的思想都和我想的比较接近,不是为了技术而技术,不是为了过程而过程,了解如何从简如繁,再从繁入简,最终能够找到自己的目标。当然后来还是谈了很多技术细节的问题,毕竟干活还是要一个好手,作了那么多年如果没有经验和技术积累也是很可怕的事情。最后我问了他两个问题:1.你学习一个新技术的过程是怎么样的?2.你和你同事如果在设计方案上有冲突你怎么解决?他告诉我他学习新技术首先会去考虑这个技术的特点是什么,和其他技术的差别,他的擅长领域是什么,这样才能够用到实处。第二个问题他和我说就是开会讨论,最后大家群体决定。我对他第一个问题感到很满意,因为我就需要这样的同事,第二个问题我给了他一个建议,其实在很多时候,将别人的架构设计的优点融入到自己的设计中,不再以方案作为边界,那么大家最终就很容易达成一致,因为你在接受别人的思想时其实能够看到自己的不足,同时对待别人不是用否定的态度,会让你更容易得到认可和接受。(这点作起来需要不断的改变程序员自身的好胜个性,我起码还是出于变化中

我记得我小时候上政治课的时候,老师给我们划分了三种人:有能力但是没有道德的人是危险的人,没有能力但是有道德的人是对社会无害的人(觉得像葛优说的那个对社会无害的海龟一个概念),有能力同时也有道德的人是对社会有益的人。我觉得其实程序员也就可以从两个纬度看:

1.       有能力,有经验,对技术有追求。

2.       对产品化和客户没有任何感觉。

拥有了素质1但是没有素质2,那么最多也就只能说是试验室的花朵,在大学搞搞研究还不错,实际要做出产品来可能就是纸上谈兵,好钢始终用不到刀刃上,有力没地使。

素质1有所欠缺,素质2很明晰,对自己目标不断追求,其实这样的人,有时候笨鸟也会飞的比聪明的鸟更高。

拥有12的人,当然就是最好的人,只需要学会做人那么就可以发挥自己的能量。(程序员有时候就是很难改变自己的个性,去学会如何沟通和理解)
         最后一类就是自以为有12的人,这类人最怕就是面试的时候被考官通过,那么后续的问题就大了。

说了怎么多,其实也无非想说出一个程序员这些年的经历,从做开发到做基础平台,到做业务平台,该怎么踏实做事,该在什么时候找到自己的瓶颈,该在什么时候改变自己的状态,都需要自己好好的让自己冷静下来想想。做基础平台需要耐得住寂寞,同时也要知道自己是有客户的,服务不好客户,那么基础组件平台就是玩具。做业务平台需要学会去分析和沟通,需要去了解每一个层次的设计如何协作,同时在兼顾业务需求的同时满足隐性需求(稳定性,可用性,响应速度,规模化等等)。但归根到底,能给开发人员不断能量的不是技术本身,而是你用技术给你的客户带来的价值,对你的认可是长期做事的一个最基本的动力,因为当你现在觉得纯做技术能够支持你不断向前走的时候,其实在不远的将来你会体会到原来过程和目标是同样重要的。走出自己的一亩三分地,给自己多一点的空间,会让自己看得更远,走的更高。

posted @ 2009-12-08 00:54 岑文初 阅读(4228) | 评论 (6)编辑 收藏

   今年blog更新的速度比去年慢很多,当然最大的原因就是工作的转变。当选择留在云公司还是去淘宝,自己做了很快的抉择,去淘宝。其实在阿软的后面这一年,对自己来说是一个技术提升的阶段,工作任务不紧,技术预研范围较大,但对于自己这么一个已经到了30的人来说,应该是把技术转变为产品的时候了,因此义无反顾地选择了TOP作为我新的开端。

    其实每个人都会有自己不同的阶段,任何阶段都有自己的目标,同时当你发现在一个阶段停留很久,都没有什么突破,或者渐渐失去目标的时候,那么就需要考虑如何找到新的起点。对我来说,技术追求和提升是没有止尽的,但是需要真正的将所学的作出一点实在的产品,同时在参与产品团队的过程中,学会沟通,交流,分析问题,全面地看问题,这些也是不可缺少的成长经验,如果仅仅局限在狭隘的某一个技术立领域,那么就和普通的学生无异。

    到了TOP,自己的工作分成了三大块:1.救火及防火。2.整体架构支持。3.核心代码的编写。前期花了不少时间在1上,同时和各个Team交流,参与各个团队的关键性设计评审,以及对平台的统一规划,让我实实在在的作了一点2的事情。(说道实实在在,记得在阿软很多团队都抱怨我所在的架构组整天派一个人挂个名字,然后就算是架构支持了,当然这有很多原因造成,并不一定是负责架构的同学的问题)。对于3这点当然是自己最乐意做的,也是自己一直告诫自己要不断提升的,不论自己有多少理由说自己忙碌,写代码是我们这种人的生命所在,不然就会漂浮在空中,渐渐的走向“另一个世界”。 但自己觉得其实还少了一块,就是对业界的发展深入了解,这会让我看的不够远(幸好我们的产品经理黑羽同学总还会给我一些新的思路),到了年底将会多花一点时间作这部分内容。

    去年年底我写了关于对于Open API的思考和探索的一篇文章作为年底总结,今年一样,对于当前自己的工作将会有一份总结和规划,即是对今年平台发展的一个回顾,也是对平台未来的一点思考,大致已经列了一个纲要,对外可能部分内容不能全写出来,不过就算不写细节也会将一些思路写一下,大家可以相互探讨一下。这部分内容也将会成为我12月份参加淘宝内部淘宝大学讲课的内容,希望能够将今年新进淘宝的同学吸引到TOP来,为TOP增加人气。

   下面是一个mind 图,大致描述了一些内容:

posted @ 2009-11-27 00:58 岑文初 阅读(2929) | 评论 (2)编辑 收藏

     摘要: 常用模式的细节问题看设计稳定性  阅读全文
posted @ 2009-11-10 01:52 岑文初 阅读(2865) | 评论 (4)编辑 收藏

在自己的blog上做个招聘广告,TOP平台架构Team欢迎各位资深或者刚毕业的对TOP有兴趣的同学加入,可以直接给我留言或者发mail到fangweng@taobao.com,非诚勿扰^_^,同事可能比老婆相处的时间都要长。对了,请附加上你的简历,方便继续沟通。
posted @ 2009-10-30 15:51 岑文初 阅读(1327) | 评论 (2)编辑 收藏

     摘要: Author:放翁(文初) Email:fangweng@taobao.com Blog:http://blog.csdn.net/cenwenchu79   闲话:(如果图片看不清楚可以看另一个blog,因为图片在家,这里上传就只能转贴了)          为什么又叫做什么…的点滴,...  阅读全文
posted @ 2009-10-30 12:27 岑文初 阅读(3657) | 评论 (6)编辑 收藏

     摘要: 上海校招回来  阅读全文
posted @ 2009-10-13 21:27 岑文初 阅读(1455) | 评论 (4)编辑 收藏

     摘要: 客户端NIO实践分析  阅读全文
posted @ 2009-09-24 08:57 岑文初 阅读(3370) | 评论 (7)编辑 收藏

     摘要: 应用架构设计“防火”经验分享  阅读全文
posted @ 2009-08-27 00:59 岑文初 阅读(3165) | 评论 (5)编辑 收藏

   今天是转岗到淘宝的第七天,也算是一周吧,期待来这个团队已经有快大半年了,这次阿软的重组给了一个机会,过去的就过去吧,不再回首有任何的抱怨和遗憾,需要面对的是新的将来。

    很奇怪,来到淘宝,都是熟人,Boss是早就相识的菲青,TOP团队的自雪,凤先,秀芳及我不认识但是认识我的其他同学都很热情,运营,PD,OST都是以前阿软的老同学,还有其他几个团队的朋友,感觉回到了家,而不是离开了家。

    原先来淘宝是比较坚决的,同时也得到王博士的支持,心里还是比较有底的,不过就是担心过来以后和淘宝已有的团队合作可能会有磨合期,因为担心有“小圈子”。结果却是很出乎我的意料,TOP的人就和做的事情一样,是一批开放的人,自雪,凤先,张三各个都很放的开的和我聊,对于架构,对于技术,对于未来的发展,这些人坐在一起什么都可以说,自己觉得自己早先是用老思维来看待这个团队了。这个团队很年轻,很有活力和创造力,缺少的只是一些经验,而我经验是有一些,但是那些斗志已经在去年一年被磨砺的差不多了,正好是我回炉好好再热一热的时候了。来之前就和黑羽有过接触,也看过他对于TOP的一些构想,在我的计划中就有和他交流的部分,上周找了一个时间碰了一下,果然有很多和我一致的想法,同时还有一些比我更加深入的idea,特别是对于大淘宝未来的一个构想。其实来到TOP我所要做的就是在技术的架构上找到商业的感觉,让商业驱动技术,技术沉淀积累来支持商业的畅想。

    这七天过的很快,全身心投入的工作,时间总是过的很快,而且过去那种沉闷的心情和处事的态度在这里得到了改变。明天基本上就看完了TOP的大部分代码,整理了一些review的建议,同时昨天还花了一些时间去看了看google appengine,写了几个小应用,看了看源码(部分反编译),因为要给boss对于小应用hosting方面的一些想法。

   总的来说还是和我原先的计划一样,商业上和PD运营交流,了解未来TOP商业发展方向,以及对技术架构的一些需求。架构上从代码和文档看起,文档不是很多,所以就只好每个工程看过来,也不错,看到自雪同学写的代码还是不错的,同时也看到了淘宝的基础组件的推广力度之大,这比在阿里软件强的多,其实也是我一直希望看到的,人人都是技术牛人,都在做重复的事情,但是却没有技术沉淀,其实大家完全可以吧自己的构想增强在别人的基础之上,而不是什么都自己搞一套,淘宝的技术应该来说在政策上得到了支持,技术积累效果还是不错的,这里还不得不提到我的淘宝同学毕玄同学的服务基础框架HSF,虽然现在还没有接触,但是应该已经发展的挺好的。

   有两个能够用人,担得起起技术团队发展的Boss,有这么一些年轻有冲劲的小同学,有这么一些乐于倾听分享协作的老同学,有这么一些很有商业feeling的非技术团队同学,要做好TOP,我想只有三个字:“没问题”。这是我在入职七天写的随记,一年后再来回看我今天说的这些话,在来看看这个团队创造的价值。

   附:在淘宝申请好了花名:放翁。陆游的字,武侠小说的人就连扫地的都没有了,历史名人也没有了,不过诗人倒是没有人用,指不定还开创了淘宝同学入职的花名新取法。

   好好工作,天天向上,为了TOP,为了家里的BB,为了自己的一点理想,踏踏实实的走自己的路,让别人开车去吧,^_^

 

本文来自CSDN博客,转载请标明出处:http://blog.csdn.net/cenwenchu79/archive/2009/08/12/4440248.aspx

posted @ 2009-08-12 23:16 岑文初 阅读(1160) | 评论 (1)编辑 收藏

   昨天是去淘宝工作的第一天,最近最头痛的就是花名,在我儿子出生的时候我就知道起名字是最麻烦的事情,而起花名更是痛苦,因为你的选择余地更小,同时还不能和前人重复,好不容易找到两个还不错的,结果一个给其他部门的老大保留了,一个因为拼音和一个同学相似而无法使用。想用文初,结果还给一个淘宝的活跃用户使用了,问了HR不取花名是否可以,回答说,不可以,太折腾了。

   昨天开了一整天的会,主要还是协调两个平台之间将来的合作模式,同时也梳理了双方的现有功能,将未来双方的边界做了初步定夺,同时也对将来的一些需求做了初步的规划,系统的模块化也提上了最近的日程。

  今天会化一些时间看看已有的代码熟悉一下Top的情况,同时也看看一些流程性的文档,希望能够尽快的对Top全方位的了解,这样便于从细节实现到整体架构设计都能给出自己的意见。

  初来乍到不容易,很多需要从新开始的,不过对我来说合作的人,做的事情还是有一定的基础,因此只是需要一周左右的过渡期,后续应该会走的更加顺畅。

 

 
posted @ 2009-08-06 05:12 岑文初 阅读(1020) | 评论 (0)编辑 收藏

     摘要: Author : 岑文初 Email: wenchu.cenwc@alibaba-inc.com Blog: http://blog.csdn.net/cenwenchu79 Date: 2009-5-26 目录 需求转而学习 “软”负载均衡 LVS (Linux Virtual Server) Virtual Server三种模式介绍 Virtual...  阅读全文
posted @ 2009-08-04 22:32 岑文初 阅读(2266) | 评论 (1)编辑 收藏

     摘要: “软”负载均衡学习点滴  阅读全文
posted @ 2009-08-04 22:30 岑文初 阅读(2075) | 评论 (0)编辑 收藏

Author : 岑文初

Email: wenchu.cenwc@alibaba-inc.com

Blog: http://blog.csdn.net/cenwenchu79

Date: 2009-5-26

目录

需求转而学习

“软”负载均衡

LVS Linux Virtual Server

Virtual Server三种模式介绍

Virtual Server三种模式的比较

Virtual Server三种模式实践

三种模式下的简单压力测试

HA-Proxy

HA-Proxy安装和使用

HA-Proxy的压力测试结果

负载学习心得

需求转而学习

         很多时候不少做开发的同学都认为技术更新的快,新技术、新概念层出不穷,大家乐此不疲的去跟随着所谓的“技术趋势”走在风头浪尖上,但其实往往忘记了一个最重要的问题“满足客户需求”。其实技术就是为满足需求服务的,用最小的代价来满足用户的需求,以最简单高效的方式来达到目标,就是每个开发者应该追求的。(不要因为自己的架构很简单就脸红拿不出手,只要你在满足用户当前需求的基础上对未来有所考虑,那么化繁为简就是一种能力的表现)

         SIP(服务集成平台)5.7版本中对于未来多个服务提供商,多种类型的服务,在每日几亿的调用压力下,需要找到一个解决方案:可以分流不同服务提供商的服务,分流不同类型的服务,服务隔离化来减少服务相互之间影响以及服务提供商之间的影响。

         当前SIP的前端是通过硬件F5作负载均衡,因此是无状态无差别的服务负载,这也使得无法区分不同的服务提供商的服务请求和不同类型的服务请求,导致服务提供商之间的服务会产生相互影响(旺旺即时通信类API在峰值占用了大部分的服务处理资源,淘宝宝贝上传类API占用了大量的带宽)。近期还有更大的两类API将会接入,因此寻找一个服务可分流的方案势在必行。(当然过去也考虑通过三级域名配置在负载均衡上来解决这些问题,但是这样首先对于开发者来说不透明,其次也是一种比较僵化的设计方案,扩展和维护也有一定的难度)

         在过去也尝试过ApacheWeb容器自己的一些load balance特性,当然效果不是很好,和硬件基本无法比拟,而一些专有的“软”负载均衡方案和开源项目也没有深入的去了解,因此借着这次机会,好好深入的挖一挖“软”负载均衡。

“软”负载均衡

         作为互联网应用,随时都需要做好用户量突然增大,访问量突然上升的准备。今年热门的词汇“云”我就不多说了,这里就简单说说服务器的横向扩展。其实和DB,文件系统等一样,当资源成为瓶颈的时候,就需要考虑如何通过扩展或者提升资源能力来满足用户的需求,这就是我们常说的横向扩展和纵向扩展。(对于横向扩展和纵向扩展的优劣大家应该都很清楚了,这里也不做赘述)横向扩展中就会要求使用负载均衡的能力,如何根据资源能力不同以及资源在运行期负荷动态变化将负载合理分配是判断负载均衡优劣的标准。

         软件负载均衡一般通过两种方式来实现:基于操作系统的软负载实现和基于第三方应用的软负载实现。LVS就是基于Linux操作系统实现的一种软负载,HA Proxy就是基于第三应用实现的软负载。(后面会详细介绍这两种方式的使用)

         最早期也是最原始的软负载均衡:“Round Robin DNS”,通过轮询方式在DNS绑定多个IP的情况下,将用户对于同一个域名的请求分配到后端不同的服务节点。这种方案的优点:配置简单,负载分配效率高。缺点:无法知晓后端服务节点服务情况(是否已经停止服务),无法保证在一个Session中多次请求由一个服务节点服务,每一个节点都要求有一个外网IP

         另一种较为常见的就是基于分发器的Load balance。服务使用者通过向分发器发起请求获得服务,分发器将请求分发给后端实际服务处理的节点,给客户提供服务,最常说的反向代理模式就是典型的分发器Load Balance。这类负载均衡处理可以基于应用级转发,也可以基于IP级别转发,当然基于应用转发效率和损耗比较大,同时分发器本身也会成为瓶颈。

LVS Linux Virtual Server

         LVS是在Linux操作系统基础上建立虚拟服务器,实现服务节点之间的负载均衡。LVS主要是处理OSI模型中的4层消息包,根据一定的规则将请求直接转发到后端的服务处理节点,有较高转发效率。

         Virtual ServerLoad Balancer和一组服务器的逻辑组合统称,使用服务者只需要与Virtual Server进行交互就可以获得高效的服务。真实服务器和Load Balancer通过高速LAN进行交互。Load Balancer能够将请求分发到不同的服务端,在一个虚拟IP下并行处理多个请求。

Virtual Server三种模式介绍

Virtual Server有三种基于IP级别的负载均衡实现方式:IP address translationNAT)、Direct routingIP Tunneling

         NAT(Network address translation)由于IPV4的某些缺陷和安全原因,某些网段例如(10.0.0.0/255.0.0.0, 172.16.0.0/255.240.0.0 and 192.168.0.0/255.255.0.0)不能被用于互联网,因此常常被用作内部局域网,通过网络地址翻译的方式可以让这些网段的服务器访问互联网或者被互联网访问。网络地址翻译主要作用就是将一组ip地址映射到其他的一组ip地址,当映射比例为1:1的时候通常称作静态映射,而当映射地址为M:N(M>N)的时候(M为被映射地址数量,通常是内部ip),则成为动态映射。而对于Virtual ServerNAT模式来说,就是利用了NAT的特性,将内部的一组服务器通过映射到一个虚拟的IP,然后以一个外网虚拟服务节点的身份对外提供服务。

         上图是一个实际的NAT范例,对外的服务IP202.103.106.5,内部建立了虚拟IP172.16.0.1,然后将内部其他两台实际服务的服务器172.16.0.2172.16.0.3映射到172.16.0.1这个虚拟IP。客户端向202.103.106.5发起请求服务,Load Balancer查看请求数据包,如果是请求目标地址是注册的虚拟IP及监听端口的时候,那么通过NAT按照一定算法选择某一台实体服务器,再重写报文目标地址,转发请求到实际的目标服务器,当目标服务器处理完毕以后,将处理结果返回给Load Balancer,由Load Balancer修改源地址,返回给客户端。

         IP TunnelingIP管道技术是在IP报文上再次封装IP报文协议的一种技术。允许将一个目标为AIP数据报文封装成为目标为BIP数据报文,在特定的IP 管道中传输。

         上图就是IP Tunneling模式的运作原理。首先客户端还是通过访问对外的一个服务IP请求服务,当Load Balancer接受到请求以后,检查VIP注册信息,然后根据算法选择实际的一台后台服务器,通过IP管道封装技术对IP报文再次封装,然后将消息通过IP管道转发到实际的服务器,实际的服务器通过解包处理请求,然后根据包体内实际的服务请求地址,将处理结果直接返回给客户端。

         Direct routing利用Load Balancer和实际服务器共享同一VIP,简单的通过修改消息报体目标MAC地址,转发请求,然后再通过实际服务器配置VIP为本地回环,直接处理消息报文,而不再转发,当处理完以后,直接将处理结果返回给客户端。

 

         上图就是Direct Routing的运作流程,当外部请求到Load Balancer时,通过查找VIP注册信息,直接选择一台后端服务器作为新的目标地址,修改消息报文中的目标地址Mac地址,转发到目标服务器,目标服务器由于配置VIP在本地网卡回路中,因此直接处理消息,将处理完的结果直接返回给客户端。

Virtual Server三种模式的比较

         下表是官方整理出的关于Virtual Server三种不同模式的区别:

NAT

TUNNEL

DR

服务器要求

无要求

需要支持IP管道

arp组件(当前也有补丁)

网络要求

Private

LAN/WAN

LAN

可支持后端服务器节点数

较少(10-20

较多

较多

服务网关

Load Balancer

本身

本身

NAT:根据其实现原理,可以知道这种模式对于操作系统,网络都没有太多的要求和约束,但是由于消息需要打解包,同时消息的响应都必须经过Load Balancer,因此Load Balancer自身成为了瓶颈,这样一个Load Balancer能够支持的后端服务节点数量就有限了。当然可以采用混合模式来解决这个问题,也就是通过TUNNEL或者DR模式作为前端模式串联起多个NAT模式Balancer

TUNNEL:这种模式要求操作系统支持IP Tunnel,通过对IP报文再次封装转发,达到负载均衡的目的。设计这种模式的初衷是考虑,对于互联网很多服务来说,服务请求数据量和返回数据量是不对称的,返回的数据往往要远远大于请求的数据量,因此如果请求和返回都走Load Balancer会大量占用带宽,影响处理能力。IP Tunnel设计中请求是通过Load Balancer,但是返回是直接返回到客户端的,因此节省了返回的带宽,提高了请求处理的能力。

DR:这种模式要求Load Balancer和后端服务器处于同一个局域网段。DR模式处理消耗最小,消息转发和回复基本没有损耗,因此效率应该是最高的,但是约束是相对来说最多的。

posted @ 2009-08-04 22:24 岑文初 阅读(3378) | 评论 (2)编辑 收藏

    小A,30,所在公司在去年的经济危机中没有倒下,但是在今年却倒下了。小A觉得能够把一个公司混倒闭了,也算是人生的一点经历。

    公司是没了,但是工作还要继续,生活还要继续,现在将要面对一个新的环境,环境很陌生,但也比较熟悉,工作职责很清晰,但也充满了挑战。人过30,有了孩子,真的成熟了很多,知道了什么叫做责任感,知道了未来真的需要好好规划,需要一个机会,需要一个平台来找到自己,实现自己的价值,不让这黄金时代就这么过去。

   小A将要面对的挑战在心里面已经做好了准备,也有了自己的一套短期的规划及工作安排,要成长有时候就要有压力。在小A即将离开原来团队的时候,和手下的一个同学发了火,因为在这阵子调整过程中,同学的心态一直变的很差,但是小A已经竭尽全力去分析他的未来,虽然听进去,但是过几天依然又开始放弃自己,这种态度让小A原本很看好他发展的心情变得很沉重,最后就在那个探讨会上说了他一些比较重的话,虽然说完以后自己也有些后悔,可能我对他和对我自己一样,要求太高了吧,就像博士说的,如果对一个人没有想法了,就恭维几句即可,大家你好我好大家好,只有当对这个人还存在一定的期望的时候才会表现出这种比较急切的感觉。

   新的开始,新的挑战,新的环境,新的机遇,新的难题,新的称呼

   好的心态,好的沟通,好的未来

   一切都需要小A用自己的能力去证明,走自己的路,让自己走的更好。

posted @ 2009-08-03 09:58 岑文初 阅读(868) | 评论 (0)编辑 收藏

    转眼到了7月份了,今年的blog更新的很慢很慢。写点东西记录自己的生活和工作状态。
   生活:
   儿子提早10天在六月八号来到我们这个小家庭,每个好友在祝福我的同时告诉我,辛苦的日子刚刚开始。不过和大家的感觉一样,辛苦但快乐着,在别人忙着在互联网上种花种草,养猪养鸡的时候,我开始扛起培养祖国新一代的责任。睡觉基本上很难保证连续性,早晨的运动也移到了晚上给儿子洗好澡以后。以前觉得就算到30岁还是觉得自己比较年轻,但是在那个23:25分儿子出来的一瞬间,自己觉得自己真的老了,需要成熟一点了,对儿子,对老婆。

    工作:
    其实今年年初的时候就有些彷徨,自己一手培养出来的SIP和原来的目标渐行渐远,7月份我在产品会议上提出了SIP6(第一阶段最终版),功能,性能,可扩展性都能够满足到明年中旬。虽然日访问量就快突破1亿,年底可能会到几个亿,但是这些数字对我来说只能证明这个架构还可以,但是SIP原有的目标已经被抛弃,成为了一个内部的服务集成平台。
   下个阶段会在做一些中心来满足团队的需要,但在我看来其实这些东西对我对团队的价值有限,创新有限,但这就是工作。
    公司内部有些变化,当然是好是坏不得而知,不过作为我们这些level已经处于地面的人来说也没啥影响。

   文章:
   最近的文章素材其实不少,但是受到内部技术专利申请,外部投稿的影响,能够写出来直接贴的越来越少,有时候也是这样,分享固然好,但是有些时候有些东西只能够小范围分享。

   睡觉,睡觉,中午的休息是很宝贵的,一觉醒来还继续自己的路。(走自己的路,让自己无路可走。没写错,呵呵,觉得这样挺搞笑的)
posted @ 2009-07-09 12:38 岑文初 阅读(743) | 评论 (0)编辑 收藏

 

         这篇blog的问题不能算是解决,仅仅只是一种分析和猜测,后续的一些行动可能会证明一些猜想,也可能什么都解决不了。如果有和我相同情况的同学,也知道是什么问题造成的,请不吝赐教。

问题:

上周周末,没有和同事们出去Outing,在家管孩子,去生产环境观察了一下集群机器的当前运行状态,发现应用在这些多核机器上压力极端不均匀。

         Top一下大致状态如下:



         峰值的时候,单CPU的使用率都到了80%,这种情况对于多核服务器来说是很不正常的使用。对于Java的开发者来说,多线程编程是无法控制线程如何在CPU上分配的,因为Java本身不实现线程机制,说是跨平台的语言,但是性能及特性会根据操作系统的实现有很大的差异,因此Java调优有时候需要对系统配置甚至内核作调优。

分析:

         首先在测试环境下作了多次同样的压力测试,尝试了与线上一样的操作系统版本,相似的配置,但测试结果却是负载分配很均匀。

   
     

         此时重新启动了一台问题机器,发现负载降下来了,同时也很均衡,也就是说在当前的压力下不应该有这样高的cpu消耗,同时也排除了硬件或者操作系统的一些配置问题。

         CPU满负荷的情况下,很多时候会认为应该是循环造成的,对于单个CPU的消耗更是。通过Top H查看具体到底哪一个线程会长时间消耗CPU

         可以看到PID13659的线程是“罪魁祸首”,但13659究竟在干什么,是应用的线程还是系统的线程,是否是陷入了死循环,不得而知。接着就按照Java的土办法,Kill -3 pid,然后看看输出日志。

         根据线程号来查找dump出来的日志中nid,发现这个线程是VM Thread,也就是虚拟机线程。(这里作一下转换,将13659转换成为16进制就是0x355b



         pstack看了一下这个线程的工作,结果如下:

Thread 2074 (Thread 1846541216 (LWP 13659)):

#0 0x0659fa65 in ObjectSynchronizer::deflate_idle_monitors ()

#1 0x065606e5 in SafepointSynchronize::begin ()

#2 0x06613e83 in VMThread::loop ()

#3 0x06613a6f in VMThread::run ()

#4 0x06506709 in java_start ()

#5 0x00aae3cc in start_thread () from /lib/tls/libpthread.so.0

#6 0x00a1896e in clone () from /lib/tls/libc.so.6

         搜索了一下ObjectSynchronizer::deflate_idle_monitors,发现了sunbug库中有bug关于jdk1.6中由于这个方法导致运行期问题的说法:http://bugs.sun.com/bugdatabase/view_bug.do;jsessionid=803cb2d95886bffffffff9a626d3b9b28573?bug_id=6781744

         然后就直接去openjdk官方网站去查找这个类的代码,大致了解一下他的作用,具体的代码链接如下:http://xref.jsecurity.net/openjdk-6/langtools/db/d8b/synchronizer_8cpp-source.html
主要工作应该是对资源对象的回收,在加上pstack的结果,应该大致知道是对线程资源的管理。但具体代码就没有进一步分析了。

接着就分析一下自己的应用:

         压力测试(高强度、长时间)都做过,没有发现什么异常。

         本身应用是否会存在的缺陷导致问题呢。有人说VM Thread兼顾着GC的工作,因此内存泄露,对象长期积压过多也可能影响,但其实在dump的结果可以看到,GC有单独的工作线程,同时我也观察到GC这些线程的工作时间长度,因此由于GC繁忙导致CPU上去,基本上来说可以排除。

         其次在SIP项目中使用了JDK的线程池(ExecutorService)LinkedBlockingQueue。后者以前的文章里面提到在1.5版本里使用poll方法会有内存泄露,到1.6虽然没有内存泄露,但是临时锁对象增长的很快,会导致GC的频度增加。

行动:

         上面零零散散的一些分析,最终让我决定有如下的行动:

1.       升级某一台服务器的JDK,当前是1.6.0_10-b33,打算升级到1.614版本。比较观察多台机器的表现,看是否升级了JDK可以解决问题。

2.       去除LinkedBlockingQueue作为消息队列,直接由生产者将生产结果按照算法分配给消费者线程,避免竞争,锁的消耗,同时也防止LinkedBlockingQueue带来的资源消耗。

3.       测试环境继续作长时间的压力测试,同时可以结合Jprofile之类的工具来分析长时间后可能出现的问题。

后话:

         这年头真的啥都要学一点,求人不如求己。

SA,DBA,测试都需要能够去学习一些,起码在初期排查问题上自己能够做点啥,要不然别人也忙,自己又无从下手。就好比这次压力测试好不容易排上队,但是还是满足不了及时上线的需求,因此自己去LoadRunner压,好歹给出一个零时的报告先大家看着。应用的异常有时候是应用本身设计问题,也可能是开发语言的问题,也可能是操作系统的问题,因此要去定位这种比较复杂的问题,真的需要有耐心去好好的学习各种知识,现在看来知识还是匮乏啊,要不然就可以分析出openjdk中可能存在的问题。

posted @ 2009-07-09 11:59 岑文初 阅读(4403) | 评论 (3)编辑 收藏

 

         昨天在看Cache Client代码的时候,发现在从资源池中获取SocketIO部分代码在高并发情况下效率不高,因此考虑通过一些变通的方式来提高效率,下面说的内容仅仅是当前自己琢磨出来可以部分提高效率的方法,希望看了这篇文章的同学能够有更好的方式或者算法来提高效率。

情景:

       Cache Client SocketIO资源池是一个两级的Map,具体定义为:ConcurrentMap<String, ConcurrentMap<SockIO, Integer>>。第一级MapHost作为Key,第二级MapSockIO本身作为Key,三种SockIO状态(可用,占用,废弃)作为value。之所以采用一个Pool来存储三种状态主要是考虑到在高并发下,多个池之间保持原子性的复杂。

每一次获取可用的SocketIO的操作需要经历:1.遍历Host所在的Map2.逐个比较状态。3.原子方法获取可用SocketIO。(并发问题所要求的,具体代码可以下载:http://memcache-client-forjava.googlecode.com/files/alisoft-xplatform-asf-cache-2.5.1-src.jar )。

在修改过去的版本里面,首先遍历的过程是一个固定顺序的过程(keyset),这样会导致在高并发的情况下,越来越多的资源申请命中率会下降,因为压力总是落在keyset靠前的那些SockIO上(重复比较)。需要考虑通过什么手段可以提高在高并发下的申请命中率。

思考:

1. 资源申请的越早,被释放的可能性越高,因此是否可以考虑采用更新SockIO最后申请时间来作为后续申请的初步依据。(本身复杂度带来的耗时可能会超过命中率降低带来的损耗)

2. 采用随机数的方式来确定keyset的起始游标,也就不是每次都从keyset第一位开始(可以把keyset看作一个首尾相接的数组)。

3. 在每次资源回收的时候纪录下该资源为可用(当前为每一个Host就记录一个可能可用的资源,简单化操作),作为申请的首选尝试。(尝试不成功在去遍历)。

当前实现了2,3组合,发现效果明显,在500个并发下,每个线程200次操作(一系列动作),压力测试结果如下:

Cache test consume(cache测试总共耗时)average boundle consume(每个线程总耗时),average per request(每个线程每次操作总耗时)

没有作任何改动以前的测试结果:

cache test consume: 11507741, average boundle consume: 57538, average per request :115

采用了2策略以后的测试结果:

cache test consume: 10270512, average boundle consume: 51352, average per request :102

采用了23策略以后的测试结果:

cache test consume: 9140660, average boundle consume: 45703, average per request :91

posted @ 2009-05-07 17:15 岑文初 阅读(1951) | 评论 (0)编辑 收藏