【问题标题】:Is there a way to create a Rails resource route called `index`?有没有办法创建一个名为“索引”的 Rails 资源路由?
【发布时间】:2016-04-26 13:22:41
【问题描述】:

我想向 Rails 4 应用程序添加一个名为 index 的资源路由,但生成的路由与预期不符。但是,如果我使用其他名称(例如show_index),它们就是。为了演示,我将从一个没有路由的普通 Rails 应用开始:

$ rake routes
You don't have any routes defined!

我将以下内容添加到config/routes.rb

  resources :items

这会产生以下资源丰富的 Rails 路线:

   Prefix Verb   URI Pattern               Controller#Action
    items GET    /items(.:format)          items#index
          POST   /items(.:format)          items#create
 new_item GET    /items/new(.:format)      items#new
edit_item GET    /items/:id/edit(.:format) items#edit
     item GET    /items/:id(.:format)      items#show
          PATCH  /items/:id(.:format)      items#update
          PUT    /items/:id(.:format)      items#update
          DELETE /items/:id(.:format)      items#destroy

应用程序有一个show 动作,如果参数散列包含{with: 'index'},则可以呈现所谓的index(这个索引是应用程序特定的东西,而不是collection 物品或类似的东西)。

我添加了一个自定义index 路由来调用带有附加参数的show 操作:

  resources :items do
    get 'index' => 'items#show', with: 'index'
  end

这会生成一条新路由,但它有 item_id 而不是预期的 id(与上面列表中的 edit_item 比较):

item_index GET    /items/:item_id/index(.:format) items#show {:with=>"index"}

Routing documentationexplains表示获取:id的方法是使用on: :member,所以路由需要是

get 'index' => 'items#show', with: 'index', on: :member

但这不会产生预期的结果。它添加了预期的路由,但它从默认的show 操作中窃取了item 方法前缀,而不是使用自己的index_item(同样,与上面列表中的edit_item 进行比较):

item GET    /items/:id/index(.:format) items#show {:with=>"index"}
     GET    /items/:id(.:format)       items#show

但是,如果我使用 index 以外的其他东西,例如 show_index,那么它会按预期工作:

get 'show_index' => 'items#show', with: 'index', on: :member

生产

show_index_item GET    /items/:id/show_index(.:format) items#show {:with=>"index"}

所以当路由被称为index 时,行为会有所不同。我预计这是因为隐含的 resources 路由使用该名称,尽管我认为他们使用它的方式不会发生冲突。在我看来,我应该能够添加一条新的index 路由,该路由将变为index_item(类似于现有的edit_item,与现有的item_index 形成对比)。

我知道我可以通过使用不同的名称来解决这个问题,正如我已经证明的那样。但是index 的阅读效果比show_index 好。

所以我的问题是是否可以用index 指定一个资源路由,该路由被关闭:id? `

【问题讨论】:

  • 试试get 'index' => 'items#show', with: 'index', on: :member, as: 'item_index'
  • Rails 的关键概念之一是“约定优于配置”。您的计划是使用七个 Rails 默认操作之一作为路由名称 在该决定中,您使用的是配置而不是约定,这是 Rails 的反模式。有可能让它工作吗?当然可以,但这不是您想要展示的代码,作为您在 Rails 应用程序上的工作示例。
  • 但这并不会改变七轨默认动作。它添加了另一个适合七个默认操作的操作。碰巧该操作的逻辑名称是index,但它不会以任何方式影响默认操作。

标签: ruby-on-rails ruby-on-rails-4 routes


【解决方案1】:

要设置特定的 url 使用 as 关键字,所以试试这样的:

get 'index' => 'items#show', with: 'index', on: :member, as: 'item_index'

或者当然是你的愿望之一。

【讨论】:

  • 使用item_index会导致方法以item_index_item为前缀,但使用index会得到index_item的预期结果。
猜你喜欢
  • 2011-06-20
  • 1970-01-01
  • 2011-08-03
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多