用于生产的Rails性能调优?

我正在接近部署基于Rails 3.1.x构建的应用程序,并开始运行一些性能测试。 在稍微摆弄ab之后,我看到一些非常令人沮丧的结果,在Heroku上产生大约15个请求/秒。

在本地测试时,我看到类似的结果,这些结果确实表明它是一个应用程序问题比什么都重要。

我正在运行Unicorn,比Celadon Cedar上的Thin快约40%。 此外,我正在使用PGSQL共享数据库。

我希望有人可以共享一份清单或基本上是一份发布清单,在准备生产应用程序并进入速度调整需求时,我应该通过该清单。 到目前为止,我还没有找到一个真正简明的可操作项目列表,根据我的情况,这似乎是有意义的。

或者,如果您在此类问题中有扎实的实践经验,那么任何输入都将受到赞赏!

我花了一些时间在heroku上调整我的应用程序,并花了一些时间在各种设置中进行Rails应用程序的性能调优。

当我运行ab -n 300 -c 75 … myapp.com ….#这是我主站点的备份,并且是与独角兽的免费雪松计划

 Requests per second: 132.11 [#/sec] (mean) Time per request: 567.707 [ms] (mean) Time per request: 7.569 [ms] (mean, across all concurrent requests) 

(这是针对一个没有做任何激烈的主页,所以我只是将它作为“heroku在一个非常简单的页面上的免费计划有多快?”的例子,而不是“你的应用程序应该是这快“”

这是我的Rails Performance Tuning 101清单:

  1. 首先测量浏览器/页面加载时间(浏览器发出大量请求,ab只告诉您其中一个请求,通常主页请求不是问题),从www.webpagetest等工具获取页面加载基线数。 org或www.gtmetrix.com用于面向公众的页面,或浏览器工具Yslow,google页面速​​度或私人页面的dynatrace。 如果你看一下页面加载瀑布图(chrome / firefox中的’Net’面板),它通常会显示你的html加载很快(在一秒内),但是其他一切都需要1-3秒才能加载。 按照Yslow /页面速度建议来了解如何改进(确保您完全使用Rails 3.1资产管道的东西)

  2. 仔细阅读你的日志文件/新文物,找到“最慢/最常点击”请求的最佳位置,并描述该请求会发生什么(它是慢速ruby /大量内存使用,还是大量查询?)你需要有一种可靠的方法来检测和监控性能问题,而不仅仅是随意改变。 确定一些目标区域后,创建测试脚本以帮助进行测试之前/之后,并certificate您的更改有所帮助,并检测回归是否存在。

  3. db列上缺少索引是最常见的问题之一,也是最容易解决的问题。 对目标查询运行说明,或查看慢速查询日志,以查看查询计划程序正在执行的操作。 根据需要添加外键,搜索列或主数据(覆盖索引)的索引。 重新测试实际生产数据,以certificate它有所作为。 (您可以在heroku中运行explain,以及对缺失或未使用的索引运行查询)

  4. 大多数性能较差的Rails应用程序都受到N + 1个查询的影响,因为它很容易编写order.owner.address.city而不考虑当它在循环中时会发生什么。 N + 1查询不一定是慢查询,因此它们不会出现在慢查询日志中,只是它们有很多,并且它们更有效地一次完成所有操作。 使用:include或.includes()用于急切加载该数据,或者以另一种方式查看您的查询。

  5. 分析您的应用程序的流程并寻找缓存机会。 如果用户在索引页面和详细信息页面之间来回跳转,然后再返回,可能在不离开索引页面的情况下对细节进行ajax视图会以更快的方式为他们提供所需的数据。 我在博客上写了更多关于它的想法

我在今年的WindyCityRails会议上介绍了芝加哥的这些技术和其他想法。 你可以在我的www.RailsPerformance.com博客上看到这里的video我对heroku的喜爱是你必须从一开始就可以扩展。 当您查看邮件列表上的讨论时,您会发现大多数人都了解性能最佳实践,以及如何充分利用服务器。 我也很喜欢你如果你想保持便宜,你会学习如何通过性能调整技巧来获得最大的成功。

祝好运!

有一些非常低调的成果几乎总能产生非常值得的性能提升:

  1. 通过使用更高效的ActiveRecord语句减少数据库查询的数量。 请务必在适当的地方使用includejoin ,并确保使用empty? 超过any? 当你需要一个COUNT时,尽可能避免使用SELECT
  2. 特别是在较重的页面上,缓存视图,即使只有几分钟。 您通常可以将较大或动态的片段分解为可以缓存的部分片段,而不会产生任何负面影响。
  3. 将任何网络上的活动移至后台作业。 这包括发送电子邮件,从其他网站获取页面,以及进行API调用(甚至[特别?]到Heroku)。 在Ruby中有许多非常好的后台作业处理库,DelayedJob非常受欢迎,因为它适用于任何ActiveRecord数据库,但我最喜欢的是Resque。

您需要注意不要花太多时间来优化Ruby例程。 除非您正在使用大量数据或处理(例如图像大小调整),否则您可能不会从优化循环或最小化内存使用量中看到非常显着的收益。 如果您发现某些页面存在问题,请深入了解日志并查看这些请求中发生的情况。

如果您还没有,那么像HireFireApp这样的自动缩放应用程序非常适合让您通过水平扩展来处理大量请求,而无需在慢速期间运行无关动态的成本。

PS:有一个名为Blitz的新Heroku附加组件,可让您测试最多5,000个用户的并发负载。

最全面的单一答案是使用类似NewRelic的东西来检测您的应用程序并找到慢点。 然后,您可以对代码应用优化或缓存以消除这些慢点。 作为Heroku客户,您可以免费获得NewRelic安装 – 它是一个可以从Heroku控制台添加到您的部署中的加载项。

一旦你了解了什么减慢了你的速度,那么你就可以开始接近它了。 Heroku处理大多数dev-ops性能调优的结束,所以你不需要在那里做任何事情。 但是,您仍然可以通过优化数据库查询并在适当的情况下执行片段和操作级缓存来获得巨大收益。

由于还没有出现,我将为PostgreSQL部分提供答案。 我无法协助Ruby。

您可以在PostgreSQL wiki中找到优化性能的出色起点。

  • 调整服务器设置 (不确定Heroku可以实现多少)
  • 特别注意慢查询
  • 检查您的硬件 (不适用于Heroku)