ใช้ Firebase ในเว็บแอปแบบไดนามิกด้วย SSR (การแสดงผลฝั่งเซิร์ฟเวอร์)

หากเคยทํางานกับ Firebase JS SDK หรือ SDK ไคลเอ็นต์ Firebase อื่นๆ คุณอาจคุ้นเคยกับอินเทอร์เฟซ FirebaseApp และวิธีใช้เพื่อกําหนดค่าอินสแตนซ์แอป Firebase มี FirebaseServerApp เพื่อช่วยอำนวยความสะดวกในการดำเนินการที่คล้ายกันฝั่งเซิร์ฟเวอร์

FirebaseServerApp เป็นตัวแปรของ FirebaseApp สำหรับใช้ในสภาพแวดล้อมการแสดงผลฝั่งเซิร์ฟเวอร์ (SSR) รวมถึงเครื่องมือสำหรับดำเนินการเซสชัน Firebase ต่อซึ่งครอบคลุมการแสดงผลฝั่งไคลเอ็นต์ (CSR) / การแสดงผลฝั่งเซิร์ฟเวอร์ เครื่องมือและกลยุทธ์เหล่านี้จะช่วยปรับปรุงเว็บแอปแบบไดนามิกที่สร้างด้วย Firebase และนำไปใช้งานในสภาพแวดล้อมของ Google เช่น Firebase App Hosting

ใช้ FirebaseServerApp เพื่อดำเนินการต่อไปนี้

  • เรียกใช้โค้ดฝั่งเซิร์ฟเวอร์ภายในบริบท user ซึ่งต่างจาก Firebase Admin SDK ที่มีสิทธิ์การดูแลระบบอย่างเต็มรูปแบบ
  • เปิดใช้ App Check ในสภาพแวดล้อม SSR
  • ดำเนินการต่อในเซสชัน Firebase Auth ที่สร้างขึ้นบนไคลเอ็นต์

วงจรชีวิตของ FirebaseServerApp

เฟรมเวิร์กการแสดงผลฝั่งเซิร์ฟเวอร์ (SSR) และรันไทม์อื่นๆ ที่ไม่ใช่เบราว์เซอร์ เช่น เวิร์กเกอร์ระบบคลาวด์ จะเพิ่มประสิทธิภาพเวลาเริ่มต้นโดยนําทรัพยากรมาใช้ซ้ำในการเรียกใช้หลายครั้ง FirebaseServerApp ได้รับการออกแบบมาเพื่อรองรับสภาพแวดล้อมเหล่านี้โดยใช้กลไกการนับการอ้างอิง หากแอปเรียกใช้ initializeServerApp ด้วยพารามิเตอร์เดียวกันกับ initializeServerApp ก่อนหน้า แอปจะได้รับอินสแตนซ์ FirebaseServerApp เดียวกันกับที่เริ่มต้นแล้ว ซึ่งจะช่วยลดค่าใช้จ่ายในการเริ่มต้นที่ไม่จำเป็นและการจัดสรรหน่วยความจำ เมื่อเรียกใช้ deleteApp ในอินสแตนซ์ FirebaseServerApp ระบบจะลดจํานวนการอ้างอิง และระบบจะยกเลิกการจัดสรรอินสแตนซ์หลังจากที่จํานวนการอ้างอิงถึง 0

กําลังล้างข้อมูลอินสแตนซ์ 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 ช่วยให้แอปใช้วิธีการลงชื่อเข้าใช้ใดก็ได้ของ 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.

ใช้ App Check ในสภาพแวดล้อม SSR

การบังคับใช้ App Check อาศัยอินสแตนซ์ App Check SDK ที่ Firebase SDK ใช้เพื่อเรียก getToken ภายใน จากนั้นระบบจะรวมโทเค็นที่ได้ไว้ในคำขอไปยังบริการ Firebase ทั้งหมด ซึ่งจะช่วยให้แบ็กเอนด์ตรวจสอบแอปได้

อย่างไรก็ตาม เนื่องจาก App Check SDK ต้องใช้เบราว์เซอร์ในการเข้าถึงวิธีการตรวจสอบที่เฉพาะเจาะจงสำหรับการตรวจสอบแอป จึงไม่สามารถเริ่มต้นใช้งานในสภาพแวดล้อมเซิร์ฟเวอร์ได้

FirebaseServerApp มีทางเลือกอื่น หากระบุโทเค็น App Check ที่ลูกค้าสร้างขึ้นระหว่างการเริ่มต้นFirebaseServerApp SDK ของผลิตภัณฑ์ Firebase จะใช้โทเค็นดังกล่าวเมื่อเรียกใช้บริการ Firebase ซึ่งจะช่วยลดความจำเป็นในการใช้อินสแตนซ์ App Check SDK

/// 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) ให้ใช้ Service Worker แนวทางนี้เกี่ยวข้องกับการขัดขวางคำขอดึงข้อมูลซึ่งทริกเกอร์ SSR และใส่โทเค็นต่อท้ายส่วนหัวคำขอ

โปรดดูการจัดการเซสชันด้วย Service Worker เพื่อดูการใช้งานอ้างอิงสำหรับ Service Worker ของ Firebase Auth นอกจากนี้ โปรดดูการเปลี่ยนแปลงฝั่งเซิร์ฟเวอร์สําหรับโค้ดที่แสดงวิธีแยกวิเคราะห์โทเค็นเหล่านี้จากส่วนหัวเพื่อใช้ในFirebaseServerApp initialization