10

I'm trying to mix Firebase's Rule wildcards with children comparisons.

I'm reading a child elsewhere who's value is '4'.

When I do a literal comparison, the simulator gives me the green light (like this):

{
  "rules": {
    "die": {
      "rolls": {
        "$i": {
          ".read": "4 == root.child('die/i').val()"
        }
      },
      "i": {
        ".read": true,
        ".write": true
      }
    }
  }
}

Output (success):

Type    read
Location    /die/rolls/4
Data    null
Auth    null
Read successful
Line 7 (/die/rolls/4)
read: "4 == root.child('die/i').val()"

But a wildcard comparison fails. Why?

{
  "rules": {
    "die": {
      "rolls": {
        "$i": {
          ".read": "$i == root.child('die/i').val()"
        }
      },
      "i": {
        ".read": true,
        ".write": true
      }
    }
  }
}

Output (failure):

Type    read
Location    /die/rolls/4
Data    null
Auth    null
Read denied
Line 7 (/die/rolls/4)
read: "$i == root.child('die/i').val()"

(also, I've tried simulating authentication; same thing.)

Alex
  • 603
  • 7
  • 13

1 Answers1

5

The reason this is failing is because

root.child('die/i').val()

returns a number. Per the firebase documentation

Note: Path keys are always strings. For this reason, it's important to keep in mind that when we attempt to compare a $ variable to a number, this will always fail. This can be corrected by converting the number to a string (e.g. $key === newData.val()+'')

The following gives you your desired results

 {
 "rules": {
   "die": {
     "rolls": {
       "$i": {
         ".read": "$i === root.child('die/i').val()+''"
       }
     },
     "i": {
       ".read": true,
       ".write": true
     }
   }
 }
}

Firebase documentation

Padawan
  • 770
  • 1
  • 8
  • 18