Gestisci ed esegui il deployment delle regole di sicurezza Firebase

Firebase offre diversi strumenti per gestire le tue Security Rules, ognuno utile in casi particolari e ognuno che utilizza la stessa API di gestione delle regole di sicurezza di backend di Firebase.

Indipendentemente dallo strumento utilizzato per richiamarla, l'API di gestione:

  • Inserisce una origine delle regole: un insieme di regole, in genere un file di codice contenente Firebase Security Rules istruzioni.
  • Archivia l'origine inserita come un ruleset immutabile.
  • Monitora il deployment di ogni ruleset in una release. I servizi abilitati per le regole di sicurezza di Firebase cercano la release di un progetto per valutare ogni richiesta di una risorsa protetta.
  • Fornisce la possibilità di eseguire test sintattici e semantici di un ruleset.

Utilizzare l'Firebase CLI

Con la Firebase CLI, puoi caricare origini locali ed eseguire il deployment di release. Firebase Local Emulator Suite dell'interfaccia a riga di comando Firebase Local Emulator Suite consente di eseguire test locali completi delle origini.

L'utilizzo dell'interfaccia a riga di comando consente di mantenere le regole sotto il controllo della versione con il codice dell'applicazione e di eseguire il deployment delle regole come parte del processo di deployment esistente.

Generare un file di configurazione

Quando configuri il progetto Firebase utilizzando la Firebase CLI, crei un file di configurazione .rules nella directory del progetto. Utilizza il seguente comando per iniziare a configurare il progetto Firebase:

Cloud Firestore

// Set up Firestore in your project directory, creates a .rules file
firebase init firestore

Realtime Database

// Set up Realtime Database in your project directory, creates a .rules file
firebase init database

Cloud Storage

// Set up Storage in your project directory, creates a .rules file
firebase init storage

Modificare e aggiornare le regole

Modifica l'origine delle regole direttamente nel file di configurazione .rules.

Assicurati che le modifiche apportate nell'Firebase interfaccia a riga di comando di Firebase si riflettano nella Firebase console o che tu apporti costantemente gli aggiornamenti utilizzando la Firebase console o l'interfaccia a riga di comando di Firebase. In caso contrario, potresti sovrascrivere gli aggiornamenti apportati nella Firebase console.

Testare gli aggiornamenti

Il Local Emulator Suite fornisce emulatori per tutti i prodotti abilitati per le regole di sicurezza. Il motore delle regole di sicurezza per ogni emulatore esegue la valutazione sintattica e semantica delle regole, superando quindi i test sintattici offerti dall'API di gestione delle regole di sicurezza.

Se utilizzi l'interfaccia a riga di comando, la suite è uno strumento eccellente per Firebase Security Rules test. Utilizza Local Emulator Suite per testare gli aggiornamenti in locale e verificare che le Security Rules della tua app si comportino come previsto.

Eseguire il deployment degli aggiornamenti

Dopo aver aggiornato e testato Security Rules, esegui il deployment delle origini in produzione.

Per Cloud Firestore Security Rules, associa i file .rules ai database denominati predefiniti e aggiuntivi esaminando e aggiornando il file firebase.json.

Utilizza i seguenti comandi per eseguire il deployment selettivo dei tuoi Security Rules da soli o eseguirne il deployment come parte del normale processo di deployment.

Cloud Firestore

// Deploy rules for all databases configured in your firebase.json
firebase deploy --only firestore:rules
// Deploy rules for the specified database configured in your firebase.json firebase deploy --only firestore:<databaseId>

Realtime Database

// Deploy your .rules file
firebase deploy --only database

Cloud Storage

// Deploy your .rules file
firebase deploy --only storage

Utilizzare la console Firebase

Puoi anche modificare Security Rules origini ed eseguirne il deployment come release da Firebase console. I test sintattici vengono eseguiti durante la modifica nell'inter101}Firebasefaccia utente della Security Rules console, mentre i test semantici sono disponibili utilizzando Playground.

Modificare e aggiornare le regole

  1. Apri la Firebase console e seleziona il tuo progetto.
  2. Quindi, seleziona Realtime Database, Cloud Firestore o Storage dalla navigazione del prodotto, quindi fai clic su Rules per accedere all' Security Rules editor.
  3. Modifica le regole direttamente nell'editor.

Testare gli aggiornamenti

Oltre a testare la sintassi nell'interfaccia utente dell'editor, puoi testare il comportamento semantico Security Rules utilizzando le risorse di database e di archiviazione del progetto, direttamente nella Firebase console, utilizzando il Security Rules Playground. Apri la schermata Rules Playground nell'editor Security Rules, modifica le impostazioni e fai clic su Esegui. Cerca il messaggio di conferma nella parte superiore dell'editor.

