mailboxer / mailboxer

A Rails gem to send messages inside a web application
MIT License
1.65k stars 461 forks source link

Finding users with unread receipts #273

Open frankjwu opened 10 years ago

frankjwu commented 10 years ago

I'm trying to do something like the following:

users = User.joins(:mailboxer_receipts).where(mailboxer_receipts: {is_read: false})

but this returns the error: Association named 'mailboxer_receipts' was not found on User even though User acts_as_messageable. What is the correct way to do this?

Here's the solution I came up with, but I was wondering if there was a more standard mailboxer way to achieve the same. Thanks!

def self.users_with_unread_notifications
    unread = Mailboxer::Receipt.all.where(:is_read => false)
    unread.map {|r| r.receiver_id }
        .uniq
        .map { |n| User.find(n) }
end
w3irdrobot commented 10 years ago

The receipt association is just called receipts. So try:

users = User.joins(:receipts).where(mailboxer_receipts: {is_read: false})
frankjwu commented 10 years ago

Hey Alex (@searsaw), thanks for getting back to me. Here's what I see in my console:

PG::UndefinedTable: ERROR:  missing FROM-clause entry for table "mailboxer_receipts"
LINE 1: ...pts" ON "receipts"."user_id" = "users"."id" WHERE "mailboxer...
ActiveRecord::StatementInvalid: PG::UndefinedTable: ERROR:  missing FROM-clause entry for table "mailboxer_receipts"
LINE 1: ...pts" ON "receipts"."user_id" = "users"."id" WHERE "mailboxer...
w3irdrobot commented 10 years ago

@frankjwu it looks like I may have told you slightly wrong in the code I gave you. According to StackOverflow, in the where clause, we need to define the hash key as the association name, not the table name. With that in mind, give the code below a shot. Hopefully that will get rid of the error.

user = User.joins(:receipts).where(receipts: { is_read: false })
frankjwu commented 10 years ago

Ah, I think I found the problem. I have another model and table named Receipts. The hash key in the where clause then maps to this model, instead of the Mailboxer::Receipts model.

This seems like a pretty unique problem, but I'm stuck. Any ideas?

w3irdrobot commented 10 years ago

The call to joins maps to an association. In this case, the user has a receipts association, which maps to Mailboxer::Receipt and the mailboxer_receipts table. If you already have an association on the user name receipts, then I would just rename your association and then map that association to your Receipts class. So something like:

class User < ActiveRecord::Base
  has_many :stubs, class_name: 'Receipt'
end