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

解决NextAuth useSession()延迟致页面加载显示错误会话信息问题

解决方案

1. 利用useSession的状态等待会话就绪

next-auth的useSession会返回status字段,取值包括loading、authenticated、unauthenticated。我们可以等待会话状态明确后再发起请求,避免在session未就绪时调用错误接口,同时减少重复请求。

修改代码如下:

const { data: session, status, update } = useSession() // 解构出会话状态

const getProductsByBrand = async () => {
  // 会话未加载完成时直接返回,不发起请求
  if (status === "loading") return;
  
  setLoading(true);
  const request = new GetProductsRequest()
  request.setBrandid((brandId as string) || '')
  const pageReq = new PageRequest()
  pageReq.setPage(page - 1)
  pageReq.setPagesize(pageSize)
  request.setPaging(pageReq)
  request.setLocale(router.locale || '')
  
  let res;
  if (session?.user?.id) {
    request.setUserid(session.user.id)
    res = await ProductService.getProducts(request, getMetaData(session.user.accessToken))
  } else {
    res = await ProductService.getProductsPublic(request, {})
  }
  
  if (res.getProductsList()?.length > 0) {
    // 处理数据逻辑
  }
  setLoading(false)
}

// 将status和session加入依赖,确保会话状态变化时重新请求
useEffect(() => {
  getProductsByBrand()
}, [brandId, session, status])

2. 改用Next.js服务器组件(推荐)

Next.js 14的App Router优先推荐服务器组件,服务器端可以通过getServerSession同步获取会话信息,完全避免客户端的会话延迟问题。

示例代码(App Router服务器组件):

// app/products/[brandId]/page.tsx
import { getServerSession } from "next-auth/next"
import { authOptions } from "@/app/api/auth/[...nextauth]/route"
import ProductService from "@/services/ProductService"

export default async function ProductsPage({ params }: { params: { brandId: string } }) {
  const session = await getServerSession(authOptions)
  const brandId = params.brandId
  const page = 1 // 根据实际路由/搜索参数获取页码
  const pageSize = 10
  const locale = "zh-CN" // 根据实际locale配置获取

  const request = new GetProductsRequest()
  request.setBrandid(brandId)
  const pageReq = new PageRequest()
  pageReq.setPage(page - 1)
  pageReq.setPagesize(pageSize)
  request.setPaging(pageReq)
  request.setLocale(locale)
  
  let res;
  if (session?.user?.id) {
    request.setUserid(session.user.id)
    res = await ProductService.getProducts(request, getMetaData(session.user.accessToken))
  } else {
    res = await ProductService.getProductsPublic(request, {})
  }

  const products = res.getProductsList() || []

  return (
    <div>
      {/* 渲染产品列表 */}
      {products.map(product => (
        <div key={product.getId()}>{product.getName()}</div>
      ))}
    </div>
  )
}

3. 取消重复请求(客户端组件补充优化)

如果必须保留客户端组件,可以使用AbortController在会话状态变化时取消未完成的请求,避免重复请求浪费资源:

const { data: session, status, update } = useSession()
const abortControllerRef = useRef<AbortController | null>(null)

const getProductsByBrand = async () => {
  if (status === "loading") return;
  
  // 取消之前未完成的请求
  if (abortControllerRef.current) {
    abortControllerRef.current.abort()
  }
  const abortController = new AbortController()
  abortControllerRef.current = abortController
  
  setLoading(true)
  const request = new GetProductsRequest()
  request.setBrandid((brandId as string) || '')
  const pageReq = new PageRequest()
  pageReq.setPage(page - 1)
  pageReq.setPagesize(pageSize)
  request.setPaging(pageReq)
  request.setLocale(router.locale || '')
  
  try {
    let res;
    if (session?.user?.id) {
      request.setUserid(session.user.id)
      res = await ProductService.getProducts(request, getMetaData(session.user.accessToken), {
        signal: abortController.signal // 传递取消信号
      })
    } else {
      res = await ProductService.getProductsPublic(request, {}, {
        signal: abortController.signal
      })
    }
    
    if (res.getProductsList()?.length > 0) {
      // 处理数据逻辑
    }
  } catch (error) {
    // 忽略取消请求的错误
    if (error.name !== "AbortError") {
      // 处理其他业务错误
    }
  } finally {
    setLoading(false)
    abortControllerRef.current = null
  }
}

useEffect(() => {
  getProductsByBrand()
  
  // 组件卸载时取消请求
  return () => {
    if (abortControllerRef.current) {
      abortControllerRef.current.abort()
    }
  }
}, [brandId, session, status])

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.05 01:33:37