Rails:记录未读通知的用户数



我目前有一个处理用户活动通知系统的活动模型。活动观察器在某个操作发生时创建一个新的活动(例如正在创建的新文章)。现在我想记录下当前用户有多少没有看到的活动通知(类似于facebook上的通知宝石)。每次用户单击其通知链接时,数字都应重置为0,创建的每个通知都应将计数增加1。我将把每个用户的数据存储在哪里?使用会话有效吗?还是其他方法更好?

有两种可能的方法:规范化和非规范化。我将从规范化开始:

方法1:标准化

听起来这里有三个模型:活动、通知("user_activities")和用户。如果我在这里的假设是错误的,请纠正我:

  • 活动belongs_to:user和has_many:notifications(一个用户执行一个活动,多个用户收到该活动的通知)
  • 通知belongs_to:activity和belongs_to:user,并具有"读取"属性/标志
  • 用户拥有(_Mny):通知

在活动的after_create回调中,模型应该确定哪些用户需要该活动的通知,然后通过为每个用户创建通知对象来通知他们。

在通知中,您可以创建一个名为read的类方法,该方法指定活动的read标志为false的条件:

def self.unread
where(:read => false)
end

然后,要访问用户的未读通知计数,只需调用:

user.notifications.unread.count

当用户查看他的通知时,调用:

user.notifications.unread.update_all(:read => true)

方法2:非规范化

在这种方法中,无论何时创建活动,都应该为每个通知的用户手动增加一个计数器。您可以通过以下任一方式实现:

  • 用户的"unseen_count"属性
  • 非关系数据库中的键值对(例如redis)

活动中:

def users_to_notify
# Find a list of users to notify
end
def notify_users(users)
users.each &:notify
end
def after_create
notify_users(users_to_notify)
end

用户内:

def notify
update_attributes(:unseen_count => unseen_count + 1)
end
def see_activities
update_attributes(:unseen_count => 0)
end

这种方法的缺点是取消了通知模型,因此用户只能获得通知的原始计数,无法查看通知及其相关活动的详细列表。您可以使用混合方法,但请记住,对于看不见的通知计数,处理两个真相来源是有风险的。

顺便说一句:在观察者中调用notify_users可能更有意义,而不是直接在模型上调用after_create:

class ActivityObserver < ActiveRecord::Observer
def after_create(activity)
activity.users_to_notify.each &:notify
end
end

如果使用观察者,则可以删除"活动#notify_users"one_answers"活动#after_create"。

请看一下这个宝石:
https://github.com/ledermann/unread

它由我编写,并以更高性能的方式处理任何ActiveRecord对象的已读/未读状态。

最新更新