`
robbin
  • 浏览: 4800092 次
  • 性别: Icon_minigender_1
  • 来自: 上海
博客专栏
377a9ecd-1ea1-34ac-9530-9daa53bb2a7b
robbin谈管理
浏览量:135782
社区版块
存档分类
最新评论

请注意Rails2.3自带的memcache-client有性能问题

    博客分类:
  • Ruby
阅读更多
Rails2.3版本发布了,这个版本内部的改动非常大,相关介绍可以看JavaEye这篇新闻:http://www.iteye.com/news/5390,估计最近也有不少人开始动手升级到Rails2.3了,JavaEye也不例外,这一升级才发现性能低得令人发指。

由于过于信任Rails框架,没有进行本地性能测试,在通过了兼容性测试就兴冲冲上线了。这一上线,动态请求立刻堵了一大堆,仔细看了看fastcgi的crash log,发现大量请求在flush数据的时候发生broen pipe。打开Rails2.3新采用的Rack框架源代码当中fastcgi的adapter一看,这代码写的太不负责了!fastcgi协议本身是没有设定缓冲区的,写出去的数据立刻就发送掉了,结果Rack还非常多余的在每次写数据之后flush一下,造成了连接已经关闭之后,fastcgi还傻傻的等着flush数据呢!

自行修改了Rack的fastcgi adapter,本地运行压力测试,fastcgi不再报错,代码上线发布,立刻又堵住了,load非常高,这下开始怀疑是不是Rack的fastcgi支持的不好,导致的性能差? 由于thin是对Rack支持最好的Rails应用服务器,因此我们把网站rails运行方式从fastcgi改成了thin,再次代码上线发布,又堵住了,而且堵的更严重,load比刚才用fastcgi还要高很多! 由此也可以看出来,fastcgi毕竟还是Rails性能最好的运行方式。

完全排除了fastcgi的问题,又排查了好几处可能造成性能影响的地方,还是无法解决rails2.3一上线请求就被堵塞的问题。最后老老实实在本地进行了性能测试,这下终于真相大白。在我本地MacOSX的环境下面,rails2.2的情况下每秒可以处理40个请求,但是rails2.3每秒只能处理25个请求,同时CPU消耗的更多,进程内存占用更高!

最后真正的原因是Rails2.3自带的memcache-client有重大性能问题

简单的来说,Rails2.2自带的memcache-client是1.5.0版本,这是一个用了很久很稳定的版本了,也是目前 memcache-client官方正式发布版本;而Rails2.3的memcache-client升级到了1.6.5版本,这是一个全新的版本,仅仅在github上面,并未正式发布,可以看成一个开发当中的版本,而这个版本有无数的问题!

第一、它设置了一个怪异的timeout参数,默认情况下,导致连接memcache server的速度变得异常缓慢,把该timeout参数改成nil以后,速度恢复正常

第二、它把连接memcache server的每个方法操作改成了闭包调用,固然代码和异常处理显得优雅一些,但是性能测试表明,整体应用性能会下降很多。

第三、它里面的代码还有一些自相矛盾的地方,比方说多线程的检测和处理代码有错误

总之,在把rails2.3的memcache client版本换成老的1.5.0版本以后,性能问题得到了解决,而且在本地性能测试的结果表明,在rails2.3上面运行JavaEye代码,速度比rails2.2上面还要提升了11%的性能,但是内存消耗有所上升(估计是rails2.3的local cache带来的)。

当然memcache-client 1.6.5也不是一无是处,他添加了自动故障转移的能力(在多个memcached server之间),内部代码也进行了一些重构(尽管重构的结果是性能更低下),添加了一些多线程支持(尽管这部分代码根本不能正常工作),不过毕竟这还是一个开发当中不成熟的版本,rails不应该很草率的就升级了memcache client版本。
分享到:
评论
56 楼 robbin 2009-03-25  
richyzhang 写道
升级过快确实是个问题,agile那本书出来了,是针对2.2的,书刚出来rails2.3就出来了.这书的销售实在会受影响.
2008年虽然升级众多,但是真的有突破性的也就只有passenger的横空出世外加支持多线程和国际化了.
不过,2.3性能比起2.2差那么多,实在是没想到.


那你可说错了,我前面说过了,严肃的应用,passenger就是一个玩具。至于多线程支持对于rails来说根本就是多余的,我前面提到的2.2的数据库查询数据量一大就出现问题就是这个问题导致的,至于国际化,本身集成不集成差别不大。

2.2,2.3都是重大的版本升级有非常多很有意义的功能升级,关于这一点,到可以自行搜索JavaEye新闻频道去了解。
55 楼 richyzhang 2009-03-25  
升级过快确实是个问题,agile那本书出来了,是针对2.2的,书刚出来rails2.3就出来了.这书的销售实在会受影响.
2008年虽然升级众多,但是真的有突破性的也就只有passenger的横空出世外加支持多线程和国际化了.
不过,2.3性能比起2.2差那么多,实在是没想到.
54 楼 t0uch 2009-03-25  

不过在3.0出来之前,DHH貌似保证继续维护2.3,一些bugfix应该也会有的。
53 楼 robbin 2009-03-24  
hjleochen 写道
我觉得这种指责和质疑相当没道理.

在产品环境不断最求最新最酷本就有如儿戏.无论是操作系统,数据库还是框架,在产品环境中至少应该延迟一个主要版本,2.1,出来的时候可以升级到2.0,2.2出来的时候可以升级到2.1,而不是新版本出现2,3天就迫不及待的追上.

一个未经过广泛使用和验证的系统本就不应该在在线系统中使用,出了问题是正常的,而出了问题用什么态度面却是另一个问题.不过值得庆幸的是实验室里面的小白鼠不会有什么太过激的反应...

另外从rails发展壮大的角度来说,dhh推崇Passenger并没什么不对的地方,如果php没有如此方便的部署,没有几十块钱一年的虚拟主机,相信一定没能发展到今天的高度.不是没个人都在机房有托管主机的,不是每个人都要尝试不同的部署组合的,也不一定每个人有权利决定使用什么服务器的.一个方便的部署方式对于rails的发展是很有好处的.


你有这种质疑不奇怪,不过你不了解rails core team不负责任的bugfix方式,正是这种方式在迫使rails用户不得不跟随rails版本升级。比方说现在rails2.3已经发布了,按照你的逻辑,现在可以放心的用rails2.2了对吧?但是当你放心的从rails2.1升级到2.2以后,从数据库里面读取大数据量的时候,你会发现rails会不定期的报告数据库查询错误,而你根本找不到任何应用代码出错的可能性;然后你还会发现升级到2.2以后,rails进程使用的内存会不定期的出现暴增,以至于你不得不定期杀掉该进程重启,最后当你google发现,该内存泄露bugfix的patch已经被提交到了rails2.3版本上去了,你想要在2.2上面解决,那么对不起,自己给生产环境的2.2打补丁吧。

除非出现重大安全bug,否则rails core team在发布一个主要的rails版本之后,不会再维护该版本,全部工作都会扑到下一个版本的开发当中,即使发现bugfix,一般也不会发布维护版本,而是合并到下一个版本当中一并解决。所以当用户发现当前版本的bug,要么就被迫跟随升级rails版本,要么就得自己维护自己的rails版本。

坦白说,这个问题也不能完全怪rails core team,毕竟core team的人手也不多,要怪只能怪rails的版本升级速度实在太快了。如果我记得不错的话,2005年年底,rails才推出1.0版本,到2006年rails就推出1.1版本,到2007年初就推出了1.2版本,重大的版本升级,然后2008年初就推出了rails2.0版本,又是重大升级,2008年中推出2.1版本,仍然是重大升级,2008年底2.2就出来来,仍然是重大版本升级,2009年3月2.3接着推出,还是重大版本升级,下半年版本3.0就会面世,这将是rails有史以来最大的版本升级。

从2005年年底到2009年下半年,三年多时间,rails总计要经历8次重大升级,平均不到6个月时间就来一次重大升级,2008年就经历3次重大升级,2009年还要经历2次重大升级,以一般的软件主要版本的维护周期为四年计算的话,那么rails core team就要同时维护8个rails版本,毫无疑问这是不可能完成的任务,所以rails core team干脆选择了不负责任的维护方式,升级一个新版本就放弃一个旧版本维护,这样做的后果就在逼着rails用户非升级不可。

其实我本人也很希望rails在发布3.0版本以后放慢重大版本升级的速度,18个月推出一个重大版本升级就足够了,尽量花更多的时间在版本的维护上面,加快小版本号升级,否则的话,除了geek,真的没人敢放心的用rails了。
52 楼 hjleochen 2009-03-24  
我觉得这种指责和质疑相当没道理.

在产品环境不断最求最新最酷本就有如儿戏.无论是操作系统,数据库还是框架,在产品环境中至少应该延迟一个主要版本,2.1,出来的时候可以升级到2.0,2.2出来的时候可以升级到2.1,而不是新版本出现2,3天就迫不及待的追上.

一个未经过广泛使用和验证的系统本就不应该在在线系统中使用,出了问题是正常的,而出了问题用什么态度面却是另一个问题.不过值得庆幸的是实验室里面的小白鼠不会有什么太过激的反应...

另外从rails发展壮大的角度来说,dhh推崇Passenger并没什么不对的地方,如果php没有如此方便的部署,没有几十块钱一年的虚拟主机,相信一定没能发展到今天的高度.不是没个人都在机房有托管主机的,不是每个人都要尝试不同的部署组合的,也不一定每个人有权利决定使用什么服务器的.一个方便的部署方式对于rails的发展是很有好处的.
51 楼 richyzhang 2009-03-24  
amonlei 写道
昨天刚升到2.3.2,xp 下面,跑ruby1.8.6,感觉开发的环境下速度快多了,2.2.2的时候一刷页面,机器就慢下来,现在好多了。。不知道生产环境如何


这个似乎是load少了的关系吧.
50 楼 luolonghao 2009-03-24  
duker 写道
shaka 写道
可以理解,看来ROR还是高级玩具。
不知道Robbin有没有上了贼船的感觉


好像看到一个测试数据, python 应该是动态语言里面速度最快的,
robbin当初为何没有选择python 呢?


我没记错的话,动态语言里最快的是mod perl。
49 楼 lllyq 2009-03-24  
与memcached有关倒是有可能,我第一次测试的结果也是2.3性能爆差,大概是2.2的一半,现在回忆起来当时memcached server正在跑一个很耗cpu的脚本,于是换了一个memcached server,结果性能就总是比较接近了。

而且我的memcached也是自己做了wraper,貌似rails升级的changelog也有与memcached的修改,也有可能我的wraper绕过了rails的修改,明天到公司再看看
48 楼 robbin 2009-03-24  
测试过了,不是template cache的问题,但是发现了一个新问题。

在我的MacBook上面测试rails2.2,用ab访问论坛首页,可以60request/s,disable memcached以后,性能下降到38request/s,换成rails2.3以后,只有16request/s,性能差的惊人!但是在disable memcached以后,居然性能提升到了24request/s,看来性能问题是和memcached有关的。而template cache打开还是关闭,对性能测试结果几乎没有影响。

不过在都关闭memcached的情况下,rails2.3的测试性能仍然远远落后于rails2.2,所以暂时对rails2.3还是不报什么希望。
47 楼 真无名 2009-03-24  
有小白鼠,爽。
不过我觉得如果语言太魔术了,性能要受影响
毕竟支持魔术背后需要很多层次
46 楼 真无名 2009-03-24  
tanggq 写道
ror好处是开发快,但部署好象就不那容易了

这个比apache+PHP基本上不会存在这个问题

这个是许多网站前台均用php的原因


ubuntu linux 有傻瓜的ror部署方案。
45 楼 robbin 2009-03-24  
我想我可能找到rails2.3性能爆差的原因了,在Rails的blog上面曾经有这样一篇日志:http://weblog.rubyonrails.org/2009/2/27/this-week-in-edge-rails,里面有这样一段话,这段话我是曾经看过的,当时没太注意,看到上面有人回帖说rails2.3慢是慢在了render view上面,我这才猛然想到了以前看过的这段话:

从老版本升级上来的代码,默认并没有打开template cache,这可能就是性能差的罪魁祸首,接下来我将测试一下。

引用
A Note About Template Loading

After some extensive work by several authors (here’s the Lighthouse ticket), Rails 2.3 includes the ability to enable or disable cached templates for any particular environment. Cached templates give you a speed boost because they don’t check for a new template file when they’re rendered – but they also mean that you can’t replace a template “on the fly” without restarting the server.

In most cases, you’ll want template caching to be turned on in production, which you can do by making a setting in your production.rb file:


config.action_view.cache_template_loading = true

This line will be generated for you by default in a new Rails 2.3 application. But please note: if you’ve upgraded from an older version of Rails, you won’t have this setting in your production.rb and template caching will be off by default. Unless you really need the ability to update templates in production without restarting the server, you should be sure to add this setting when you upgrade.
44 楼 neodoxy 2009-03-24  
duker 写道
shaka 写道
可以理解,看来ROR还是高级玩具。
不知道Robbin有没有上了贼船的感觉


好像看到一个测试数据, python 应该是动态语言里面速度最快的,
robbin当初为何没有选择python 呢?

如果这么说的话,现在我正在游戏服务器里集成web服务,使用lua,速度快得多,不过需要自己造不少轮子
43 楼 QuakeWang 2009-03-24  
amonlei 写道
昨天刚升到2.3.2,xp 下面,跑ruby1.8.6,感觉开发的环境下速度快多了,2.2.2的时候一刷页面,机器就慢下来,现在好多了。。不知道生产环境如何

我在开发环境下面也是快很多,这得益于2.3的lazy load,可是到了生产环境就慢得不像话,按道理2.3移植到了rack,并且加上了一些性能优化,不应该这么挫的,等有时间好好profile一把。
42 楼 dualface 2009-03-24  
ruby 轮子少是因为以前没什么人用 ruby,现在用户多起来,轮子也会多起来的,呵呵。下次换 php 得啦。
41 楼 amonlei 2009-03-24  
昨天刚升到2.3.2,xp 下面,跑ruby1.8.6,感觉开发的环境下速度快多了,2.2.2的时候一刷页面,机器就慢下来,现在好多了。。不知道生产环境如何
40 楼 amonlei 2009-03-24  
lllyq 写道
2.3.2.1就是用gem install的2.3.2

我测下来性能差距在10%, 2.3慢,主要在render部分,如果没有render view,性能持平
有空大家也测测看

补充一下,如果view比较复杂,有loop render partial的n>10,差距稍稍增加,也不超过15%

god! 俺超爱用render :file ,还循环内嵌用。。。。没办法太喜欢了。。。。html一多,我就想办法拆分。。。render。。。。

ps:这习惯是从liferay里面学来的,用了n多的include,而且用得很好
39 楼 lllyq 2009-03-24  
2.3.2.1就是用gem install的2.3.2

我测下来性能差距在10%, 2.3慢,主要在render部分,如果没有render view,性能持平
有空大家也测测看

补充一下,如果view比较复杂,有loop render partial的n>10,差距稍稍增加,也不超过15%
38 楼 t0uch 2009-03-24  
不知道这个和blog上说的2.3.2.1版本又没有太大关系
37 楼 系统程序 2009-03-24  
我两台服务器40万PV, 一台做数据库一台跑rails, 正想升呢

相关推荐

Global site tag (gtag.js) - Google Analytics