Firebase Real-Time Database Tutorial for iOS |

Learn how to use Firebase Real-Time Database to seamlessly store and fetch data in real-time, while supporting offline mode and secure access.

This is a companion discussion topic for the original entry at

Hi, the tutorial was great, but there is a typo in the code snippet under “Customizing the rules” for the real-time database. The code differs from the code in the screenshots below “$thoughtId”:{ } is missing. I tried the starter and final project (of course I added the new “GoogleService-Info.plist” but there is still an observer error like “Listener at /users/xxxxxx/thoughts failed: permission_denied”, although I added “databasePath?.removeAllObservers()”. So when I post a thought and I log out and re-login the new thoughts were there, but when I am logged in and I press “Post” the new thought is not showing up and I see the permission_denied error. Here the rules for the real-time db: { “rules”: { “users”: { // 1 “$uid”: { // 2 “thoughts”: { // 3 “$thoughtId”:{ “.read”: “auth != null && auth.uid == $uid”, // 4 “.write”: “auth != null && auth.uid == $uid” } } } } } }

Whoops! Good spot Michael, thank you. Have updated the code snippet now.

Yusuf, thanks for this updated tutorial on Firebase - my first intro to Firebase last year didn’t work nearly as smoothly as this sample app. However, I ran into the same permission error, even with the updated rules definition Michael suggested.
Perhaps something at the Firebase end changed, but what I found worked for me is: it appears the auth logic in the Firebase console rule set is defined one level too deep. i.e. it only applies if the access path includes a $thoughtID. However, the .observe(.childAdded) listener appears to only attach to the collection path (/users/$uid/thoughts) - which resulted in a permission error for me. I changed the rules to this, which allowed the listener to work:

  "rules": {
    "users": { // 1
      "$uid": { // 2
        "thoughts": { // 3
          //"$thoughtId": { // 4
            ".read": "auth != null && auth.uid == $uid", // 5
            ".write": "auth != null && auth.uid == $uid"

Hope this helps others. Cheers!