Rails搜索表单指向create而非index动作问题求助
这个问题的核心是form_tag的语法错误加上不必要的RESTful路由导致的,我们一步步来修复:
1. 修正form_tag的写法
你当前的form_tag参数传递方式有误,把:url和:method混在了controller参数里,导致表单的action和method都没正确设置。正确的写法应该是把目标路径作为第一个参数,然后在选项哈希里指定请求方法:
修改home/index.html.erb中的表单代码:
<%= form_tag(search_index_path, method: :get) do %> <%= label_tag(:name, "Search for:") %> <%= text_field_tag(:name) %> <%= submit_tag("Search") %> <% end %>
这样写的话,表单会正确生成action="/search"且method="get",提交时会直接触发GET请求到SearchController#index。
2. 精简路由配置
你当前用了resources :search,这会自动生成所有RESTful路由(包括POST /search对应的create动作),但你的SearchController并没有实现create方法,这也是报错的直接原因。我们可以只生成需要的路由:
修改routes.rb:
Rails.application.routes.draw do root 'home#index' resources :home # 只生成index和show动作的路由,避免不必要的路由冲突 resources :search, only: [:index, :show] end
如果你的搜索功能只需要index动作,甚至可以更简化:
get 'search', to: 'search#index'
为什么之前会报错?
你原来的form_tag写法错误,导致:url被当成了查询参数(所以表单action变成了/search?method=get),同时:method参数没有被正确识别,表单默认使用了POST方法。而resources :search会把POST请求到/search映射到SearchController#create,但你并没有实现这个方法,所以就出现了The action 'create' could not be found for SearchController的错误。
修复后,表单会以GET方法提交到/search,路由会正确指向SearchController#index,同时你也不会再触发不需要的create路由了。
内容的提问来源于stack exchange,提问作者Alex Erling

