1

要在下面的示例中创建用户,我必须加载 它们@projects@companies因为它们是创建用户所必需的。

class UsersController < ApplicationController
  def new
    @user = User.new
    # duplication here
    @projects = Project.all
    @companies = Company.all
  end

  def create
   @user = User.new(params[:user])
    if @user.save
      redirect_to @user
    else
      # and here
      @projects = Project.all
      @companies = Company.all
      render :action => "new"
    end
  end
end

我必须在两种(重复)情况下加载这些依赖项,以便在用户无效时执行新操作和创建操作。

我可以通过将这些依赖项封装在一个方法中来进行重构load_user_dependencies

class UsersController < ApplicationController
  def new
    @user = User.new
    load_user_dependencies
  end

  def create
   @user = User.new(params[:user])
    if @user.save
      redirect_to @user
    else
      load_user_dependencies
      render :action => "new"
    end
  end

  private

  def load_user_dependencies
      @projects = Project.all
      @companies = Company.all
  end
end

或者通过将它们添加为 helper_methods。

 class UsersController < ApplicationController
  helper_method :projects, :companies

  def new
    @user = User.new
  end

  def create
   @user = User.new(params[:user])
    if @user.save
      redirect_to @user
    else
      render :action => "new"
    end
  end

  def projects
    @projects ||= Project.all
  end

  def companies
    @companies ||= Company.all
  end
end

我也可以创建一个视图对象

class UserView
  def products
    @products ||= Product.all
  end

  def companies
    @companies ||= Company.all
  end
end

class UsersController < ApplicationController
   def new
     @user = User.new
     @user_view = UserView.new
   end

   def create
    @user = User.new(params[:user])
     if @user.save
       redirect_to @user
     else
       @user_view = UserView.new
       render :action => "new"
     end
   end
 end

其他选择是使用演示者

class UserPresenter < SimpleDelegator
  def products
     @products ||= Product.all
  end

  def companies
    @companies ||= Company.all
  end
end

class UsersController < ApplicationController
   def new
     @user = UserPresenter.new User.new
   end

   def create
    @user = UserPresenter.new User.new(params[:user])
     if @user.save
       redirect_to @user
     else
       render :action => "new"
     end
   end
 end

大家平时是怎么处理剧情的呢?

4

1 回答 1

1

这有点个人品味问题,但在我们的项目中,如果合适,我们会在视图中进行,如果很复杂,我们会在 before_filter 中进行。

视图 - 如果它是没有任何逻辑的东西,则无需为此创建变量。如果您的表单包含在部分中,则超级有用,因为它只完成一次,因此很容易维护。

<%= form.select :project_id, Project.all, :id, :name %>

如果它可以根据任何因素而改变,那么控制器中的 before_filter :

MyController
  before_filter :find_projects, :except => [:destroy, :some_method] # Will load the values but not for the destroy or some_method actions

  def find_projects
    @projects = Project.where(:some conditions => true)
  end
于 2013-06-13T14:09:12.717 回答