Take the 2-minute tour ×

Every show action in my app has the same template for every model (it is an Admin-portal type interface). I have a view show.html.erb that all of these models inherit.

The controllers all use InheritedResources, so I have access to some helper variables such as resource, which I use to display the attributes for the model being shown through resource.attributes in my parent view.

What I would like to be able to do is whitelist which attributes are being shown in each model. I have thought of two ways to do this... the first is to define some method in a class my model's inherit from, say it is called attr_visible and define each attribute in the model. The reason I don't like this approach is that it puts too much of the view logic in the models. I would rather provide my views with the model, and let the view determine what is displayed.

The second approach is what this question is about. I want to have a file /app/views/users/show.html.erb, and set which attributes for a User I would like to be shown, say something like:

@attributes = [:name, :email, :etc]

And then pass them to the parent view which I described in the beginning of this question. That view would then be able to loop through @attributes and display the attributes necessary.

Is it possible to use a "super"-type method from views? Everything I have read about view inheritance suggests the view is loaded based on where it is located in the directory structure, and then after that you're out of luck.

edit: I have sort of done what I want. I defined a partial _show.html.erb in the /app/views/users directory that looks like:

<% @attributes = ['name', ...] %>

And then in the parent view I call <%= render "show" %> before looping through @attributes. This works, but feels clunky since I am not actually rendering anything when I call render. Is there a better way?

share|improve this question
add comment

1 Answer

up vote 0 down vote accepted

You can use a presenter for this. Adding "view" logic to a model is better done through this type of object. Take a look at draper.

Once the resource is decorated, you can just call visible_attributes or whatever. Of course, you would need to implement that method for each resource.

Views inheritance works when looking for a view, not when rendering it. Take a look at the original plugin implementation.

Other way would be to make the show parent view to call render on resource and create several partials for the classes.

For a better understanding on Rails Views, I recommend The Rails View: Create a Beautiful and Maintainable User Experience

share|improve this answer
add comment

Your Answer


