Ask A Question

Notifications

You’re not receiving notifications from this thread.

How do I structure a Conversation between two models?

Taylor Cooney asked in Rails

I have a Store object that has an email_address attribute. Using the logic from and How To Build A Form and Handling Inbound Email Parsing with Rails, I'm trying to figure out how to structure a Conversation where a visitor can email the Store, and the Store can reply through email - their replies would post messages to the Conversation.

When a visitor inquires to the store (via form), I create a Reservation record with their name and email, and start a Conversation like this,
@conversation = Conversation.create(sender_id: self.id, recipient_id: self.store_id)

I wanted to model the notifications similar to this, where everyone but the sender receives an email, but I'm stumped on how to map the User, since it's two different objects (Reservation and Store):

def send_notifications!
    (forum_thread.users.uniq - [user]).each do |user|
      UserMailer.new_post(user, self).deliver_now
    end
  end

The Conversation model looks like this, may be wrong, any guidance on what I could use to make the messages unique and structure the notifications?

class Conversation < ApplicationRecord
  belongs_to :sender, :foreign_key => :sender_id, class_name: "Reservation"
  belongs_to :recipient, :foreign_key => :recipient_id, class_name: "Store"
  belongs_to :reservation

  has_many :messages, dependent: :destroy
end

The Message Post isn't fully fleshed out, not sure what to use to make it unique between the two Objects.

class Message < ApplicationRecord
  belongs_to :conversation
  validates_presence_of :body, :conversation_id

  def send_notifications!

  end
end
Reply

Talor, would you mind posting the message model as well?

Reply

Just updated the bottom of the thread Casey; needing some guidance on setting up the Conversation and Message between two different models.

Reply

My assumption: A conversation is only between 2 people

So I think one thing that would make this easier to by putter an author_id on a message. This way you know who composed and sent the message. If you do this then you can just send a notification on the after_create callback of the Message model. In that callback I would do something like.

def after_create
  UserMailer.new_message(self.id).deliver_later
end

class UserMailer
  def new_message(message_id)
        message = Message.includes(conversation: [:sender, :recipient]).find(message_id)
        recipient = message.conversation.sender_id == message.author_id ? message.conversation.recipient : message.conversation.sender
        mail(to: recipient.email)
    end
end
Reply

What does your code like that receives and parses the email?

Reply

I haven't written the portion to parse the email and create the post, but I planned to model it around the logic here, Handling Inbound Email Parsing with Rails

Reply

I didn't realize I could access conversation.recipient and conversation.sender so easily, going to try to model it as you suggested above Casey :thumbs_up:

Reply
Join the discussion
Create an account Log in

Want to stay up-to-date with Ruby on Rails?

Join 81,842+ developers who get early access to new tutorials, screencasts, articles, and more.

    We care about the protection of your data. Read our Privacy Policy.

    Screencast tutorials to help you learn Ruby on Rails, Javascript, Hotwire, Turbo, Stimulus.js, PostgreSQL, MySQL, Ubuntu, and more.

    © 2024 GoRails, LLC. All rights reserved.