You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何解决Nuxt VueFire中Session Cookie与App Check及密钥限制的兼容问题?

解决Nuxt VueFire Session Cookie与App Check共存问题

问题背景

尝试在Nuxt项目中结合VueFire实现Session Cookie认证,核心配置如下:

// nuxt.config.ts
export default defineNuxtConfig({
  runtimeConfig: {
    public: {
      brandName: "",
      fbApiKey: "",
      fbAuthDomain: "",
      projectId: "",
      fbDefaultStorageBucket: "",
      fbMessagingSenderId: "",
      fbAppId: "",
      fbMeasurementId: "",
      gcpRecaptchaEnterpriseSiteKey: "",
    },
  },
  vuefire: {
    config: {
      apiKey: process.env.NUXT_PUBLIC_FB_API_KEY,
      authDomain: process.env.NUXT_PUBLIC_FB_AUTH_DOMAIN,
      projectId: process.env.NUXT_PUBLIC_PROJECT_ID,
      storageBucket: process.env.NUXT_PUBLIC_FB_DEFAULT_STORAGE_BUCKET,
      messagingSenderId: process.env.NUXT_PUBLIC_FB_MESSAGING_SENDER_ID,
      appId: process.env.NUXT_PUBLIC_FB_APP_ID,
      measurementId: process.env.NUXT_PUBLIC_FB_MEASUREMENT_ID,
    },
    auth: {
      enabled: true,
      sessionCookie: true,
    },
    appCheck: {
      debug: process.env.NODE_ENV !== "production",
      isTokenAutoRefreshEnabled: true,
      provider: "ReCaptchaEnterprise",
      key: process.env.NUXT_PUBLIC_GCP_RECAPTCHA_ENTERPRISE_SITE_KEY || "none",
    },
  },
})

遇到两个核心错误:

  1. 同时启用App Check和Session Cookie时,服务器端触发:
500
Firebase: Error (auth/firebase-app-check-token-is-invalid.).

at _fail (/Users/BenJackGill/Dev/seoturbo/node_modules/@firebase/auth/src/core/util/assert.ts:65:9)
at _performFetchWithErrorHandling (/Users/BenJackGill/Dev/seoturbo/node_modules/@firebase/auth/src/api/index.ts:210:9)
at process.processTicksAndRejections (node:internal/process/task_queues:95:5)
at _performSignInRequest (/Users/BenJackGill/Dev/seoturbo/node_modules/@firebase/auth/src/api/index.ts:231:27)
at Module.signInWithCustomToken (/Users/BenJackGill/Dev/seoturbo/node_modules/@firebase/auth/src/core/strategies/custom_token.ts:56:37)
at async ./node_modules/nuxt-vuefire/dist/runtime/auth/plugin-authenticate-user.server.mjs:36:135
  1. Firebase浏览器API密钥设置域名限制后,服务器端触发:
500
Firebase: Error (auth/requests-from-referer-<empty>-are-blocked.).

at _fail (/Users/BenJackGill/Dev/seoturbo/node_modules/@firebase/auth/src/core/util/assert.ts:65:9)
at _performFetchWithErrorHandling (/Users/BenJackGill/Dev/seoturbo/node_modules/@firebase/auth/src/api/index.ts:210:9)
at process.processTicksAndRejections (node:internal/process/task_queues:95:5)
at _performSignInRequest (/Users/BenJackGill/Dev/seoturbo/node_modules/@firebase/auth/src/api/index.ts:231:27)
at Module.signInWithCustomToken (/Users/BenJackGill/Dev/seoturbo/node_modules/@firebase/auth/src/core/strategies/custom_token.ts:56:37)
at async ./node_modules/nuxt-vuefire/dist/runtime/auth/plugin-authenticate-user.server.mjs:36:135

同时,尝试跳过服务器端路由中间件无效,中间件代码如下:

// middleware/auth.ts
export default defineNuxtRouteMiddleware(async (to, from) => {
  // 尝试跳过服务器端执行但无效
  // if (import.meta.server) {
  //   return;
  // }

  const user = await getCurrentUser();

  if (!user) {
    return navigateTo({
      path: "/login",
    });
  }
});

解决方案

1. 隔离App Check的客户端与服务器逻辑

App Check调试令牌仅在浏览器环境有效,服务器端需禁用App Check或使用Admin SDK验证:

// nuxt.config.ts
vuefire: {
  // ...其他配置
  appCheck: {
    // 仅在客户端启用App Check
    enabled: process.client,
    debug: process.env.NODE_ENV !== "production" && process.client,
    isTokenAutoRefreshEnabled: true,
    provider: "ReCaptchaEnterprise",
    key: process.env.NUXT_PUBLIC_GCP_RECAPTCHA_ENTERPRISE_SITE_KEY || "none",
  },
}

2. 解决API密钥域名限制

  • 为服务器端单独创建无域名限制的Firebase API密钥,或在控制台将服务器IP加入允许列表;
  • 配置Firebase Admin SDK用于服务器端Session Cookie验证:在.env中添加服务账号信息:
FIREBASE_SERVICE_ACCOUNT='{"type": "service_account", "project_id": "...", ...}'

VueFire会自动使用Admin SDK处理服务器端认证,规避客户端API密钥的域名限制。

3. 修正路由中间件

确保中间件在服务器端正确放行,或使用VueFire提供的响应式用户状态:

// middleware/auth.ts
export default defineNuxtRouteMiddleware(async (to, from) => {
  // 服务器端直接放行,依赖VueFire自动处理Session Cookie认证
  if (import.meta.server) {
    return;
  }

  // 客户端验证用户状态
  const user = await getCurrentUser();
  if (!user) {
    return navigateTo("/login");
  }
});

若需服务器端验证,改用useCurrentUser()(自动处理服务器端 hydration):

// middleware/auth.ts
export default defineNuxtRouteMiddleware(async (to, from) => {
  const user = useCurrentUser();

  // 服务器端等待用户状态 hydration
  if (import.meta.server && !user.value) {
    return navigateTo("/login");
  }

  // 客户端验证
  if (import.meta.client && !await getCurrentUser()) {
    return navigateTo("/login");
  }
});

内容的提问来源于stack exchange,提问作者TinyTiger

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.24 06:46:02