Andy Harvey
Andy Harvey

Reputation: 12653

How to perform if statements on associated has_many records in Rails

In a Rails 3.2 app I have a model Project, which has many Tasks. Each Task has a :status field, which is an integer as follows

1=Normal
2=Urgent

In the Project show view, I want to display a text alert if any of the associated tasks are flagged as urgent.

If the status field was within the Project model, I would do something like this:

<% if Project.status == 2 %>
   <div class="alert">URGENT TASKS!</div>
<% end %>

How can I set up a similar if statement, that will cycle through all associated Tasks, and return true if at least one task is marked as urgent?

I'm not sure what terms I should be searching on for this sort of functionality. Or maybe I'm not looking at the problem the right way. I'd be grateful for any pointers in the right direction.

Thanks

Upvotes: 1

Views: 109

Answers (2)

Kevin Hughes
Kevin Hughes

Reputation: 600

This method in Project will do it:

def urgent?
  tasks.detect{|t| t.status==2}
end

Then you can do, if you have @project set to the project you're looking at:

<% if @project.urgent? %>
  ...whatever ...
<% end %>

This next bit was added in answer to your comment. This method in Project will return the highest priority set (lowest number in your example) for any task in a particular project:

def highest_priority
  tasks.map{|t| t.status}.min
end

You can then switch between them in your view:

<% case @project.highest_priority
   when 1 %>
     ...priority 1 stuff...
<% when 2 %>
     ...priority 2 stuff...
<% when 3 %>
     ...and so on...
<% end %>

Upvotes: 3

cicloon
cicloon

Reputation: 1099

I guess that you want to check if a project has some urgent task to be completed. If thats the case I think the best way to achieve that would be to create new method in the Project model, something like this:

def has_urgent_task?
  tasks.map(&:status).include?(Task::URGENT) 
end

Assuming you have defined your statuses as constants in your Task model, if not just replace Task::URGENT for 2.

So in your view you only need to do this:

<% if @project.has_urgent_task? %>
  <div class="alert">URGENT TASKS!</div>
<% end %>

Upvotes: 0

Related Questions