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

NextJS中getServerSideProps调用UseContext返回null报错求助

解决Next.js中getServerSideProps调用Auth Context报错的问题

问题说明

在登录、数据库交互等客户端场景中能正常使用Auth Context,但在getServerSideProps或自定义API路由中调用UseAuth()时,出现报错:

TypeError: Cannot read properties of null (reading 'useContext')

报错原因

  • React的useContext是客户端专属的React钩子,只能在React组件或自定义钩子的顶层调用,不能在服务器端的非React上下文环境中执行。
  • UseAuth()本质是封装了useContext调用,而getServerSideProps是Next.js的服务器端渲染函数(运行在Node.js环境,无React上下文),自定义API路由同样是服务器端的Node.js环境,直接调用UseAuth()必然触发上下文不存在的错误。

解决方案

场景1:在getServerSideProps中获取用户信息

需要通过请求的Cookie获取Firebase认证的会话信息,用Firebase Admin SDK验证并拿到用户数据:

  1. 安装Firebase Admin SDK
npm install firebase-admin
  1. 配置Firebase Admin SDK
    在项目根目录创建firebase-admin.js:
import admin from 'firebase-admin';

if (!admin.apps.length) {
  admin.initializeApp({
    credential: admin.credential.cert({
      projectId: process.env.NEXT_PUBLIC_FIREBASE_PROJECT_ID,
      clientEmail: process.env.FIREBASE_CLIENT_EMAIL,
      privateKey: process.env.FIREBASE_PRIVATE_KEY.replace(/\\n/g, '\n'),
    }),
    databaseURL: `https://${process.env.NEXT_PUBLIC_FIREBASE_PROJECT_ID}.firebaseio.com`,
  });
}

export default admin;
  1. 修改getServerSideProps逻辑
import admin from '../firebase-admin';

export async function getServerSideProps(context) {
  let allDocs = [];
  let avgDocs = [];
  let currentUser = null;

  // 从请求Cookie中提取Firebase会话Cookie
  const sessionCookie = context.req.cookies.__session;

  if (sessionCookie) {
    try {
      // 验证会话Cookie,获取用户信息
      const decodedClaims = await admin.auth().verifySessionCookie(sessionCookie, true);
      currentUser = { uid: decodedClaims.uid, email: decodedClaims.email };

      // 这里可以用currentUser查询数据库,填充allDocs和avgDocs
      // 示例:
      // const userDoc = await admin.firestore().doc(`users/${currentUser.uid}`).get();
      // if (userDoc.exists()) {
      //   // 处理数据...
      // }
    } catch (error) {
      // Cookie无效/过期,跳转登录页
      return {
        redirect: {
          destination: '/',
          permanent: false,
        },
      };
    }
  } else {
    // 无会话Cookie,跳转登录页
    return {
      redirect: {
        destination: '/',
        permanent: false,
      },
    };
  }

  return {
    props: { allDocs, avgDocs, currentUser },
  };
}
  1. 客户端登录时设置会话Cookie
    修改auth-context.js中的登录函数,添加会话Cookie设置:
async function login(email, password) {
  return signInWithEmailAndPassword(auth, email, password)
    .then(async (result) => {
      const user = result.user;
      // 获取ID Token并创建会话Cookie
      const idToken = await user.getIdToken();
      const expiresIn = 60 * 60 * 24 * 5; // 有效期5天
      const sessionCookie = await auth.createSessionCookie(idToken, { expiresIn });
      // 设置Cookie(生产环境开启secure)
      document.cookie = `__session=${sessionCookie}; max-age=${expiresIn}; path=/; ${process.env.NODE_ENV === 'production' ? 'secure; ' : ''}HttpOnly; SameSite=Lax`;
      
      await userToDb(user);
      router.push('/portfolio');
      return user;
    }).catch((error) => {
      console.error(error);
    });
}

同时修改logout函数清除Cookie:

function logout() {
  // 清除会话Cookie
  document.cookie = '__session=; max-age=0; path=/';
  router.push('/');
  return signOut(auth);
}

场景2:在自定义API路由中获取用户信息

逻辑和getServerSideProps一致,用Admin SDK验证Cookie:

// pages/api/your-api.js
import admin from '../../firebase-admin';

export default async function handler(req, res) {
  const sessionCookie = req.cookies.__session;

  if (!sessionCookie) {
    return res.status(401).json({ message: '未授权' });
  }

  try {
    const decodedClaims = await admin.auth().verifySessionCookie(sessionCookie, true);
    const currentUser = { uid: decodedClaims.uid, email: decodedClaims.email };
    // 执行你的API业务逻辑
    res.status(200).json({ user: currentUser });
  } catch (error) {
    res.status(401).json({ message: '认证失效' });
  }
}

注意事项

  • 禁止在服务器端的非React环境中调用任何React钩子(useContext、useState等),这违反React钩子的使用规则。
  • Firebase Admin的配置信息(clientEmail、privateKey)需存储在环境变量中,切勿硬编码到代码里。
  • 生产环境必须开启Cookie的secure属性,确保通过HTTPS传输。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.08 00:30:55