我的Rails应用程序中有一个酒店资源。我为一些额外的功能添加了一些自定义的非RESTful操作。
我有以下routes.rb文件:
resources :hotels do
post 'sort', on: :collection
post 'update_hotel_settings', on: :collection
end
以下是rake routes
的输出:
....
sort_hotels POST /hotels/sort(.:format) hotels#sort
update_hotel_settings POST /hotels/update_hotel_settings(.:format) hotels#update_hotel_settings
hotels GET /hotels(.:format) hotels#index
POST /hotels(.:format) hotels#create
new_hotel GET /hotels/new(.:format) hotels#new
edit_hotel GET /hotels/:id/edit(.:format) hotels#edit
hotel GET /hotels/:id(.:format) hotels#show
PUT /hotels/:id(.:format) hotels#update
DELETE /hotels/:id(.:format) hotels#destroy
update_hotel_settings操作是将一些常规设置保存到数据库的位置。 以下是发送给该操作的表单的开始:
<%= simple_form_for(@store, url: update_hotel_settings_hotels_path, html: {class: 'form-horizontal', id: 'hotel-settings-form'}) do |f| %>
给予:
<form accept-charset="UTF-8" action="/hotels/update_hotel_settings" class="simple_form form-horizontal" id="hotel-settings-form" method="post" novalidate="novalidate">...
然而,在提交表格后,POST请求被酒店抓住了。 REST更新操作,但有关网络能够找到id =&#34; update_hotel_settings&#34;的网站的例外情况。
显然这是一个不受欢迎的结果,我似乎无法找到它的原因。 不应该通过PUT / PATCH方法触发更新操作,而不是POST?我还尝试使用另一个名称作为路线+动作,而不是&#34; update_hotel_settings&#34;,没有运气。
最令人讨厌的是,上面列出的排序操作运行正常! (唯一的区别是&#39;排序&#39;动作是通过ajax触发的,但不确定是否重要)
修改
与您的想法相反,嵌套路线选择器实际上优先于资源的7条默认路线。
编辑2:另一个线索,另一个问题!
起初我很尴尬地注意到我忘记了simple_form_for论证中的method: :post
选项,当我添加它时 - Kapow!表格路线到正确的行动!奇怪的不是吗?特别是当已经有一个方法=&#34; post&#34;表单标签中的属性!
发生了什么事?
答案 0 :(得分:-1)
路由从上到下捕获。意思是,如果匹配,它就会停止。因此,您所要做的就是将update_hotel_settings路由从资源中取出并在此之前。
match '/hotels/update_hotel_settings', to: 'hotels#update_hotel_settings', via: 'post', as :update_hotel_settings_hotels
resources :hotels do
[...]