Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Validate a Firebase Key is an integer

Here is the database schema:

enter image description here

Here are the rules:

"notifications": {
   "$year": {
      ".read": "false",
      ".write": "!data.exists()",
      "$month": {
          ".read": "false",
          ".write": "!data.exists()",

          "$day": {
              ".read": "false",
              ".write": "!data.exists()",

              "$hour": {
                  ".read": "false",
                  ".write": "!data.exists()",

                  "$minute": {
                      ".read": "false",
                      ".write": "!data.exists()",
                      "$data": {
                          ".read": "false",
                          ".write": "!data.exists()"
                      }
                  }
              }
          }
      }
   }

How can I validate (using ".validate" or ".write" rules) that the users can enter only integers into that tree? Or is there some workaround?

What I am trying to achieve is to create write only (no deletes, or updates) log that has some structure and will be processed later. I can change the structure for example to something like 2015-10-6-17-30 for the key, or something else. I just can't believe that Firebase does not have something for this situation.

Update: This is not duplicate, I am searching for a workaround, or something else that will help me achieve what I am after.

like image 564
SM79 Avatar asked Oct 06 '15 20:10

SM79


2 Answers

To validate that a key is a number:

{
  "$key": {
     ".validate": "$key.matches(/^[0-9]+$/)"
  }
}

But please read about array-like behaviors in Firebase. Hint: probably use a prefix like "y2015", "m12", etc. to avoid some unexpected results with using numbers.

like image 53
Kato Avatar answered Nov 15 '22 18:11

Kato


If using push IDs works for you, here's a security rule structure you could use.

{
    "notifications": {
        "$notification_id": {
            ".write": "!data.exists()",
            ".read": "false",
            ".validate": "newData.hasChildren(['time', 'state', 'message'])",
            "time": {
                ".validate": "newData.val().matches(/YOUR REGEX/)"
            },
            "state": {
                ".validate": ""
            },
            "message": {
                ".validate": ""
            }
        }
    }
}

Obviously you'll need to fill in the blanks. The main thing here is that you can use a regex to match the time field.

The actual data would look like:

{
    "notifications": {
        "-K-z5koYf8mYZu5OfSGR": {
            "time": "2015-10-06-17-30",
            "state": 1,
            "message": "foo"
        },
        "-K-z5koYf8mYZwgwsfGx": {
            "time": "2015-10-06-17-30",
            "state": 1,
            "message": "bar"
        }
    }
}
like image 2
Anid Monsur Avatar answered Nov 15 '22 17:11

Anid Monsur