Eseguire il deployment degli aggiornamenti

Quando sei soddisfatto degli aggiornamenti, fai clic su Pubblica.

Utilizzare l'SDK Admin

Puoi utilizzare il Admin SDK per i ruleset di Node.js. Con questo accesso programmatico, puoi:

  • Implementare strumenti, script, dashboard e pipeline CI/CD personalizzati per la gestione delle regole.
  • Gestire le regole più facilmente in più progetti Firebase.

Quando aggiorni le regole in modo programmatico, è molto importante evitare di apportare modifiche involontarie al controllo dell'accesso per la tua app. Scrivi il tuo Admin SDK codice tenendo presente soprattutto la sicurezza, in particolare quando aggiorni o esegui il deployment delle regole.

Un'altra cosa importante da tenere presente è che le release Firebase Security Rules richiedono un periodo di diversi minuti per la propagazione completa. Quando utilizzi Admin SDK per eseguire il deployment delle regole, assicurati di evitare condizioni di race in cui la tua app si basa immediatamente su regole il cui deployment non è ancora completato. Se il tuo caso d'uso richiede aggiornamenti frequenti delle regole di controllo dell'accesso, valuta le soluzioni che utilizzano Cloud Firestore, progettato per ridurre le condizioni di race nonostante gli aggiornamenti frequenti.

Tieni presente anche questi limiti:

  • Le regole devono essere inferiori a 256 KiB di testo con codifica UTF-8 quando vengono serializzate.
  • Un progetto può avere al massimo 2500 ruleset di cui è stato eseguito il deployment. Una volta raggiunto questo limite, devi eliminare alcuni ruleset precedenti prima di crearne di nuovi.

Creare ed eseguire il deployment di Cloud Storage o Cloud Firestore ruleset

Un flusso di lavoro tipico per la gestione delle regole di sicurezza con il Admin SDK potrebbe includere tre passaggi distinti:

  1. Creare un'origine del file delle regole (facoltativo)
  2. Creare un ruleset
  3. Pubblicare o eseguire il deployment del nuovo ruleset

L'SDK fornisce un metodo per combinare questi passaggi in una singola chiamata API per Cloud Storage e Cloud Firestore regole di sicurezza. Ad esempio:

    const source = `service cloud.firestore {
      match /databases/{database}/documents {
        match /carts/{cartID} {
          allow create: if request.auth != null && request.auth.uid == request.resource.data.ownerUID;
          allow read, update, delete: if request.auth != null && request.auth.uid == resource.data.ownerUID;
        }
      }
    }`;
    // Alternatively, load rules from a file
    // const fs = require('fs');
    // const source = fs.readFileSync('path/to/firestore.rules', 'utf8');

    await admin.securityRules().releaseFirestoreRulesetFromSource(source);

Lo stesso pattern funziona per le regole Cloud Storage con releaseFirestoreRulesetFromSource().

In alternativa, puoi creare il file delle regole come oggetto in memoria, creare il ruleset ed eseguire il deployment del ruleset separatamente per un controllo più preciso di questi eventi. Ad esempio:

    const rf = admin.securityRules().createRulesFileFromSource('firestore.rules', source);
    const rs = await admin.securityRules().createRuleset(rf);
    await admin.securityRules().releaseFirestoreRuleset(rs);

Aggiornare i ruleset Realtime Database

Per aggiornare i ruleset Realtime Database con Admin SDK, utilizza i metodi getRules() e setRules() di admin.database. Puoi recuperare i ruleset in formato JSON o come stringa con i commenti inclusi.

Per aggiornare un ruleset:

    const source = `{
      "rules": {
        "scores": {
          ".indexOn": "score",
          "$uid": {
            ".read": "$uid == auth.uid",
            ".write": "$uid == auth.uid"
          }
        }
      }
    }`;
    await admin.database().setRules(source);

Gestire i ruleset

Per facilitare la gestione di ruleset di grandi dimensioni, Admin SDK consente di elencare tutte le regole esistenti con admin.securityRules().listRulesetMetadata. Ad esempio:

    const allRulesets = [];
    let pageToken = null;
    while (true) {
      const result = await admin.securityRules().listRulesetMetadata(pageToken: pageToken);
      allRulesets.push(...result.rulesets);
      pageToken = result.nextPageToken;
      if (!pageToken) {
        break;
      }
    }

