0

I'm combining two models in my controller, and trying to print them in a similar fashion, but I'd like to do an if statement in an each loop to distinguish one model from the other. My models are comments and likes.

In the controller:

@items = (@user.likes + @user.comments).sort{|a,b| a.created_at <=> b.created_at }

In my view:

<%= @items.each do |item| %>
  <% item.name %>
<% end %>

I need an if statement to say IF comment or IF like in the each loop. I've been drawing a blank on the situation.

sawa
  • 165,429
  • 45
  • 277
  • 381
the_
  • 1,183
  • 2
  • 30
  • 61

3 Answers3

1

Assuming you have model Like and Comment

<%= @items.each do |item| %>
  <% if item.instance_of?(Like) %>
    Something for likes
  <% elsif item.instance_of?(Comment) %>
    Something for comments
  <% end %>
<% end %>
Yang
  • 1,915
  • 1
  • 9
  • 15
0

You could do item.class.name as Nithin mentioned, and it'll work fine. However, the more idiomatic way is to use instance_of?. So it'd look like this:

if item.instance_of?(Post)
  # do something
elsif item.instance_of?(User)
  # do something else
end

Note you're not passing in 'Post' or 'User' as strings - you're passing in the Ruby class constants themselves.

On this topic, it's also worth knowing about Ruby's is_a? and kind_of? methods which work similar to instance_of? but return true if the instance you're testing is an instance of a subclass of the parameter you pass in (more info at Ruby: kind_of? vs. instance_of? vs. is_a?).

Community
  • 1
  • 1
joshua.paling
  • 13,762
  • 4
  • 45
  • 60
0

What you need to do is to check for the class of the Item of interest.

Basically, each object belongs to a class, and the class name of a comment will be a Comment while that of a like will be a Like.

So, in the loop, check for the class name as:

<%= @items.each do |item| %>
  <% if item.class == Comment %>
    ...comments here
  <% elsif item.class == Like %>
    ...likes here
  <% end %>
<% end %>
x6iae
  • 4,074
  • 3
  • 29
  • 50