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

Next SSR:如何重定向至登录页并传递登录失败错误数据

登录失败重定向时传递错误信息的实现方案

问题场景

开发登录页面时,需要在登录失败后重定向回当前登录页并展示错误提示,但一直没法实现。想知道重定向时怎么同时传递数据。

现有代码:

服务器端 Action 代码

'use server'

import { revalidatePath } from 'next/cache'
import { redirect } from 'next/navigation'
import { createClient } from 'utils/supabase/server'

export async function login() {
  const supabase = await createClient()

  const { data, error } = await supabase.auth.signInAnonymously()

  if (error) {
    redirect('/anonlogin');
  } else {
    revalidatePath('/', 'layout')
    redirect('/')
  }
}

登录页面组件代码

import { login } from '@/anonlogin/actions'
import styles from '@/components/global/button.module.css'

export default function LoginPage() {
  return (
    <div>
      <form>
        <button className={styles.button} formAction={login}>Log in</button>
      </form>
    </div>
  )
}

可行解决方案

方案1:URL查询参数传错误信息

这是最直接简单的办法,把错误信息编码后拼到URL里,页面加载时读取显示。

修改服务器端 Action

'use server'

import { revalidatePath } from 'next/cache'
import { redirect } from 'next/navigation'
import { createClient } from 'utils/supabase/server'

export async function login() {
  const supabase = await createClient()

  const { data, error } = await supabase.auth.signInAnonymously()

  if (error) {
    // 编码错误信息避免特殊字符干扰
    const encodedError = encodeURIComponent(error.message)
    redirect(`/anonlogin?error=${encodedError}`);
  } else {
    revalidatePath('/', 'layout')
    redirect('/')
  }
}

修改登录页面组件读取参数

在App Router里,页面组件可以直接接收searchParams props来获取URL参数:

import { login } from '@/anonlogin/actions'
import styles from '@/components/global/button.module.css'

export default function LoginPage({ searchParams }) {
  // 解码并获取错误信息
  const loginError = searchParams.error ? decodeURIComponent(searchParams.error) : null

  return (
    <div>
      {/* 显示错误提示 */}
      {loginError && (
        <div style={{ color: '#dc2626', marginBottom: '16px', padding: '8px', border: '1px solid #fecdd3', borderRadius: '4px' }}>
          {loginError}
        </div>
      )}
      <form>
        <button className={styles.button} formAction={login}>Log in</button>
      </form>
    </div>
  )
}

方案2:用Cookie临时存储错误信息

如果不想在URL里暴露错误内容,就用Cookie临时存,页面加载后读取再删掉。

修改服务器端 Action

'use server'

import { revalidatePath } from 'next/cache'
import { redirect } from 'next/navigation'
import { createClient } from 'utils/supabase/server'
import { cookies } from 'next/headers'

export async function login() {
  const supabase = await createClient()
  const cookieStore = cookies()

  const { data, error } = await supabase.auth.signInAnonymously()

  if (error) {
    // 设置有效期1分钟的临时Cookie,只在当前路由生效
    cookieStore.set('login_error', encodeURIComponent(error.message), {
      maxAge: 60,
      path: '/anonlogin',
      httpOnly: false, // 允许前端读取
      secure: process.env.NODE_ENV === 'production'
    })
    redirect('/anonlogin');
  } else {
    revalidatePath('/', 'layout')
    redirect('/')
  }
}

修改登录页面组件读取Cookie

需要改成客户端组件才能操作浏览器Cookie:

'use client'

import { login } from '@/anonlogin/actions'
import styles from '@/components/global/button.module.css'
import { useEffect, useState } from 'react'

export default function LoginPage() {
  const [loginError, setLoginError] = useState(null)

  useEffect(() => {
    // 从Cookie中提取错误信息
    const errorCookie = document.cookie.split('; ')
      .find(row => row.startsWith('login_error='))
      ?.split('=')[1]
    
    if (errorCookie) {
      const decodedError = decodeURIComponent(errorCookie)
      setLoginError(decodedError)
      // 读取后立即删除Cookie,避免重复显示
      document.cookie = 'login_error=; path=/anonlogin; max-age=0'
    }
  }, [])

  return (
    <div>
      {loginError && (
        <div style={{ color: '#dc2626', marginBottom: '16px', padding: '8px', border: '1px solid #fecdd3', borderRadius: '4px' }}>
          {loginError}
        </div>
      )}
      <form>
        <button className={styles.button} formAction={login}>Log in</button>
      </form>
    </div>
  )
}

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.15 09:07:37