Per i deployment di grandi dimensioni che raggiungono il limite di 2500 ruleset nel tempo, puoi creare una logica per eliminare le regole più vecchie in un ciclo di tempo fisso. Ad esempio, per eliminare tutti i ruleset di cui è stato eseguito il deployment da più di 30 giorni:

    const thirtyDays = new Date(Date.now() - THIRTY_DAYS_IN_MILLIS);
    const promises = [];
    allRulesets.forEach((rs) => {
      if (new Date(rs.createTime) < thirtyDays) {
        promises.push(admin.securityRules().deleteRuleset(rs.name));
      }
    });
    await Promise.all(promises);
    console.log(`Deleted ${promises.length} rulesets.`);

Utilizzare l'API REST

Gli strumenti descritti sopra sono adatti a vari workflow, inclusa la gestione delle regole di sicurezza di Firebase per più database Cloud Firestore nel tuo progetto, ma potresti voler gestire ed eseguire il deployment delle regole di sicurezza di Firebase utilizzando l'API di gestione stessa.Firebase Security RulesFirebase Security RulesCloud Firestore L'API di gestione offre la massima flessibilità.

Tieni presente anche questi limiti:

  • Le regole devono essere inferiori a 256 KiB di testo con codifica UTF-8 quando vengono serializzate.
  • Un progetto può avere al massimo 2500 ruleset di cui è stato eseguito il deployment. Una volta raggiunto questo limite, devi eliminare alcuni ruleset precedenti prima di crearne di nuovi.

Creare ed eseguire il deployment di Cloud Firestore o Cloud Storage ruleset con REST

Gli esempi in questa sezione utilizzano Firestore Security Rules, ma si applicano anche a Cloud Storage Security Rules.

Gli esempi utilizzano anche cURL per effettuare chiamate API. I passaggi per configurare e trasmettere i token di autenticazione vengono omessi. Puoi sperimentare con questa API utilizzando Explorer API integrato nella documentazione di riferimento.

I passaggi tipici per creare ed eseguire il deployment di un ruleset utilizzando l'API di gestione sono:

  1. Creare origini del file delle regole
  2. Creare un ruleset
  3. Pubblicare (eseguire il deployment) del nuovo ruleset.

Creare un'origine

Supponiamo che tu stia lavorando al progetto Firebase secure_commerce e che tu voglia eseguire il deployment delle regole di sicurezza di Cloud Firestore bloccate in un database del tuo progetto denominato east_store.Cloud Firestore Security Rules

Puoi implementare queste regole in un file firestore.rules.

service cloud.firestore {
  match /databases/{database}/documents {
    match /{document=**} {
      allow read, write: if false;
    }
  }
}

Creare un ruleset

Ora, genera un'impronta digitale con codifica in base64 per questo file. Puoi quindi utilizzare l'origine in questo file per popolare il payload necessario per creare un ruleset con la chiamata REST projects.rulesets.create. Qui, utilizza il comando cat per inserire i contenuti di firestore.rules nel payload REST.

Per il monitoraggio, per associare questo al database east_store, imposta attachment_point su east_store.

curl -X POST -d '{
  "source": {
    "files": [
      {
        "content": "' $(cat storage.rules) '",
        "name": "firestore.rules",
        "fingerprint": <sha fingerprint>
      },
    "attachment_point": "firestore.googleapis.com/databases/east_store"
    ]
  }
}' 'https://firebaserules.googleapis.com/v1/projects/secure_commerce/rulesets'

L'API restituisce una risposta di convalida e un nome di ruleset, ad esempio projects/secure_commerce/rulesets/uuid123.

Pubblicare (eseguire il deployment) di un ruleset

Se il ruleset è valido, l'ultimo passaggio consiste nell'eseguire il deployment del nuovo ruleset in una release denominata.

curl -X POST -d '{
  "name": "projects/secure_commerce/releases/cloud.firestore/east_store"  ,
  "rulesetName": "projects/secure_commerce/rulesets/uuid123"
}' 'https://firebaserules.googleapis.com/v1/projects/secure_commerce/releases'

Tieni presente che le release Firebase Security Rules richiedono un periodo di diversi minuti per la propagazione completa. Quando utilizzi l'API REST di gestione per eseguire il deployment, assicurati di evitare condizioni di race in cui la tua app si basa immediatamente su regole il cui deployment non è ancora completato.

Aggiornare i Realtime Database ruleset con REST

Realtime Database fornisce la propria interfaccia REST per la gestione di Security Rules. Consulta Gestire Realtime Database Security Rules tramite REST.

Gestire i ruleset con REST

