Structuring Security Rules

Las reglas de seguridad de Cloud Firestore te permiten controlar el acceso a los documentos y las colecciones de tu base de datos. La sintaxis de reglas flexibles te permite crear reglas que coincidan con todo, desde todas las operaciones de escritura en la base de datos hasta las operaciones en un documento específico.

Esta guía describe la sintaxis básica y la estructura de las reglas de seguridad. Combina esta sintaxis con las condiciones de las reglas de seguridad para crear conjuntos de reglas completos.

Declaración del servicio y la base de datos

Las reglas de seguridad de Cloud Firestore siempre comienzan con la siguiente declaración:

service cloud.firestore {
  match /databases/{database}/documents {
    // ...
  }
}

La declaración service cloud.firestore define el alcance de las reglas a Cloud Firestore, lo que evita conflictos entre las reglas de seguridad de Cloud Firestore y las reglas de otros productos, como Cloud Storage.

La declaración match /databases/{database}/documents especifica que las reglas deberían coincidir con cualquier base de datos de Cloud Firestore en el proyecto. Actualmente, cada proyecto tiene solo una base de datos llamada (default).

Reglas básicas de lectura y escritura

Las reglas básicas consisten en una declaración match que especifica la ruta de un documento y una expresión allow que describe cuándo se permite la lectura de los datos especificados:

service cloud.firestore {
  match /databases/{database}/documents {

    // Match any document in the 'cities' collection
    match /cities/{city} {
      allow read: if <condition>;
      allow write: if <condition>;
    }
  }
}

Todas las declaraciones de coincidencia deben apuntar a los documentos, no a las colecciones. Una declaración de coincidencia puede apuntar a un documento específico, como en match /cities/SF o usar comodines para apuntar a cualquier documento en la ruta especificada, como en match /cities/{city}.

En el ejemplo anterior, la declaración de coincidencia usa la sintaxis de comodín {city}. Esto significa que la regla se aplica a cualquier documento de la colección cities, como /cities/SF o /cities/NYC. Cuando se evalúan las expresiones allow en la declaración de coincidencia, la variable city se resolverá según el nombre del documento de ciudad, como SF o NYC.

Operaciones detalladas

En algunas situaciones, es útil desglosar read y write en operaciones más detalladas. Por ejemplo, la app podría aplicar diferentes condiciones a la creación de documentos en comparación con la eliminación de documentos. También, podrías permitir lecturas de un solo documento, pero rechazar las consultas de mayor tamaño.

Una regla read se puede desglosar en get y list, mientras que una regla write se puede desglosar en create, update y delete:

service cloud.firestore {
  match /databases/{database}/documents {
    // A read rule can be divided into get and list rules
    match /cities/{city} {
      // Applies to single document read requests
      allow get: if <condition>;

      // Applies to queries and collection read requests
      allow list: if <condition>;
    }

    // A write rule can be divided into create, update, and delete rules
    match /cities/{city} {
      // Applies to writes to nonexistent documents
      allow create: if <condition>;

      // Applies to writes to existing documents
      allow update: if <condition>;

      // Applies to delete operations
      allow delete: if <condition>;
    }
  }
}

Datos jerárquicos

Los datos de Cloud Firestore se organizan en colecciones de documentos y cada documento puede extender la jerarquía a través de subcolecciones. Es importante comprender cómo interactúan las reglas de seguridad con los datos jerárquicos.

Considera el caso en el que cada documento de la colección cities contiene una subcolección landmarks. Las reglas de seguridad se aplican solo a la ruta que coincide, por lo que no se aplican los controles de acceso definidos de la colección cities a la subcolección landmarks. En cambio, debes escribir reglas explícitas para controlar el acceso a las subcolecciones:

service cloud.firestore {
  match /databases/{database}/documents {
    match /cities/{city} {
      allow read, write: if <condition>;

        // Explicitly define rules for the 'landmarks' subcollection
        match /landmarks/{landmark} {
          allow read, write: if <condition>;
        }
    }
  }
}

Cuando anidas declaraciones match, la ruta de la declaración match interna siempre es relativa a la declaración match externa. Por lo tanto, los siguientes conjuntos de reglas son equivalentes:

service cloud.firestore {
  match /databases/{database}/documents {
    match /cities/{city} {
      match /landmarks/{landmark} {
        allow read, write: if <condition>;
      }
    }
  }
}
service cloud.firestore {
  match /databases/{database}/documents {
    match /cities/{city}/landmarks/{landmark} {
      allow read, write: if <condition>;
    }
  }
}

Si quieres usar reglas que se apliquen a una jerarquía de profundidad arbitraria, usa la sintaxis de comodines recurrentes, {name=**}:

service cloud.firestore {
  match /databases/{database}/documents {
    // Matches any document in the cities collection as well as any document
    // in a subcollection.
    match /cities/{document=**} {
      allow read, write: if <condition>;
    }
  }
}

Cuando uses la sintaxis de comodines recurrentes, los comodines disponibles contendrán el segmento de la ruta que coincide completo, incluso si el documento se ubica en una subcolección anidada a mayor profundidad. Por ejemplo, las reglas anteriores coincidirían con un documento ubicado en /cities/SF/landmarks/coit_tower y el valor de la variable document sería SF/landmarks/coit_tower.

Los comodines recurrentes no pueden coincidir con una ruta vacía, por lo que match /cities/{city}/{document=**} coincidirá con los documentos de las subcolecciones, pero no con los de la colección cities, mientras que match /cities/{document=**} coincidirá con los documentos en la colección cities y sus subcolecciones.

Es posible que un documento coincida con más de una declaración match. Si varias expresiones allow coinciden con una solicitud, se permite el acceso siempre que alguna de las condiciones sea true:

service cloud.firestore {
  match /databases/{database}/documents {
    // Matches any document in the 'cities' collection.
    match /cities/{city} {
      allow read, write: if false;
    }

    // Matches any document in the 'cities' collection or subcollections.
    match /cities/{document=**} {
      allow read, write: if true;
    }
  }
}

En el ejemplo anterior, se permitirán todas las lecturas y escrituras en la colección cities, ya que la segunda regla siempre es true, incluso si la primera regla siempre es false.

Límites de las reglas de seguridad

Cuando trabajes con reglas de seguridad, ten en cuenta los siguientes límites:

Límite Detalles
Cantidad máxima de llamadas exists(), get() y getAfter() únicas por evaluación.

3 de cada una, con una cantidad máxima combinada de 5. Las solicitudes múltiples al mismo documento no cuentan como solicitudes independientes.

Cuando se evalúan las reglas de una operación de escritura o de un conjunto de operaciones de escritura en una transacción o lote de escrituras, las solicitudes de destinos de escritura no cuentan como parte del límite.

Profundidad máxima de llamada a una función 20
Cantidad máxima de llamadas recurrentes o cíclicas a una función 0 (no permitidas)
Cantidad máxima de expresiones en un conjunto de reglas 10,000
Tamaño máximo de un conjunto de reglas 64 KB

Próximos pasos

Enviar comentarios sobre…

¿Necesitas ayuda? Visita nuestra página de asistencia.