RESTfully Nesting Resource Routes with Single Identifiers

前端 未结 4 1903
情话喂你
情话喂你 2021-02-06 04:47

In my Rails app I have a fairly standard has_many relationship between two entities. A Foo has zero or more Bars; a Bar belongs to exactly

相关标签:
4条回答
  • 2021-02-06 05:16

    As you already know, every item has to have a unique address. I would suggest that the shorter and easier the address is, the better for everyone involved - your routing code, your client apps, etc. If you can identify a Bar by its unique ID, I would probably specify only that in the URL.

    You don't need to lose the semantic information about the Bar's assignment to a Foo, though. That can be part of the representation.

    As an enhancement, you could allow the client to address Bar 200 as /foo/100/bar/200, but then redirect to the preferred /bar/200/ address, using, e.g., a 303 ("See Other") response.

    0 讨论(0)
  • 2021-02-06 05:16

    Personally, if each Bar is dependent on a Foo, option #2 makes more sense. For example, if Foo is a blog and Bar is a post, it is far more logical to access a particular post at example.bloghosting.com/blog/1/post/2 than example.bloghosting.com/post/21.

    Do do this with the latest version of Rails:

    class Food < ActiveRecord::Base
        has_many :bars
    end
    
    class Bar < ActiveRecord::Base
        belongs_to :foo
    end
    

    Then, in the Rails router (/config/routes.rb):

    map.resources :foos do |foo|
        foo.resource :bars
    end
    

    For more information, see Rails Routing from the Outside In and the Rails API Documentation.

    0 讨论(0)
  • 2021-02-06 05:18

    You're looking for shallow routes. As you pointed out, the idea of having a deeply nested route for things like creates, updates is unnecessary since you are targeting the desired record directly.

    I have never actually done the shallow routing thing so I'll pass on the railscast episode where Ryan Bates explains it probably better than I could: 139 Nested Resources.

    Edit: You can read up a little more on the guides for routing 3.8.4.

    0 讨论(0)
  • 2021-02-06 05:27

    Rails' shallow nesting gives us the best of both worlds: it lets us have Foo-specific routes where it makes sense (create, new, index) and Bar-only routes otherwise (show, edit, update, destroy).

    Unfortunately, the new routing DSL in Rails 3 (which I'm using) does not support shallow routing yet (as of Beta 3). It appears to be in the works but it's not functional for today.

    However, you can fake it by mapping the resource twice, once nested and once shallow:

    resources :foo do
      resources :bar, :only => [:index, :new, :create]    
    end
    resources :bar, :only => [:show, :edit, :update, :destroy]
    

    This will tide me over until the :shallow option is up and running again.

    0 讨论(0)
提交回复
热议问题