Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Two controllers for one shared view in Ruby on Rails

I have two controllers for two respective models, by example, photos and categories. index and show methods are very similar in each controller, and the views are identical. What is the best method for share the view by the two models?

I've though two options:

  • Use a helper. In the helper will put the code for the view, and will call the helper from each view (photos/views and categories/views)

  • Use a partial in each views. I think it's a more clean solution, but I see huge DRY's in my mind when going to code this solution.

So, I have two controllers from two models, each one at and exposes a @photo object (photos controller with all the photos, and categories controller with just the selected categorie's photos) and I need one view to show both.

I'm looking for an elegant solution for this, complaining REST and DRY principes. Any idea?

Thanks in advance.

like image 406
ARemesal Avatar asked Jan 23 '09 13:01

ARemesal


4 Answers

I have a similar situation with one of my projects. All the delete views for most controllers are styled the same way, display the same confirmation boxes, and simply renders a predictable display of whatever object is being deleted.

The solution was quite simple and elegant in my opinion. Simply put, what we (the developers) did was create a new directory in app/views called shared and put shared views in there. These could be full template files or just partials.

I would suggest using a shared template (in neither categories nor photos view directories, but rather in the shared directory) and rendering it manually from the view.

e.g. have a method as such in both controllers and a file app/views/shared/photo.html.erb:

def show
  @photo = Photo.first # ... or whatever here
  render :template => 'shared/photo'
end

This should successfully render the shared template. It is the DRYest route and doesn't have the feeling of pollution you get when using a more-or-less empty view in each controller's view directory just to include a shared partial, as I understand your question is suggesting.

like image 143
Bo Jeanes Avatar answered Nov 12 '22 08:11

Bo Jeanes


About the first answer:

If the partial must be rendered from a view:

<%= render :partial => "shared/photo" %>

and the partial must be in app/views/shared/_photo.html.erb

like image 40
Rodrigo Avatar answered Nov 12 '22 10:11

Rodrigo


I'd use an helper because they are shared among views. For the HTML part, I'd use partials so it would be a mix of both ways.

like image 1
Keltia Avatar answered Nov 12 '22 09:11

Keltia


This looks like a good use case for the Cells gem.

like image 1
Marnen Laibow-Koser Avatar answered Nov 12 '22 10:11

Marnen Laibow-Koser