渲染背后的基本原理:new而不是redirect_to new for POST create?

时间:2012-02-13 11:32:55

标签: ruby-on-rails rest

给定一个rails RESTful控制器

class WidgetsController
  def new
    @widget = Widget.new
  end

  def create
    @widget = Widget.new(params[:widget])
    render :new and return unless w.save

    redirect_to widget_path(@widget)
  end
end

除了捕获参数和呈现验证消息之外,如果验证失败,为什么约定为render :new而不是redirect_to new_widget_path

如果验证失败,URL将从/widgets/new更改为/widgets这不会破坏REST的概念吗?

3 个答案:

答案 0 :(得分:2)

渲染不会调用控制器操作,因此您在创建操作中设置的实例变量将被带到新视图。

这意味着任何验证错误都会在新视图中保留...

redirect_to将为new运行控制器操作,因此创建模型的新实例...并且您将丢失错误...

希望这会有所帮助

答案 1 :(得分:1)

你可以这样做而不是渲染新动作吗?

   flash[:thing] = params[:thing]
   redirect_to new_thing_path

然后在新的

   @thing = Thing.new(flash[:thing] || params[:thing])

这对我来说真的好看,因为否则如果你的控制器中有任何逻辑需要渲染新的/编辑动作,你必须重复那个逻辑(或创建一些before_filter或者其他东西) )在更新/创建。我意识到这涉及到另外一个请求,但除此之外,代码似乎更简单,更安全(除了您正在破坏rails约定的事实)并且它为用户提供了一个有效的URL,对于查看/执行相同的操作始终是相同的的事情。

如果他们刷新,他们将失去他们的价值观,但在提交前任何形式都是如此。这似乎对我来说比刷新更有意义,导致重新提交警告,这很奇怪。例如,用户应该如何清除表单?

这个rails-ism总是让我烦恼。这是否有任何严重的问题我不考虑?其他应用程序框架是否也都这样做?

答案 2 :(得分:0)

渲染的东西是它不会导致生成另一个请求。它将转到相应的视图并显示它。但是,通过重定向,将生成对浏览器的重定向请求,这将导致对服务器的另一个请求。