无法修复 Firebase 安全规则

问题描述 投票:0回答:1

我有一个简单的应用程序,用户 A 可以向另一个用户 B 发送通知(聊天、点赞、评论),显然,用户 B 可以接收和阅读这些通知。

我的 firestore 数据库集合如下所示:

/Notifications/{userId}/NotificationItems/{notificationId}

其中

Notifications
NotificationItems
是集合,
userId
是接收通知的用户的 if。
notificationId
是一个文档,其中包含有关通知的信息。

我的集合结构对我来说似乎很合理,所以最初我的 Firestore 规则是这样的:

match /Notifications/{userId}{
      match /NotificationItems/{notificationId} {
         allow create: if isUserAuthenticated();
         allow read: if isUserAuthenticated() && userOwnsResource(userId);
         allow update: if isUserAuthenticated() && userOwnsResource(userId);
      }
    }

其中函数

userAuthenticated
userOwnsResource
如下:

function isUserAuthenticated() {
      return request.auth.uid != null;
    }

    function userOwnsResource(userId) {
      return request.auth.uid == userId;
    }

这些功能已经足够好了,我可以获取通知、发送通知、将其显示为可见等。

问题是我是否想发送

chat
通知类型。如果我想发送聊天通知,首先,我想检查我之前是否发送过聊天通知。如果我过早发送聊天通知,我不会发送新的通知。我拨打的 Firestore 电话:

await firebase
    .firestore()
    .collection("Notifications")
    .doc(userId)      //I dont have access to this user notifications as per the above rules
    .collection("NotificationItems")
    .where("chatId", "==", chatId)
    .orderBy("date", "desc")
    .get()

显然,这个调用失败了。我想通过实现一些功能来修复它,例如:

function itIsChatNotification(){
                let chatId =  get(/databases/$(database)/documents/Notifications/$(userId)/NotificationItems/$(notificationId)).data.chatId;
            return request.auth.uid in get(/databases/$(database)/documents/Chats/$(chatId)).data.users;
         }

即检查是否是聊天通知类型,获取该通知的chatId,然后检查该用户ID是否属于创建该聊天的用户。

然后将我的

read
访问权限更改为
allow read: if isUserAuthenticated() && (userOwnsResource(userId) || itIsChatNotification());

不用说,上面的功能不起作用,我不知道为什么。

我的聊天通知类型包含

authorId
body
type
(等于
chat
)、
chatId
date
字段。

如果有人可以帮助编写正确的 Firestore 规则,那就太好了!

google-cloud-firestore firebase-security
1个回答
0
投票

试试这个

   match /Notifications/{userId}{
  match /NotificationItems/{notificationId} {
    allow create: if isUserAuthenticated();
    allow read: if isUserAuthenticated() && (userOwnsResource(userId) || itIsChatNotification());
    allow update: if isUserAuthenticated() && userOwnsResource(userId);
  }
}

function isUserAuthenticated() {
  return request.auth.uid != null;
}

function userOwnsResource(userId) {
  return request.auth.uid == userId;
}

function itIsChatNotification() {
  let chatId = resource.data.chatId;
  let chatRef = /databases/$(database)/documents/Chats/$(chatId);
  let chatDoc = get(chatRef).data;
  return request.auth.uid in chatDoc.users;
}
最新问题
© www.soinside.com 2019 - 2025. All rights reserved.