简体   繁体   中英

Notification associations - what's the right way to do it?

I have a Rails 3.2 application with a user model. I want to add a notification mechanism that can be triggered by the following use cases:

  • Liking someone's profile
  • Commenting on someone's profile
  • Following someone

In all cases, one user generates a notification by his behavior that the other user will receive. So, there is a sender and a recipient of notifications.

I am now pondering how to structure my associations. So far, my models looks like the following:

Notification.rb

attr_accessible :content, :read_at, :recipient_id, :sender_id

belongs_to :sender,     class: :user
belongs_to :recipient,  class: :user

User.rb

has_many :notifications, as: :recipient, dependent: :destroy, foreign_key: :recipient_id
has_many :notifications, as: :sender, dependent: :destroy, foreign_key: :sender_id

This pseudocode shall only help understand what I need - what confuses me a lot is that I refer to the user model twice inside the notification model, and that a user has many notifications in two different ways.

So, my questions are:

  • How would you adjust the above associations?
  • What would you call them?
  • How will I be able to call all sent notifications and all received notifications on a user model without having to write scopes?
  • Is it the right approach at all, or should I use a join table somewhere two avoid referencing the user twice?

Thanks!

Solution

To put Shane's solution into words, this is what the models have to look like. It was really much easier than I thought. I assumed I would have to do some magic here - but Rails tricked me again with its stunning simplicity! Well, that's why I like it so much.

Thanks a lot, Shane!

Notification.rb

attr_accessible :content, :read_at, :recipient, :recipient_id, :sender, :sender_id

belongs_to :sender, class_name: "User"
belongs_to :recipient, class_name: "User"

User.rb

has_many :received_notifications, class_name: "Notification", foreign_key: "recipient_id", dependent: :destroy
has_many :sent_notifications, class_name: "Notification", foreign_key: "sender_id", dependent: :destroy

This is completely normal. Here is example of the same pattern used in a Redmine, a popular open source app:

https://github.com/edavis10/redmine/blob/master/app/models/workflow_rule.rb#L23-L24

As for needing a method that gets both sent and received notifications, the answer here works well for basic needs.

Rails Model has_many with multiple foreign_keys

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM