Масштабирование с помощью нескольких баз данных

Лучший способ оптимизировать производительность и масштабировать данные в Firebase Realtime Database – разделить данные между несколькими экземплярами Realtime Database. Это также называется сегментированием базы данных. Шардинг позволяет масштабировать базу данных за пределы ограничений, которые применяются к отдельным экземплярам, а также балансировать нагрузку и оптимизировать производительность.

Когда нужно сегментировать данные

Если вы используете Realtime Database, вам может потребоваться сегментировать данные по нескольким базам данных в следующих случаях:

  • Вам нужно превысить лимит в 200 000 одновременных подключений, 1000 операций записи в секунду или другие ограничения для одного экземпляра базы данных.
  • У вас есть несколько отдельных наборов данных и вы хотите оптимизировать производительность (например, приложение для чата, которое обслуживает отдельные независимые группы пользователей).
  • Вы хотите распределить нагрузку между несколькими базами данных, чтобы повысить время работы и снизить риск перегрузки одного экземпляра базы данных.

Как сегментировать данные

Чтобы сегментировать данные, выполните следующие действия (подробно описаны ниже):

  1. Сопоставляйте данные с несколькими базами данных в соответствии с потребностями приложения.
  2. Создайте несколько экземпляров базы данных.
  3. Настройте приложение так, чтобы оно подключалось к экземпляру Realtime Database, необходимому для каждого набора данных.

Сопоставьте данные

При сопоставлении данных с несколькими базами данных постарайтесь выполнить следующие условия:

  • Каждый запрос выполняется только для одного экземпляра базы данных. Realtime Database не поддерживает запросы к нескольким экземплярам базы данных.
  • Отсутствие или минимальный объем совместного использования или дублирования данных между экземплярами базы данных.
  • Каждый экземпляр приложения в любой момент времени подключается только к одной базе данных.

При сопоставлении данных рекомендуем придерживаться следующих стратегий:

Создайте основной сегмент

Храните карту, на которой показано, как ваши данные хранятся в экземплярах базы данных. Таким образом, вы можете программно определить, какой экземпляр базы данных соответствует подключающемуся клиенту. Имейте в виду, что это может иметь больше накладных расходов, чем прямое подключение к конкретному экземпляру базы данных, который вам нужен, когда он вам нужен.

Как группировать данные по категориям или клиентам

Храните данные в изолированных экземплярах базы данных, сгруппированных по пользователям или типам данных. Например, если вы создаете приложение для чата, которое обслуживает несколько организаций, вы можете создать экземпляр базы данных для каждой организации и хранить все данные чата в уникальных экземплярах базы данных.

В этом случае организации A и B не обмениваются данными, в ваших базах данных нет дублирующихся данных, и вы выполняете запросы только к одному экземпляру базы данных. Кроме того, пользователи в каждой организации подключаются только к базе данных своей организации, когда используют приложение Chat.

Вы можете заранее создать несколько экземпляров базы данных и использовать идентификатор организации, чтобы сопоставить команду с ее экземпляром базы данных. Например, организация А сопоставляется с базой данных Realtime Database А.

Способ сопоставления данных для приложения зависит от конкретного случая использования, но условия и стратегии, описанные выше, могут помочь вам определить, что подходит для ваших данных.

Создание нескольких экземпляров Realtime Database

Если вы используете тарифный план Blaze, то можете создать до 1000 экземпляров базы данных в одном проекте Firebase.

создать базу данных в консоли Firebase с помощью контекстного меню в разделе баз данных

  1. В консоли Firebase перейдите в раздел Databases & Storage (Базы данных и хранилище) > Realtime Database (База данных в реальном времени) > Data (Данные).

  2. В раскрывающемся меню выберите Создать базу данных.

  3. Настройте ссылку на базу данных и Security Rules, а затем нажмите ОК.

Повторите эти действия, чтобы создать нужное количество экземпляров базы данных. У каждого экземпляра базы данных есть собственный набор Firebase Realtime Database Security Rules, поэтому вы можете точно настроить доступ к своим данным.

Вы можете создавать экземпляры баз данных и управлять ими в консоли Firebase или с помощью Realtime Database Management REST API.

Управление определенными экземплярами и взаимодействие с ними с помощью CLI

Управлять определенными экземплярами Realtime Database и взаимодействовать с ними можно с помощью интерфейса командной строки Firebase.

По умолчанию команды CLI взаимодействуют с экземпляром базы данных default. Однако вы можете взаимодействовать с экземпляром базы данных, не используемым по умолчанию, с помощью флага --instance DATABASE_NAME.

Например, чтобы запустить профилировщик для экземпляра базы данных с названием my-example-shard.firebaseio.com, используйте следующую команду:

firebase database:profile --instance "my-example-shard"

Флаг --instance поддерживается следующими командами:

  • firebase database:get
  • firebase database:profile
  • firebase database:push
  • firebase database:remove
  • firebase database:set
  • firebase database:update

Измените и разверните Realtime Database Security Rules для каждого экземпляра

Убедитесь, что Realtime Database Security Rules разрешают соответствующий доступ к каждому экземпляру базы данных в вашем проекте. У каждой базы данных есть собственный набор правил, которые можно изменять и развертывать в консоли Firebase или с помощью интерфейса командной строки Firebase.

  • Чтобы изменить и развернуть правила из консоли Firebase, выполните следующие действия:

    1. В консоли Firebase перейдите в раздел Databases & Storage (Базы данных и хранилище) > Realtime Database (База данных реального времени) > Rules (Правила).

    2. Выберите базу данных, которую нужно изменить, и измените правила.

  • Чтобы изменить и развернуть правила с помощью CLI Firebase, выполните следующие действия:

    1. Измените правила в файлах правил для экземпляров базы данных (например, foo.rules.json).

    2. Создайте и примените цели развертывания, чтобы связать базы данных, использующие один и тот же файл правил. Пример:

      firebase target:apply database main my-db-1 my-db-2
      firebase target:apply database other my-other-db-3

    3. Добавьте в файл конфигурации firebase.json цели развертывания:

      {
        "database": [
          {"target": "main", "rules": "foo.rules.json"},
          {"target": "other", "rules": "bar.rules.json"}
        ]
      }
      
    4. Выполните команду развертывания:

      firebase deploy

Редактируйте и развертывайте правила в одном и том же месте. Развертывание правил из интерфейса командной строки Firebase отменяет все изменения, внесенные в консоли Firebase, а редактирование правил непосредственно в консоли Firebase отменяет все недавние изменения, развернутые через интерфейс командной строки Firebase.

Как подключить приложение к нескольким экземплярам базы данных

Используйте ссылку на базу данных, чтобы получить доступ к данным, хранящимся в дополнительных экземплярах базы данных. Вы можете получить ссылку на определенный экземпляр базы данных по URL или приложению. Если вы не укажете URL, вы получите ссылку на экземпляр базы данных приложения по умолчанию.

Web

import { initializeApp } from "firebase/app";
import { getDatabase } from "firebase/database";

const app1 = initializeApp({
  databaseURL: "https://testapp-1234-1.firebaseio.com"
});

const app2 = initializeApp({
  databaseURL: "https://testapp-1234-2.firebaseio.com"
}, 'app2');

// Get the default database instance for an app1
const database1 = getDatabase(app1);

// Get a database instance for app2
const database2 = getDatabase(app2);

Web

const app1 = firebase.initializeApp({
  databaseURL: "https://testapp-1234-1.firebaseio.com"
});

const app2 = firebase.initializeApp({
  databaseURL: "https://testapp-1234-2.firebaseio.com"
}, 'app2');

// Get the default database instance for an app1
var database1 = firebase.database();

// Get a database instance for app2
var database2 = firebase.database(app2);
Swift
Примечание. Эта функция Firebase недоступна для блиц-приложений.
// Get the default database instance for an app
var ref: DatabaseReference!

ref = Database.database().reference()
// Get a secondary database instance by URL var ref: DatabaseReference! ref = Database.database("https://testapp-1234.firebaseio.com").reference()
Objective-C
Примечание. Эта функция Firebase недоступна для блиц-приложений.
// Get the default database instance for an app
@property (strong, nonatomic) FIRDatabaseReference *ref;

self.ref = [[FIRDatabase database] reference];
// Получение экземпляра дополнительной базы данных по URL @property (strong, nonatomic) FIRDatabaseReference *ref; self.ref = [[FIRDatabase databaseWithURL:@"https://testapp-1234.firebaseio.com"] reference];

Kotlin

// Get the default database instance for an app
val primary = Firebase.database.reference

// Get a secondary database instance by URL
val secondary = Firebase.database("https://testapp-1234.firebaseio.com").reference

Java

// Get the default database instance for an app
DatabaseReference primary = FirebaseDatabase.getInstance()
        .getReference();

// Get a secondary database instance by URL
DatabaseReference secondary = FirebaseDatabase.getInstance("https://testapp-1234.firebaseio.com")
        .getReference();

Оптимизируйте подключения к каждой базе данных

Если каждому клиенту необходимо подключиться к нескольким базам данных во время сеанса, вы можете уменьшить количество одновременных подключений к каждому экземпляру базы данных, подключаясь к каждому экземпляру базы данных только на то время, которое необходимо.

Получить больше советов

Если вам нужна помощь с сегментированием данных по нескольким экземплярам базы данных, обратитесь к экспертам Firebase на канале Slack или на сайте Stack Overflow.