rails路由中的嵌套资源有什么作用?

时间:2015-12-01 19:19:53

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

我遇到了一些看起来像这样的代码:

resources :posts, only: [:create, :index, :show] do
  resources :comments, only: [:show, :create] do
  end
end

我知道resources做了什么(它会自动创建一些宁静的路由),我知道only做了什么(它限制了哪些只包含),但我不知道其他内容是什么资源呢。

这实际上是对项目做了什么,还是将它们嵌套好以便你可以看到它们之间的相关性?

换句话说,这会完成同样的事情吗?:

resources :posts, only: [:create, :index, :show]
resources :comments, only: [:show, :create]

3 个答案:

答案 0 :(得分:1)

不,它不会产生完全相同的东西。

您实际上可以尝试并查看rake routes输出。

第一个选项意味着,模型Post与模型has_manyComment关联(Comment模型这里是{{1}的子项}})。

使用此选项,您可以查看和创建某些Post条评论。查看更多详情in docs

第一个选项会产生如下路线:

post

但在第二种选择中,你将没有这样的机会,因为路线是无关的。

这里生成的路线看起来像

/posts/:post_id/comments/comment_id

答案 1 :(得分:0)

查看有用的路线指南: http://guides.rubyonrails.org/routing.html#nested-resources

  

拥有逻辑上其他资源的子资源是很常见的。例如,假设您的应用程序包含以下模型:

class Magazine < ActiveRecord::Base      
  has_many :ads    
end     

class Ad < ActiveRecord::Base
  belongs_to :magazine    
end
  

嵌套路由允许您在路由中捕获此关系。在这种情况下,您可以包含此路由声明:

resources :magazines do
  resources :ads
end
  

除了杂志的路线之外,此声明还会将广告路由到AdsController。广告网址需要杂志

答案 2 :(得分:0)

查看RESTful architecture。如果您理解它,那么为什么要嵌套资源会更清楚。

正如名称所示,resources在某种程度上是数据库中的记录。例如Userscarstasks等等。但当然,你并不仅限于拥有其中一个。

然而,有时资源属于其他资源。例如,用户has many汽车或任务或其他任何东西。由于任务不属于另一个用户,我们将它们嵌套到用户的资源中。

resources :users do
    resources :cars
    resources :tasks
end

这是有道理的,因为至少这个应用程序的任务或汽车只属于一个用户。

你当然也可以嵌套不仅仅是一个级别。你可以这样做:

resources :users do
    resources :lists do
        resources :tasks do
            resources :likes    # The social task sheet :)
        end
    end
end

但这不是一个好习惯,因为它会创建长长的不可维护的URL,如下所示:

http://example.com/users/1/lists/124/tasks/25/likes/2124

这很难维持。

但是,如果你使用范围正确,它会带来巨大的优势,例如更好,更具可扩展性Authorization或更少的代码重复。

它对于不同的回答也非常方便。例如,如果您严格遵循CRUD,则控制器应该只有createreadupdatedestroy一种资源。这很有效,直到您想要其他功能。

例如,您有一个post资源。稍后您决定要添加like(资源)功能。您现在不应该将它们全部放入PostController,因为它只适用于posts负责人。你应该做一些像我上面提到的那样的事情:

resources :posts do
    resources :likes
end

现在您有一个PostsController负责posts和一个LikesController,负责帖子的likes。由于他们属于scope,所以给他们自己post是没有意义的。

我希望你为什么要嵌套资源更容易理解。