Guidance on organizing routes - ruby-on-rails

I am working on this project that has products and under products I have cars and trucks and each have comments and the ability to vote on both the car model and comments. The car models all work correctly but the trucks model does not have the correct routes. I am thinking it has something to do with having comments shallow, but honestly, I am not sure what I am doing wrong. Any guidance would be appreciated.
resources :products do
resources :cars do
member { post :vote }
resources :car_comments, shallow: true do
member { post :vote }
end
end
resources :trucks do
member { post :vote }
resources :truck_comments, shallow: true do
member { post :vote }
end
end
end
UPDATE
After looking over one of the controller files, I found the error and now the routes work as expected. However, I still feel that my routes look clunky, and since there will be more models, boats, tractors, etc, I dont think the way the routes are written now will hold up.

I believe it is because you are using resources :trucks, when you use the resouces it calls the CRUD methods. if you want certain routes you need to specify them, for example: resources :trucks, only: [:create, :destroy]

Related

rails routing member and non-member nesting

Two quite similar routing settings really is confusing.
resources :authors do
resources :books
end
and
resources :authors do
member do
resources :books
end
end
As we all know, rails will generate the following routings :
writer_book GET /writers/:writer_id/books/:id(.:format) books#show
and
book GET /writers/:id/books/:id(.:format) books#show
How is this member option useful?
One can just not using member option and set params[:writer_id] in books_controller and be done with it right?
Does this will have a bad affect when the application gets bigger? What are the consequences?
The member and collection methods are meant to add additional RESTful actions to resources
resources :writers do
member do
post :favorite
end
collection do
get :unpublished
end
end
They are not intended for nesting resources
# bad
resources :writers do
member do
resources :books
end
end
# good
resources :writers do
resources :books
end
What are the consequences?
Using member here will result in the route
GET /writers/:id/books/:id(.:format)
Which means that the id param is ambigous! It could be either the id of the book or the author! Not good! Not using member would give us params[:writer_id] which we can use to fetch the parent record.
GET /writers/:writer_id/books/:id(.:format) books#show
See:
Rails Routing from the Outside In

rails - Best practice for creating similar routes?

In my application, a User can make a Post, and a User can make Correction (think of it as a comment) on another user's post. Each User can have many Posts, and each Post can have many Corrections.
On each show page for a Post, there is a form to create a new Correction. This uses the user_post_corrections path.
On the show page for each User, I would like to display each Correction they've submitted for any Post. This requires a user_corrections path.
In order to achieve this, I have the following in my routes.rb:
resources :users do
resources :posts do
resources :corrections
end
end
resources :users do
resources :corrections
end
This intuitively feels bad to me, as I've created two nested routes that are very similar to one another.
Is there a better way to do this? My code is working fine as it is but is there a best practice method for implementing this kind of model?
Routing concerns are an excellent but underused tool for DRYing out your routes:
concern :correctable do
resources :corrections
end
# just an example of multiple concerns
concern :commentable do
resources :comments
end
resources :users, concerns: :correctable
resources :posts, concerns: [:correctable, :commentable]
However you should take when creating nested routes so that you are not nesting needlessly.
Often you might want the collective actions [new, index, create] to be scoped by the parent:
GET|POST /posts/:post_id/corrections
GET /posts/:post_id/corrections/new
While you want the member actions to be unscoped since you can always access a record directly if it has a unique id.
GET /corrections/:id
GET /corrections/:id/edit
PATCH /corrections/:id
DELETE /corrections/:id
To do this you would declare the routes like so:
resources :corrections, only: [:show, :update, :edit]
concern :correctable do
resources :corrections, only: [:new, :index, :create]
end
resources :users, :posts, concerns: [:correctable]
The shallow: true option does something like this but does not work well when you declare the same resources several times as it adds unscoped routes for every call.

How can code duplication be avoided in Rails routes?

I have many resources in routes.rb where many few resources are used and repeated.
Is there a way to avoid code duplication?
resources :pages do
resources :comments
##other routes
member { post :vote }
end
resources :videos do
resources :comments
##other routes
member { post :vote }
end
resources :images do
resources :comments
##other routes
member { post :vote }
end
You can organize your routes file so as to keep it from becoming a massive, unmanageable mess. But, it's not via Concerns ... it's actually more "basic" than that. Just break up the files and include them in the main routes file :).
I read a good post on this a while back: splitting routes,rb into smaller parts
Hope it helps.
I've used procs for this myself. Then I just call it in each namespace or resource block where I need it.
But concerns are likely a better and more readable solution.

Polymorphic routes pointed to same controller and action

This is a polymorphic association!
resources :professors, :labs do
member do
resources :teaching_assistants
end
end
I want to have index for professors teaching assistants, labs teaching assistants and teaching assistants like so:
/professors/id/teaching_assistants
/labs/id/teaching_assistants
/teaching_assistants
All these routes are pointing to
teaching_assistants#index. Do i have to explicitly point the nested routes to an action in in the professors and labs controller? How would I do that/alter the routes file?
resources :professors, :labs do
member do
resources :teaching_assistants, except: :index
end
end
get '/professors/id/teaching_assistants' => professors#assistantsindex
get '/labs/id/teaching_assistants' => labs#assistantsindex
Using resources is for creating all the basic RESTful pointers (index/create/read/update/delete). It sounds like your teaching assistants are a 'one off' listing page, in which case you would simply use get to create the route.
Try this:
resources :professors, :labs do
member do
# /professors/id/teaching_assistants > professors#teaching_assistants
# /labs/id/teaching_assistants > labs#teaching_assistants
get 'teaching_assistants'
end
end
# /teaching_assistants
get 'teaching_assistants'

How to route to a nested resource whilst not routing to the outer parent resource?

Given the following code:
resources :subjects do
resources :partipicants
end
I want to route /subjects/x/partipicants etc
But I do not want to route /subjects etc. (i.e. the regular outer resource).
Anyone know how to pull this off cleanly?
Jack
You can try this:
resources :subjects, :only => [] do
resources :partipicants
end

Resources