ruby-on-rails - 一个用户的关联记录为零,但另一用户的关联记录为零
问题描述
我在两个用户之间运行了一个简单的消息传递系统。创建 a 的用户conversation
获得我可以通过 访问的记录User.find(sender_id).conversation.last
,但是如果我尝试访问,收件人将获得 => nil User.find(recipient_id).conversation.last
(我用实际 ID 替换了收件人 ID 和发件人 ID)。
但是,两个用户都会收到与对话相关的消息并且可以聊天。我正在根据Medium 上的 Dana Mulder的教程使用外键。我认为这很奇怪,因为我希望两个用户(接收者和发送者)都应该能够访问他们正在进行的对话的记录。有没有办法做到这一点?
我的模型:
用户.rb
has_many :conversations, :foreign_key => :sender_id, dependent: :destroy
has_many :messages, through: :conversations
对话.rb
belongs_to :sender, :foreign_key => :sender_id, class_name: 'User'
belongs_to :recipient, :foreign_key => :recipient_id, class_name: 'User'
has_many :messages, dependent: :destroy
消息.rb
belongs_to :conversation
belongs_to :user
对话控制器:
conversations_controller.rb
def create
if Conversation.between(params[:sender_id],params[:recipient_id]).present?
@conversation = Conversation.between(params[:sender_id], params[:recipient_id]).first
else
@conversation = Conversation.create!(conversation_params)
end
redirect_to conversation_messages_path(@conversation)
end
你知道如何让两个用户都能访问对话吗?(它是可访问的,但不是我需要的方式)。
提前致谢!
解决方案
您与对话的用户关联只是在寻找sender_id
has_many :conversations, :foreign_key => :sender_id, dependent: :destroy
接收用户正在寻找他的 id assender_id
而不是 as的对话recipient_id
。
我认为你可以通过在用户和对话之间添加一个连接模型而不是只属于发件人和收件人的对话来解决这个问题(尽管你应该保存这些引用)。
就像是
class ConversationsUsers < ....
belongs_to :user
belongs_to :conversation
end
class User < ...
has_many :conversations_users
has_many :conversations, through: :conversations_users
has_many :started_conversations, class_name: 'Conversation', foreign_key: :sender_id
has_many :received_conversations, class_name: 'Conversation', foreign_key: :recipient_id
end
class Conversation < ...
has_many :convesations_users
end
对于每个对话,您将在 conversations_users 表上有两条记录,每个用户都有一条记录。现在,两个用户都可以查询所有对话,无论是发件人还是收件人(如果您打算扩展对话,您也可以有任意数量的参与者!)。
但是,您必须手动创建一些记录,在创建 Conversation 之后,您可以有一个 after 回调来为每个用户创建两个 conversation_user 对象。
另一种选择是只使用一种方法
def conversations
Conversation.where(sender_id: id).or(Conversation.where(recipient_id: id))
end
但您将无法使用连接/包含/等。
编辑:要获取所有消息,请添加另一种方法:
def messages
conv_ids = conversations.pluck(:id)
Message.where(conversation_id: conv_ids)
end
然后你可以这样来获取所有已读消息,例如
current_user.messages.where(read: true)
推荐阅读
- python - Python Flask 没有从 SQLAlchemy 数据库中删除具有给定帖子标题的正确帖子
- php - 在 Prestashop 模块中注册钩子
- python - 不和谐中特定角色的用户列表(Python)
- entity-framework-core - 将扩展类存储在不同的表中
- java - Vaadin Java:css文件的导入问题
- c - 人类可读的结构 cpuinfo_x86 内核 Linux
- javascript - HTML菜单的Javascript
- list - 在 Haskell 中使用语法糖检查集合中的所有元素
- c# - 如何使用彼此的方法处理两个类?
- c# - LINQ GroupBy 一个名称,但如何获取用户 ID?