I plan to implement a private message system between members. I'm wondering what are the preferred approaches to this.
Requirements are
I should be able to retrieve them easily as something like this
@user.conversations #Should return User objects that I sent or received messages from (but not me)
@user.conversations.messages #Messages from all or specific user objects.
@user.conversations.messages.unread #Unread messages
When calling @user.conversations should retrieve only the people that sent me messages or people I send messages to. current_user should be excluded.
If i'm sender_id=5 and send to_id=10 then, the other person would reply as sender=10 to_id=5. This should be considered and understood as the same conversation object.
Regarding last point. I'm not sure what's the preferred approach to modeling.
It's preferred to use one Conversation model to handle all messages such as
attr_accessible :user_id, :friend_id, :message, :read
belongs_to :user
Or it's preferred to create a Conversation model to handle association and a Message model for messages.
I would like to see sample cases of how to implement this relationship and if there's additional method to implement.
I'm a bit lost here.
A much simpler model is to capture each Message:
class Message < ActiveRecord::Base
belongs_to :from_user, :class_name => 'User' # from_user_id field fk Users
belongs_to :to_user, :class_name => 'User' # to_user_id field fk Users
belongs_to :thread, :class_name => 'Message' # Reference to parent message
has_many :replies, :class_name => 'Message', :foreign_key => 'thread_id'
named_scope :in_reply_to, lambda { |message| :conditions => {:thread => message}, :order => 'created_at' }
end
class User < ActiveRecord::Base
has_many :messages_received, :class_name => 'Message', :foreign_key=> 'to_user_id'
has_many :messages_sent, :class_name => 'Message', :foreign_key=> 'from_user_id'
end
If you need to capture the message threads, any Message that's a reply can store a reference to the initial message starting the Conversation (aka Thread). For example:
first_msg = Message.new(:to_user => bob, :from_user => sally, :body => 'Hello!')
sally_reply = first_msg.replies.build(:to_user => bob, :from_user => sally, :body => 'hi back')
bob_reply = first_msg.replies.build(:to_user => sally, :from_user => bob, :body => 'later')
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With