Iterating over a has_many collection within a named_scope
Here are my models:
class Message < ActiveRecord::Base
has_many :comments
attr_accessible :read #bool
def unread_comments?
comments.each { |comment| return true unless comment.read?}
false
end
end
class Comment < ActiveRecord::Base
belongs_to :message
attr_accessible :read #bool
end
Here is what I am looking to do: I'd like to c开发者_如何学Goreate a named_scope in Message, called unread
that basically returns true if any of the message's comments are unread or the message itself is unread. Is there a way I can do this?
class Message < AR::Base
...
def unread?
!self.read && !self.comments.all?(&:read)
end
end
How about this:
named_scope :unread, :conditions => ['messages.read = ? OR comments.read = ?',
false, false],
:include => :comments
Why the named scope? You could just do
def has_unread
!self.read || unread_comments?
end
or, if it needs to be a class method
def self.has_unread(message)
msg = Message.find(message.id)
msg.read == false && msg.unread_comments?
end
Is you really do want to use named scopes though, you'll want something like this:
scope :get_unreads, lambda {|message|
{ :joins => :comments,
:conditions => {:comments => {:message_id => message.id}, :message => ['read',0]},
:select => "DISTINCT `clients`.*" # kill duplicates
}
}
def self.has_unread?(message)
self.get_unreads(message).exists? && self.find(message.id).read
end
精彩评论