Rails应用优化指南 (2)

优化ActionController

  使用components会对ActionController的性能造成较大的影响,我的建议是没有特别的理由,不要使用components,因为调用render_component会引发一个新的请求处理循环。大部分情况下,component都可以使用helper 或者partials代替。

  优化ActionView

  对于每一个请求,Rails都会创建一个controller和view实例,并会将controller的action中创建的实例变量通过 instance_variable_get和instance_variable_set传递给view,因此不要在action中创建view中用不到的实例变量。

  优化helper

  首先是pluralize,可以看一下pluralize的实现,如果不给出最后一个参数,它会创建一个Inflector实例,因此不要写pluralize(n, ‘post’),应该写成pluralize(n, ‘post’, ‘posts’)。

  其次是link_to与url_for,由于需要查找路由策略,因此link_to与url_for可以说是最慢的helper方法,没有特别的需要,不要使用这两个函数。

<a href=“/recipe/edit/<%=#{recipe.id}%>”class=“edit_link”>
look here for something interesting
</a>

  会比下面这段同样结果的代码快许多:

<%= link to “look here for something interesting” ,{ :controller => “recipe”, :action => edit, :id => @recipe.id },{ :class => “ edit link” } %>。


  优化ActiveRecord

  访问AR对象的关联对象相对而言会比较慢,可以使用:include提前获取关联对象

class Article
belongs to :author
end
article.find ( :all, :include => :author)


  或者使用piggy backing指定要获取的关联对象的某些字段,关于piggy backing的介绍请参看[2]

class Article
piggy back :author name, :from => :author, :attributes => [:name]
end
article = Article . find ( :all, :piggy => :author)
puts article .author name


  另外需要注意的是,从数据库中获取的字段值一般来说都是String类型,因此每次访问可能都需要进行类型转换,如果你在一个请求处理过程中需要进行多次转换,那么最好对转换后的值进行缓存。

  还有,根据我对一个应用的分析,大约有30%的时间花在了字符处理上,另外30%时间花在了垃圾收集,还有10%用于URL识别,因此在数据库中缓存格式化后的字段可以大大减小字符处理的开销。

  优化Ruby代码

  前面,我们的优化策略主要是针对Rails框架本身进行,现在我们将精力集中到Ruby语言本身上来。

  首先,Ruby语言中的各种元素由于算法的不同,访问时间也各不相等,比如局部变量采用数组索引,在解析时进行顶问,因此访问代价总是O(1),而实例变量和和方法调用由于使用Hash访问,因此只能保持理论上的O(1)访问,也就是没有冲突的情况下,同时调用方法时如果不能在子类找到这个方法,则还需要沿继承树向上回溯查找。

  因此,应该尽量避免不必要的多态继承,同时应该尽量使用局部变量,比如下面这段代码的效率就不如修改后的高:

def submit to remote(name, value, options = {})
options[ :with ] ||= ’Form.serialize( this .form)’
options[:html ] ||= {}
options[:html ][ :type ] = ’button’
options[:html ][ :onclick ] = ”#{remote function(options)}; return false ; ”
options[:html ][ :name] = name
options[:html ][ :value] = value
tag(”input” , options[:html ], false )
end


  修改后:

def submit to remote(name, value, options = {})
options[ :with ] ||= ’Form.serialize( this .form)’
html = (options[:html ] ||= {})
html[:type ] = ’button’
html[:onclick ] = ”#{remote function(options)}; return false ; ”
html[:name] = name
html[:value] = value
tag(”input” , html, false )
end


  其次,对于经常用到的数据,应该进行缓存,避免每次用到时再进行计算,比如:

def capital_letters
( ”A” .. ”Z” ). to a
end


  写成下面这样会更好:

def capital letters
 @capital letters ||= ( “A” .. “Z” ). to a
end



  当然对于上面这种情况,如果所有类需要的数据都相同,那么完全可以将它定义成class级变量:

@@capital letters = (“A” .. “Z” ). to a
def capital letters
@@capital letters
end


  当然,除了效率也要注意优美,下面这段代码就不够优美:

def actions
 unless @actions
 # do something complicated and costly to determine action’s value
@actions = expr
end
@actions
end



  改成这样会更好一些:

def actions
@actions ||=
begin
# do something complicated and costly to determine action’s value
expr
end
end


  另外,使用常量对效率也有一定提升。

def validate_find_options (options)
options.assert valid keys( :conditions , :include , :joins , :limit , :offset ,
:order , :select , :readonly, :group, :from )
end



  上面这段代码进行如下修改会更好一些:

VALID FIND OPTIONS = [
:conditions , :include , :joins ,:limit ,:offset ,:order , :select ,:readonly,:group,:from ]
def validate find options (options)
options.assert valid keys(VALID FIND OPTIONS)
end



  同时,应该尽可能的使用局部变量。

