到目前為止,我們已經建置好 Firebase 基礎設施(專案、應用程式、reCAPTCHA Enterprise 金鑰、App Check、Remote Config、Firebase AI Logic 以及 App Hosting),以啟用我們全新的 AI 功能。
現在,我們可以開始撰寫程式碼來將 Firebase 與 Angular 進行整合。我們將建立一個 ConfigService 來呼叫 Firebase API,藉此處理初始化、安全性與 Remote Config。
在應用程式初始化期間,會插入(Inject)ConfigService 來執行該邏輯。此外,Gemini 模型會在應用程式引導(Bootstrap)操作中提供,以支援 AI 功能。
npm i --save-exact firebase
如果您尚未安裝 firebase 相依套件,請先進行安裝。
此設定服務會呼叫 Firebase API 來處理下列任務:
使用由 Node.js 指令碼產生並寫入 public/ 資料夾的 Firebase 設定物件,來初始化 Firebase 應用程式。
初始化 App Check 並啟用 App Check 偵錯權杖(Debug Token)提供者。
匯入預設的 Firebase Remote Config 數值,並將其指派給 Remote Config 的 defaultConfig 屬性。
取得即時的 Firebase Remote Config 數值並將其啟用。
我們將在接下來的子章節中,逐步拆解主要的 initialize 方法。
import remoteConfigDefaults from '@/public/remote-config-defaults.json';
import { FirebaseApp, initializeApp } from 'firebase/app';
import { initializeAppCheck, ReCaptchaEnterpriseProvider } from 'firebase/app-check';
@Service()
export class ConfigService {
#app: FirebaseApp | undefined = undefined;
async initialize(): Promise<void> {
this.#app = initializeApp(firebaseConfig.app);
}
}
請記住,firebaseConfig 物件保有 app、recaptchaEnterpriseKey 以及 appCheckDebugToken 屬性。
{
"app": { ...api key, authDomain, .... },
"recaptchaEnterpriseKey": "6L...",
"appCheckDebugToken": "10..."
}
在該方法中,firebaseConfig.app 物件會被傳遞給 initializeApp 以初始化 Firebase App。
const isLocalhost = ['localhost', '127.0.0.1', '::1', '[::1]'].include(window.location.hostname);
const debugToken = firebaseConfig.appCheckDebugToken;
(globalThis as Record<string, unknown>)['FIREBASE_APPCHECK_DEBUG_TOKEN'] = isLocalhost ? debugToken || true : false;
initializeAppCheck(this.#app, {
provider: new ReCaptchaEnterpriseProvider(firebaseConfig.recaptchaEnterpriseKey),
isTokenAutoRefreshEnabled: true,
});
設定 firebaseConfig.appCheckDebugToken 允許您在本地開發期間,跨多個瀏覽器重複使用同一個 App Check 工作階段。若不進行此設定,每個瀏覽器都會產生各自的偵錯權杖,這需要您每次都手動到 Firebase 主控台(Console)進行註冊。
起初,firebaseConfig.appCheckDebugToken 是空白的。一旦產生權杖後,您必須更新 .env 中的 APP_FIREBASE_APPCHECK_DEBUG_TOKEN,並執行指令碼來重新產生 public/firebase.config.json。
Remote Config 的 JSON 檔案外觀應如下所示:
它至少包含代理平台後端位置、Gemini 模型名稱、Gemini TTS 模型名稱,以及是否使用存留期較短的權杖(Short-lived tokens)。
{
"geminiModelName": "gemini-3.8-flash",
"geminiTTSModelName": "gemini-3.1-flash-tts-preview",
"useLimitedUseAppCheckTokens": "false",
"vertexAILocation": "global"
}
從 public/remote-config-defaults.json 匯入鍵值組。
import remoteConfigDefaults from '@/public/remote-config-defaults.json';
import { fetchAndActivate, getRemoteConfig, getValue, RemoteConfig } from 'firebase/remote-config';
appConfig = {
useLimitedUseAppCheckTokens: remoteConfigDefaults.useLimitedUseAppCheckTokens === 'true',
vertexAILocation: remoteConfigDefaults.vertexAILocation,
geminiModelName: remoteConfigDefaults.geminiModelName,
};
this.#remoteConfig = getRemoteConfig(this.#app);
this.#remoteConfig.defaultConfig = remoteConfigDefaults;
appConfig 會以預設值進行初始化。這些數值將在應用程式引導操作中,用於建構 Firebase AI 後端與 Gemini 模型。
將預設值指派給 defaultConfig 屬性。如果 Firebase Remote Config API 無法取得即時數值,應用程式將會重導回(Fall back)使用預設值。
await fetchAndActivate(this.#remoteConfig);
const rc = this.#remoteConfig;
this.appConfig = {
vertexAILocation: getValue(rc, 'vertexAILocation').asString(),
useLimitedUseAppCheckTokens: getValue(rc, 'useLimitedUseAppCheckTokens').asBoolean(),
geminiModelName: getValue(rc, 'geminiModelName').asString(),
};
當成功取得 Remote Config 數值後,appConfig 便會以即時數值進行更新。
ConfigService 已完成,我們將在應用程式初始化期間呼叫 initialize 方法。
但我們目前仍缺少一個用於建構 Firebase AI 後端與 Gemini 模型的自訂提供者(Provider)。
Firebase AI 後端和 Gemini 模型非常適合作為單例(Singleton),因為它們只需實例化一次,即可在所有的服務呼叫中重複使用。
export const VISION_AI_MODEL = new InjectionToken('VISION_AI_MODEL');
export const AI_BACKEND = new InjectionToken('AI_BACKEND');
function getGenerativeAIModel(appConfig: AppRemoteConfig) {
return getGenerativeModel(inject(AI_BACKEND), {
model: appConfig.geminiModelName,
generationConfig: {
responseMimeType: 'application/json',
responseSchema: ImageAnalysisSchema,
thinkingConfig: {
thinkingLevel: appConfig.thinkingLevel,
includeThoughts: true,
},
},
safetySettings: SAFETY_SETTINGS,
tools: {
googleSearch: {},
},
});
}
export function provideFirebase() {
return makeEnvironmentProviders([
{
provide: AI_BACKEND,
useFactory: () => inject(ConfigService).aiBackend as AI,
},
{
provide: VISION_AI_MODEL,
useFactory: () => getGenerativeAIModel(inject(ConfigService).appConfig),
},
]);
}
AI_BACKEND 插入權杖會插入 Firebase AI 後端,而 VISION_AI_MODEL 則會插入 Gemini 3.8 flash 模型。
我們可以匯入該提供者,以提供後端和 Gemini 模型。
我們向 provideAppInitializer 提供一個函式,以插入 ConfigService 並呼叫 initialize 方法。provideFirebase 提供者則會包含在 providers 陣列中。
export const appConfig: ApplicationConfig = {
providers: [
... other providers ...
provideAppInitializer(async () => await inject(ConfigService).initialize()),
provideFirebase(),
],
};
為了簡化我的工作流程,我更進一步將 App Check 偵錯權杖指派給 global.FIREBASE_APPCHECK_DEBUG_TOKEN,從而免去了在不同瀏覽器類型之間管理不同權杖的繁瑣工作。
我們執行 ng serve 來在開發者工具(DevTool)主控台中尋找偵錯權杖,更新 .env,並將其複製以在 Firebase 主控台中進行註冊。

警告: 切勿向任何人透露此權杖,因為它會有效地繞過檢查,允許存取您的 Firebase 資源。
點擊左側選單中的 App Check,然後點擊 Apps 頁籤。該頁籤會列出所有的 Web 應用程式,且每個項目都有一個垂直三點按鈕。點擊該按鈕以開啟選單,並選取「Manage debug tokens」項目。

點擊 Add debug token 按鈕以註冊偵錯權杖。

現在,偵錯權杖即可跨瀏覽器工作階段共享。
今天就到這裡。明天我們將定義負責圖片轉文字(Image-to-text)任務的 Vision 服務。
相關資源:
Firebase AI Logic 官方文件
Firebase Remote Config 官方文件
Firebase App Check 官方文件
在網頁應用程式中使用帶有偵錯提供者的 App Check