原创作者: hideto
阅读:1191次
评论:0条
更新时间:2011-05-26
Rails里富有Magic的东西往往实现起来非常简单,比如scaffolding
看看代码先,scaffolding.rb:
代码非常清楚,使用module_eval生成list/show/destroy/new/create/edit/update方法,然后调用render#{suffix}_scaffold方法
render#{suffix}_scaffold方法首先判断是否存在调用它的action的模板,如blog/new.rhtml,如果没有则使用scaffold_path下默认的模板new.rhtml
我们可以给scaffold方法给一个参数:suffix => true,这样生成的action方法带__#{singular_name}参数,如list_post、new_post
而默认的scaffold模板就在actionpack-1.13.3\lib\action_controller\templates\scaffolds目录下
看看代码先,scaffolding.rb:
module ActionController module Scaffolding def self.included(base) base.extend(ClassMethods) end module ClassMethods def scaffold(model_id, options = {}) options.assert_valid_keys(:class_name, :suffix) singular_name = model_id.to_s class_name = options[:class_name] || singular_name.camelize plural_name = singular_name.pluralize suffix = options[:suffix] ? "_#{singular_name}" : "" unless options[:suffix] module_eval <<-"end_eval", __FILE__, __LINE__ def index list end end_eval end module_eval <<-"end_eval", __FILE__, __LINE__ verify :method => :post, :only => [ :destroy#{suffix}, :create#{suffix}, :update#{suffix} ], :redirect_to => { :action => :list#{suffix} } def list#{suffix} @#{singular_name}_pages, @#{plural_name} = paginate :#{plural_name}, :per_page => 10 render#{suffix}_scaffold "list#{suffix}" end def show#{suffix} @#{singular_name} = #{class_name}.find(params[:id]) render#{suffix}_scaffold end def destroy#{suffix} #{class_name}.find(params[:id]).destroy redirect_to :action => "list#{suffix}" end def new#{suffix} @#{singular_name} = #{class_name}.new render#{suffix}_scaffold end def create#{suffix} @#{singular_name} = #{class_name}.new(params[:#{singular_name}]) if @#{singular_name}.save flash[:notice] = "#{class_name} was successfully created" redirect_to :action => "list#{suffix}" else render#{suffix}_scaffold('new') end end def edit#{suffix} @#{singular_name} = #{class_name}.find(params[:id]) render#{suffix}_scaffold end def update#{suffix} @#{singular_name} = #{class_name}.find(params[:id]) @#{singular_name}.attributes = params[:#{singular_name}] if @#{singular_name}.save flash[:notice] = "#{class_name} was successfully updated" redirect_to :action => "show#{suffix}", :id => @#{singular_name} else render#{suffix}_scaffold('edit') end end private def render#{suffix}_scaffold(action=nil) action ||= caller_method_name(caller) if template_exists?("\#{self.class.controller_path}/\#{action}") render :action => action else @scaffold_class = #{class_name} @scaffold_singular_name, @scaffold_plural_name = "#{singular_name}", "#{plural_name}" @scaffold_suffix = "#{suffix}" add_instance_variables_to_assigns @template.instance_variable_set("@content_for_layout", @template.render_file(scaffold_path(action.sub(/#{suffix}$/, "")), false)) if !active_layout.nil? render :file => active_layout, :use_full_path => true else render :file => scaffold_path('layout') end end end def scaffold_path(template_name) File.dirname(__FILE__) + "/templates/scaffolds/" + template_name + ".rhtml" end def caller_method_name(caller) caller.first.scan(/`(.*)'/).first.first end end_eval end end end end
代码非常清楚,使用module_eval生成list/show/destroy/new/create/edit/update方法,然后调用render#{suffix}_scaffold方法
render#{suffix}_scaffold方法首先判断是否存在调用它的action的模板,如blog/new.rhtml,如果没有则使用scaffold_path下默认的模板new.rhtml
我们可以给scaffold方法给一个参数:suffix => true,这样生成的action方法带__#{singular_name}参数,如list_post、new_post
而默认的scaffold模板就在actionpack-1.13.3\lib\action_controller\templates\scaffolds目录下
评论 共 0 条 请登录后发表评论