Reputation: 1083
I'd like this custom url helper to be accessible from controllers, views, tests... Ending with both _url and _path. Also it should have the possibility to add parameters at the end as a url helper.
def reviews(reviewable)
"/reviews/#{reviewable.class}/#{reviewable.id}"
end
reviews_url Book.find(1) # /reviews/Book/1
reviews_path Film.find(3) # /reviews/Film/3
Review.reviewable is polymorphic.
config/routes
get "reviews/:reviewable_type/:reviewable_id" => "reviews#index"
Upvotes: 1
Views: 1618
Reputation: 1083
Even though my question has been answered a long time ago, I want to add another answer according to the title of the question. So if you actually want to create custom url and path helpers, here's the answer with an example: Generating a full resourceful path giving only the last resource to the routes helper
Rails docs: https://api.rubyonrails.org/classes/ActionDispatch/Routing/Mapper/CustomUrls.html#method-i-direct
Upvotes: 0
Reputation: 101811
I would just define the routes as:
resources :books do
resources :reviews, only: [:new, :create, :index]
end
resources :films do
resources :reviews, only: [:new, :create, :index]
end
This will create the routes as:
books/:book_id/reviews
films/:film_id/reviews
This is the conventional RESTful way to define nested resources. And more importantly it works with the Rails polymorphic route helpers.
You can use routing concerns to DRY it if needed.
concern :reviewable do
resources :reviews, only: [:new, :create, :index]
end
resources :books, concerns: :reviewable
resources :films, concerns: :reviewable
It gives you the named route helpers book_reviews_path(@book)
and film_reviews_path(@film)
. You can also use the polymorphic route helpers:
<%= link_to "Reviews for #{@reviewable.title}" [@reviewable, :reviews] %>
...
<%= form_for([@reviewable, @reviewable.review.new]) do %>
...
redirect_to [@reviewable, :reviews], notice: 'Review created'
Upvotes: 4