Boris Grunwald
Boris Grunwald

Reputation: 2712

How should i structure my firestore security rules?

I am making a little web based tic tac toe game as a project to show on my portfolio website. I want someone visiting the site to be able to create a game, and then another player to join that game.

The person that creates the game creates a document in my firestore database under a "Games" collection, that is defined by this interface:

type Player = 'x' | 'o'
type GameFieldValue = null | Player;
type Coordinate = [number, number]
type Row = [GameFieldValue, GameFieldValue, GameFieldValue];

interface IGameDoc {
    playerTurn: Player;
    playerTwoUid: string | null
    gameState: {
        rowOne: Row
        rowTwo: Row
        rowThree: Row
    };
}

The document is stored with the id of the user that created the game e.g.

enter image description here

So the rules in my firebase firestore for creaing a game are simply that you need to be signed in (which I just do anonymously whenever someone visits the site)

rules_version = '2';
// Allow read/write access on all documents to any user signed in to the application
service cloud.firestore {
  match /databases/{database}/documents {

    match /Games/{gameId} {
      

      allow read, write: if request.auth != null;
      
    }
  }
}

Now player one can send the gameId to someone else that can then join the game. Two players can then listen for real time updates to the gamestate and update the UI accordingly.

Now my problem is figuring out how to let the second player join the game.

The second player needs to initially be able to update the document and insert his uid in the playerTwo field. On subsequent request to update the document it should only be allowed for the player that created the game as well as the second player to do that.

I hope I made myself somewhat clear here.

Can anyone help me how to structure my firestore rules to achieve this?

Upvotes: 2

Views: 43

Answers (1)

Frank van Puffelen
Frank van Puffelen

Reputation: 598623

It sounds like you're looking for this:

allow create: if (resource.data.player1 == request.auth.uid);
allow update: if (resource.data.player2 == null && request.resource.data.player2 == request.auth.uid)
              || (resource.data.player1 == request.auth.uid)
              || (resource.data.player2 == request.auth.uid)

In words: you're allow to create a document if you set your own UID as player1, and you're allowed to update a document if you're player1 or player2, or if there is no player2 yet and you're setting yourself up as player2.

Upvotes: 1

Related Questions