我正在使用Ionic / Angular和Firebase构建实时信使。我使用Firebase身份验证来验证我的用户,使用Firebase DB来存储邮件和邮件线程。
我的问题是我应该使用什么安全规则才能使消息线程变得私有且可行,并且只能写入参与给定消息线程的2个人。
我的数据库结构现在看起来像这样:
-chats
--Message_thread_ID
---Unique_ID_generated_message by Firebase
----Message
----Sender ID
----Receiver ID
---Unique_ID_generated_message by Firebase
----Message
----Sender ID
----Receiver ID
--Message_thread_ID
---Unique_ID_generated_message by Firebase
----Message
----Sender ID
----Receiver ID
我目前的firebase安全规则是:
{
"rules": {
".read": "auth != null",
".write": false,
"$messageThreadID": {
".write": "auth != null && !data.exists()",
".read": "auth != null"
}
}
}
这样可以正常工作,但这样任何经过身份验证的用户都可以读取任何用户之间的所有消息。这不是我想要的。我想将消息线程专用于任何给定线程中的两个用户。
我应该如何重构我的数据库以获得最佳解决方案?
PS:我有办法使用后端,或为各自线程的两个用户中的每一个制作两个副本,但这些解决方案看起来非常次级。
答案 0 :(得分:1)
您当前的数据模型仅存储聊天消息。它还没有存储谁是每个聊天的参与者。或者......它确实将它存储在消息本身中,但这并不足以使您的安全规则能够读取它。
因此,第一步是向模型添加有关谁是其成员的数据:
members
Message_thread_ID1
member_uid_1: true
member_uid_2: true
Message_thread_ID2
member_uid_1: true
member_uid_3: true
现在我们拥有更新安全规则所需的所有信息。
{
"rules": {
".read": "auth != null",
".write": false,
"$messageThreadID": {
".write": "root.child('members').child($messageThreadID).child(auth.uid).exists()",
}
}
}
现在,如果用户是该线程的成员,则用户只能写入消息线程。
对于应用的各种用例,您通常最终会得到多个此类查找列表。例如,您可能希望在用户登录时显示消息线程列表。为了有效地执行此操作,您可能会为每个用户添加一个"消息线程列表&#34 ;,这几乎与上面members
列表相反:
threads_per_user
member_uid_1: true
Message_thread_ID1
Message_thread_ID2
member_uid_2: true
Message_thread_ID1
member_uid_3: true
Message_thread_ID2
对于来自关系/ SQL背景的开发人员来说,这种数据结构最初感觉非常不自然,但在NoSQL数据库中实际上很常见。
了解更多信息: