Используйте Firebase в динамических веб-приложениях с SSR (серверный рендеринг), используйте Firebase в динамических веб-приложениях с SSR (серверный рендеринг)

Если вы работали с Firebase JS SDK или другими клиентскими SDK Firebase, вы, вероятно, знакомы с интерфейсом FirebaseApp и тем, как использовать его для настройки экземпляров приложений. Для упрощения аналогичных операций на стороне сервера Firebase предоставляет FirebaseServerApp .

FirebaseServerApp — это вариант FirebaseApp , предназначенный для использования в средах серверного рендеринга (SSR). Он включает инструменты для продолжения сессий Firebase, охватывающих как клиентский, так и серверный рендеринг. Эти инструменты и стратегии могут помочь улучшить динамические веб-приложения, созданные с помощью Firebase и развернутые в средах Google, таких как Firebase App Hosting .

Используйте FirebaseServerApp для:

  • В отличие от Firebase Admin SDK, который предоставляет полные права администратора, серверный код выполняется в контексте пользователя .
  • Включите использование App Check в средах SSR.
  • Продолжить сессию аутентификации Firebase, созданную на стороне клиента.

Жизненный цикл FirebaseServerApp

Фреймворки серверного рендеринга (SSR) и другие среды выполнения, не использующие браузеры, такие как облачные рабочие процессы, оптимизируют время инициализации за счет повторного использования ресурсов в нескольких выполнениях. FirebaseServerApp разработан для работы в таких средах с использованием механизма подсчета ссылок. Если приложение вызывает initializeServerApp с теми же параметрами, что и предыдущий initializeServerApp , оно получает тот же экземпляр FirebaseServerApp , который уже был инициализирован. Это сокращает ненужные накладные расходы на инициализацию и выделение памяти. Когда вызывается deleteApp для экземпляра FirebaseServerApp , он уменьшает счетчик ссылок, и экземпляр освобождается после того, как счетчик ссылок достигнет нуля.

Очистка экземпляров FirebaseServerApp

Определить, когда следует вызывать deleteApp для экземпляра FirebaseServerApp , может быть непросто, особенно если вы выполняете множество асинхронных операций параллельно. Поле releaseOnDeref в FirebaseServerAppSettings помогает упростить этот процесс. Если вы присвоите releaseOnDeref ссылку на объект с временем жизни, равным времени жизни запроса (например, объект заголовков SSR-запроса), FirebaseServerApp уменьшит количество ссылок, когда фреймворк освободит объект заголовка. Это автоматически очистит ваш экземпляр FirebaseServerApp .

Вот пример использования releaseOnDeref :

/// Next.js
import { headers } from 'next/headers'
import { FirebaseServerAppSettings, initializeServerApp} from "@firebase/app";

export default async function Page() {
  const headersObj = await headers();
  appSettings.releaseOnDeref = headersObj;
  let appSettings: FirebaseServerAppSettings = {};
  const serverApp = initializeServerApp(firebaseConfig, appSettings);
  ...
}

Возобновить авторизованные сессии, созданные на стороне клиента.

Когда экземпляр FirebaseServerApp инициализируется токеном Auth ID, это обеспечивает связь между аутентифицированными пользовательскими сессиями в средах клиентского рендеринга (CSR) и серверного рендеринга (SSR). Экземпляры Firebase Auth SDK, инициализированные объектом FirebaseServerApp , содержащим токен Auth ID, попытаются выполнить вход пользователя при инициализации без необходимости вызова каких-либо методов входа в систему со стороны приложения.

Предоставление токена Auth ID позволяет приложениям использовать любой из методов авторизации Auth на стороне клиента, гарантируя продолжение сессии на стороне сервера, даже для тех методов авторизации, которые требуют взаимодействия с пользователем. Кроме того, это позволяет перенести ресурсоемкие операции на сервер, такие как запросы Firestore с подтверждением аутентификации, что должно улучшить производительность отрисовки вашего приложения.

/// Next.js
import { initializeServerApp } from "firebase/app";
import { getAuth } from "firebase/auth";

// Replace the following with your app's
// Firebase project configuration
const firebaseConfig = {
  // ...
};

const firebaseServerAppSettings = {
  authIdToken: token  // See "Pass client tokens to the server side
                      // rendering phase" for an example on how transmit
                      // the token from the client and the server.
}

const serverApp =
  initializeServerApp(firebaseConfig,
                      firebaseServerAppSettings);
const serverAuth = getAuth(serverApp);

// FirebaseServerApp and Auth will now attempt
// to sign in the current user based on provided
// authIdToken.

Используйте проверку приложений в средах SSR.

Проверка приложений с помощью App Check основана на использовании экземпляра SDK App Check, который SDK Firebase используют для внутреннего вызова getToken . Полученный токен затем включается в запросы ко всем сервисам Firebase, что позволяет бэкэнду проверять приложение.

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

FirebaseServerApp предлагает альтернативный вариант. Если во время инициализации FirebaseServerApp предоставляется сгенерированный клиентом токен App Check, он будет использоваться SDK продуктов Firebase при вызове сервисов Firebase, что устраняет необходимость в экземпляре SDK App Check.

/// Next.js
import { initializeServerApp } from "firebase/app";

// Replace the following with your app's
// Firebase project configuration
const firebaseConfig = {
  // ...
};

const firebaseServerAppSettings = {
  appCheckToken: token // See "Pass client tokens to the server side
                       // rendering phase" for an example on how transmit
                       // the token from the client and the server.
}

const serverApp =
  initializeServerApp(firebaseConfig,
                      firebaseServerAppSettings);

// The App Check token will now be appended to all Firebase service requests.

Передайте клиентские токены на этап рендеринга на стороне сервера.

Для передачи аутентифицированных токенов Auth ID (и токенов App Check) от клиента к этапу рендеринга на стороне сервера (SSR) используется сервис-воркер. Этот подход предполагает перехват запросов fetch, запускающих SSR, и добавление токенов в заголовки запроса.

Для получения примера реализации сервис-воркера Firebase Auth обратитесь к разделу «Управление сессиями с помощью сервис-воркеров» . Также см. раздел «Изменения на стороне сервера» для кода, демонстрирующего, как извлекать эти токены из заголовков для использования при инициализации FirebaseServerApp .