sql << ” GROUP BY #{options[:group]} ” if options[:group]


  上面这种方式明显不如以下两种:

if opts = options[:group]
sql << ” GROUP BY #{opts} ”
end
opts = options[:group] and sql << ” GROUP BY #{opts} ”



  当然,能够写成这样是最好的:

sql << ” GROUP BY #{opts} ” if opts = options[:group]


  但是目前版本的Ruby还不支持这样做。

  另外,还有一些小技巧:

logger.debug ”args: #{hash.keys.sort.join ( ’ ’ )}” if logger


  这段代码的问题在于,不管logger.level是否为DEBUG,hash.keys.sort.join(’ ’) 都会被执行,因此,应该写成这样:

logger.debug ”args: #{hash.keys.sort.join ( ’ ’ )}” if logger && logger.debug?


  还有就是关于ObjectSpace.each_object的,在production模式最好不要使用这个方法。

ObjectSpace.each object(Class) {|c| f(c) }


  事实上这跟下面的代码是相等的:

ObjectSpace.each object {|o| o.is a?(Class) && f(o) }


  它会对堆上的每一个对象都进行检查,这会对性能造成极大损耗。
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
该资源内项目源码是个人的课程设计、毕业设计,代码都测试ok,都是运行成功后才上传资源,答辩评审平均分达到96分,放心下载使用! ## 项目备注 1、该资源内项目代码都经过测试运行成功,功能ok的情况下才上传的,请放心下载使用! 2、本项目适合计算机相关专业(如计科、人工智能、通信工程、自动化、电子信息等)的在校学生、老师或者企业员工下载学习,也适合小白学习进阶,当然也可作为毕设项目、课程设计、作业、项目初期立项演示等。 3、如果基础还行,也可在此代码基础上进行修改,以实现其他功能,也可用于毕设、课设、作业等。 下载后请首先打开README.md文件(如有),仅供学习参考, 切勿用于商业用途。 该资源内项目源码是个人的课程设计,代码都测试ok,都是运行成功后才上传资源,答辩评审平均分达到96分,放心下载使用! ## 项目备注 1、该资源内项目代码都经过测试运行成功,功能ok的情况下才上传的,请放心下载使用! 2、本项目适合计算机相关专业(如计科、人工智能、通信工程、自动化、电子信息等)的在校学生、老师或者企业员工下载学习,也适合小白学习进阶,当然也可作为毕设项目、课程设计、作业、项目初期立项演示等。 3、如果基础还行,也可在此代码基础上进行修改,以实现其他功能,也可用于毕设、课设、作业等。 下载后请首先打开README.md文件(如有),仅供学习参考, 切勿用于商业用途。
Phusion Passenger是一种基于Nginx或Apache的应用服务器,它可以帮助我们快速、稳定地部署Rails应用。下面以Redmine为例,介绍在CentOS下如何使用Phusion Passenger方式部署Rails应用。 1. 安装必要的软件 首先需要安装Ruby、Rails、Nginx、Passenger等软件,可以使用以下命令: ``` sudo yum install epel-release sudo yum install ruby ruby-devel rubygems gcc gcc-c++ make sqlite-devel sudo gem install rails sudo gem install passenger ``` 2. 安装Nginx和Passenger 使用以下命令安装Nginx和Passenger: ``` sudo yum install nginx sudo passenger-install-nginx-module ``` 在安装过程中,需要选择“1. Yes: download, compile and install Nginx for me”选项,让Passenger自动编译和安装Nginx。 3. 配置Nginx和Passenger 默认情况下,Passenger会自动添加Nginx的配置文件并启动Nginx服务,但是我们需要手动修改Nginx配置文件。 找到Nginx的配置文件,一般是/etc/nginx/nginx.conf,添加以下内容: ``` http { # ... server { listen 80; server_name yourserver.com; root /path/to/your/redmine/public; passenger_enabled on; passenger_ruby /usr/bin/ruby; passenger_app_env production; } } ``` 其中,yourserver.com是你的服务器域名或IP地址,/path/to/your/redmine是你的Redmine应用所在路径。 4. 启动Nginx服务 启动Nginx服务: ``` sudo systemctl start nginx ``` 5. 配置数据库 修改/config/database.yml文件,配置Redmine连接数据库的相关信息。 6. 初始化Redmine 在Redmine目录下运行以下命令初始化数据库: ``` RAILS_ENV=production bundle exec rake db:create RAILS_ENV=production bundle exec rake db:migrate RAILS_ENV=production bundle exec rake redmine:load_default_data ``` 7. 启动Redmine 在Redmine目录下运行以下命令启动Redmine: ``` RAILS_ENV=production bundle exec rails server -e production ``` 现在你就可以在浏览器中输入yourserver.com访问Redmine了。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值