Firebase规则验证不会验证数据 [英] Firebase rules validation does not validate data

查看:161
本文介绍了Firebase规则验证不会验证数据的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

继续我的 上一个问题 我的应用程式有以下设计。

设计


  • 可以登录到应用程序的用户

  • 登录用户可以创建将存储在节点
    下的客户,其值将是当前登录的用户标识符



以下是我通过android应用程序添加数据的方式。 $ b

  FirebaseInstance mFirebaseInstance = FirebaseDatabase.getInstance(); 
FirebaseDatabase mFirebaseDatabase = mFirebaseInstance.getReference(tbl-customers)。child(FirebaseAuth.getInstance()。getCurrentUser()。getUid());
//这将在tbl-customers下创建或获取用户ID节点。

btnSave.setOnClickListener(new View.OnClickListener(){
@Override
public void onClick(View view){
String name = inputName.getText()。 toString();
String email = inputCode.getText()。toString();
String limit = inputLimit.getText()。toString(); $ b $ createUser(name,email,limit) ;
}
});

$ b private void createUser(String name,String email,String limit){
userId = mFirebaseDatabase.push()。getKey();
客户客户=新客户(姓名,电子邮件,限额);

mFirebaseDatabase.child(userId).setValue(customer);





就是这样..在数据库中它是以某种方式表示如下:

  tbl-customers 
| ___ loggedInUserId1
| ___ customerID1
| ___ customerName
| ___ customerCode
| ___ customerLimit
| ___ customerID2
| ___ customerName
| ___ customerCode
| ___ customerLimit
| ___ customerID3
| ___ customerName
| ___ customerCode
| ___ customerLimit
| ___ loggedInUserId2
| ___ customerID4
| ___ customerName
| ___ customerCode
| ___ customerLimit

我定义的规则为

$ p $ {
rules: {
tbl-customers:{
.read:auth!= null,
.write:auth!= null,
$ custId:{
customerName:{
.validate:newDat a.isString()&& newData.val()。length< 100& newData.val()。length> 8

customerCode:{
.validate:newData.isString()&& newData.val()。length< 4&& !newData.exists()&& newData.val()。length> 1

customerLimit:{}
}
}
}
}

不幸的是,插入的数据没有考虑为每个属性写的任何验证。插入



我开始考虑写规则是否是正确的结构,因为如果我看到插入的数据,它有3个级别 - tbl-customer - > loggedInUserId - > customerId 但是规则只写为 tbl-customer - > customerId
$ b 所以我改变了规则如下。



< pre $ {
rules:{
tbl-customers:{
.read:auth!= null,
.write:auth!= null,
$ user_id:{
.validate:auth.uid === $ user_id,
$ custId:{
customerName:{
.validate:newData.isString()&& newData.val()。length< 100
},
customerCode:{
.validate:newData.isString()&& newData.val()。length< 4&& !newData.exists()

customerLimit:{}
}
}

}
}
}

通过包括

 $ user_id:{
.validate:auth.uid === $ user_id
...
}

但现在抛出权限被拒绝异常在这个时候出了点想法,有人能指导我正确的方向吗?我从前面的问题提到很多帖子,但是对于我的不好,我不能从中得到很多信息,希望能找到一些清楚的解释为什么规则验证失败,为什么数据插入与上述第一条规则。

解决方案

我可能在这里是错的,但.read和.write规则将永远级联你的树,不管这里,.write:auth!= null 是最有可能的地方,你面临的问题。

最好把这个规则移动到.validate:auth.uid === $ user_id规则是,并删除验证规则。然后你会改变它像auth.uid == $ user_id。我相信验证规则只是在特定位置接受书面输入,然后接受或拒绝。



我相信这应该是这样的: / b>

  {
rules:{
tbl-customers:{
阅读:auth!= null
$ user_id:{
.write:auth.uid === $ user_id
$ custId:{
customerName:{$ b $.validate:newData.isString()& newData.val()。length< 100
},
customerCode :$ b $.validate:newData.isString()& newData.val()。length< 4&&!newData.exists()
},
customerLimit:{}
}
}

}
}
}

这个结构将允许所有记录在用户读取数据,如果你愿意,你可以进一步限制到$ user_id位置,类似于当前的写入规则。这将只允许匹配$ user_id读写权限的用户。



案例研究



为了补充说明,这是我之前设置的一个结构,它允许管理员添加用户:

 rules:{
Administrator:{
.read:auth!= null
},
Users :{
$ user_id:{
.write:$ user_id === auth.uid,
.read:$ user_id === auth。 uid

}
}
}


In continuation to my previous question I have below design for my application.

Design

  • A user who can login to the application
  • Logged in user can create customers which will be stored under node whose value will be the current logged in userid

Here is how I add the data through my android application.

FirebaseInstance mFirebaseInstance = FirebaseDatabase.getInstance();
FirebaseDatabase mFirebaseDatabase = mFirebaseInstance.getReference("tbl-customers").child(FirebaseAuth.getInstance().getCurrentUser().getUid());
//This will create or fetch user id node under tbl-customers.

btnSave.setOnClickListener(new View.OnClickListener() {
       @Override
       public void onClick(View view) {
            String name = inputName.getText().toString();
            String email = inputCode.getText().toString();
            String limit= inputLimit.getText().toString();
            createUser(name, email,limit);
       }
});


private void createUser(String name, String email,String limit) {
    userId = mFirebaseDatabase.push().getKey();
    Customer customer = new Customer(name, email,limit);

    mFirebaseDatabase.child(userId).setValue(customer);
}

That's it.. In Database it is somehow represented as below:

tbl-customers
|___loggedInUserId1
    |___customerID1
        |___customerName
        |___customerCode
        |___customerLimit
    |___customerID2
        |___customerName
        |___customerCode
        |___customerLimit
    |___customerID3
        |___customerName
        |___customerCode
        |___customerLimit
|___loggedInUserId2
    |___customerID4
        |___customerName
        |___customerCode
        |___customerLimit

and I have rules defined as

{
    "rules": {
        "tbl-customers": {
            ".read": "auth != null",
            ".write": "auth != null",
            "$custId": {
                "customerName": {
                    ".validate": "newData.isString() && newData.val().length < 100 && newData.val().length > 8"
                },
                "customerCode": {
                    ".validate": "newData.isString() && newData.val().length<4 && !newData.exists() && newData.val().length>1"
                },
                "customerLimit": {}
            }
        }
    }
}

Unfortunately, the data is inserted without considering any of the validation written for each properties. Even the empty data gets inserted.

I started thinking whether the rule written is of proper structure, because if I see the data inserted then it has 3 levels - tbl-customer-->loggedInUserId-->customerId but rules have been only written for tbl-customer-->customerId.

So I changed the rules as below.

{
    "rules": {
        "tbl-customers": {
            ".read": "auth != null",
            ".write": "auth != null",
            "$user_id": {
                ".validate": "auth.uid===$user_id",
                "$custId": {
                    "customerName": {
                        ".validate": "newData.isString() && newData.val().length < 100"
                    },
                    "customerCode": {
                        ".validate": "newData.isString() && newData.val().length<4 && !newData.exists()"
                    },
                    "customerLimit": {}
                }
            }

        }
    }
}

extending it to one more level by including,

"$user_id": {
             ".validate": "auth.uid===$user_id"
           ...
}

But now this throws Permission Denied Exception. Am out of ideas at this point of time. Could someone guide me in the right direction? I have referred lot of posts from my previous question but to my bad, I couldn't grab much information from it. Hope to find some clear explanation as on why rules validation are failing and why data gets inserted with above mentioned first rule.

解决方案

I might be wrong here, but the .read and .write rules will always cascade down your tree regardless here, which the line ".write": "auth != null" is most likely where you're facing the problems.

It would be best to move this rule to where the ".validate": "auth.uid===$user_id" rule is and remove the validate rule. You would then change it to something like "auth.uid == $user_id". The 'validate' rule I believe is just for taking in a written input at that specific location and then accepting or rejecting.

This is how I believe it should look:

{
    "rules": {
        "tbl-customers": {
            ".read": "auth != null"
            "$user_id": {
                ".write": "auth.uid === $user_id"
                "$custId": {
                    "customerName": {
                        ".validate": "newData.isString() && newData.val().length < 100"
                    },
                    "customerCode": {
                        ".validate": "newData.isString() && newData.val().length<4 && !newData.exists()"
                    },
                    "customerLimit": {}
                }
            }

        }
    }
}

This structure will allow all logged in users to read the data, which you could restrict further to the $user_id location if you wish, similar to the write rule currently in place. This would then only allow users who match the $user_id read and write privileges.

CASE STUDY

To add to this, this is a structure I set up sometime ago that would allow an administrator the ability to add users:

{
  "rules": {
      "Administrator": {
          ".read": "auth != null"
      },
      "Users": {
        "$user_id": {
          ".write": "$user_id === auth.uid",
          ".read": "$user_id === auth.uid"
        }
      }
  }
}

这篇关于Firebase规则验证不会验证数据的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