Per facilitare la gestione dei deployment di regole di grandi dimensioni, oltre a un metodo REST per la creazione di ruleset e release, l'API di gestione fornisce metodi per:

  • Elencare, ottenere ed eliminare ruleset
  • Elencare, ottenere ed eliminare le release delle regole

Per i deployment di grandi dimensioni che raggiungono il limite di 2500 ruleset nel tempo, puoi creare una logica per eliminare le regole più vecchie in un ciclo di tempo fisso. Ad esempio, per eliminare tutti i ruleset di cui è stato eseguito il deployment da più di 30 giorni, puoi chiamare il metodo projects.rulesets.list, analizzare l'elenco JSON degli oggetti Ruleset nelle relative chiavi createTime, quindi chiamare project.rulesets.delete sui ruleset corrispondenti in base a ruleset_id.

Testare gli aggiornamenti con REST

Infine, l'API di gestione consente di eseguire test sintattici e semantici sulle Cloud Firestore e Cloud Storage risorse nei progetti di produzione.

Il test con questo componente dell'API consiste in:

  1. Definire un oggetto JSON TestSuite per rappresentare un insieme di oggetti TestCase
  2. Inviare TestSuite
  3. Analizzare gli oggetti TestResult restituiti

Definiamo un oggetto TestSuite con un singolo TestCase in un file testcase.json. In questo esempio, trasmettiamo l'origine del Security Rules linguaggio in linea con il payload REST, insieme alla suite di test da eseguire su queste regole. Specifichiamo un'aspettativa di valutazione delle regole e la richiesta del client rispetto alla quale deve essere testato il ruleset. Puoi anche specificare il livello di completezza del report di test, utilizzando il valore "FULL" per indicare che nel report devono essere incluse le espressioni del Security Rules linguaggio, incluse quelle che non corrispondono alla richiesta.

 {
  "source":
  {
    "files":
    [
      {
        "name": "firestore.rules",
        "content": "service cloud.firestore {
          match /databases/{database}/documents {
            match /users/{userId}{
              allow read: if (request.auth.uid == userId);
            }
            function doc(subpath) {
              return get(/databases/$(database)/documents/$(subpath)).data;
            }
            function isAccountOwner(accountId) {
              return request.auth.uid == accountId 
                  || doc(/users/$(request.auth.uid)).accountId == accountId;
            }
            match /licenses/{accountId} {
              allow read: if isAccountOwner(accountId);
            }
          }
        }"
      }
    ]
  },
  "testSuite":
  {
    "testCases":
    [
      {
        "expectation": "ALLOW",
        "request": {
           "auth": {"uid": "123"},
           "path": "/databases/(default)/documents/licenses/abcd",
           "method": "get"},
        "functionMocks": [
            {
            "function": "get",
            "args": [{"exact_value": "/databases/(default)/documents/users/123"}],
            "result": {"value": {"data": {"accountId": "abcd"}}}
            }
          ]
      }
    ]
  }
}

Possiamo quindi inviare questo TestSuite per la valutazione con il metodo projects.test.

curl -X POST -d '{
    ' $(cat testcase.json) '
}' 'https://firebaserules.googleapis.com/v1/projects/secure_commerce/rulesets/uuid123:test'

Il TestReport restituito (contenente lo stato di RIUSCITA/ERRORE del test, elenchi di messaggi di debug, elenchi di espressioni delle regole visitate e i relativi report di valutazione) confermerà con lo stato RIUSCITA che l'accesso è consentito correttamente.

Gestire le autorizzazioni per tra servizi Cloud Storage Security Rules

Se crei Cloud Storage Security Rules che utilizzano i contenuti dei documenti Cloud Firestore per valutare le condizioni di sicurezza, ti verrà chiesto nella console Firebase o nell'interfaccia a riga di comando Firebase di abilitare le autorizzazioni per collegare i due prodotti.

Se decidi di disattivare la sicurezza tra servizi:

  1. Innanzitutto, prima di disattivare la funzionalità, modifica le regole, rimuovendo tutte le istruzioni che utilizzano le funzioni Security Rules per accedere a Cloud Firestore. In caso contrario, dopo la disattivazione della funzionalità, le Security Rules valutazioni causeranno il fallimento delle richieste di Storage.

  2. Utilizza la pagina IAM nella console Google Cloud per eliminare il ruolo "Firebase Rules Firestore Service Agent" seguendo la guida di Cloud per revocare i ruoli.

Ti verrà chiesto di riattivare la funzionalità la prossima volta che salvi le regole tra servizi dall'interfaccia a riga di comando di Firebase o dalla console Firebase.