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

React fetch请求登录接口报401及Unexpected end of input错误排查

React登录接口401及JSON解析报错解决方案

报错信息

  • 接口请求返回401 Unauthorized未授权状态
  • 控制台抛出未捕获Promise异常:SyntaxError: Unexpected end of input
  • 异常触发位置为登录逻辑中result = await result.json()代码行

问题根因

  • 错误配置mode: 'no-cors':fetch的no-cors模式返回的是opaque不透明响应,前端JS无权读取响应体内容,调用.json()解析不可读/空响应体直接触发语法错误。这个模式仅适用于埋点上报这类不需要读取响应的场景,完全不适合登录这类需要拿接口返回值的业务。
  • no-cors模式下自定义请求头不生效:你设置的Content-Type: application/json属于CORS非简单请求头,no-cors模式下会被浏览器自动剔除,后端收到的请求不是JSON格式,参数解析失败直接返回401。
  • 路由跳转写法错误:React Router v6版本不存在Navigate.push的调用方式,需要通过useNavigate钩子生成跳转方法。
  • 缺少响应状态校验和异常捕获:接口返回401等错误状态时,响应体可能不是合法JSON格式,直接调用.json()必然报错。

修复方案

  1. 删除fetch配置中的mode: 'no-cors'项,使用默认cors模式,同时协调后端为登录接口配置CORS响应头,允许前端所在域名跨域访问。
  2. 增加响应状态判断,只有状态码为2xx的成功响应才执行JSON解析,401状态单独做用户名密码错误提示。
  3. 修正路由跳转逻辑,使用useNavigate钩子实现路由跳转。
  4. 增加try/catch异常捕获,避免未处理的Promise异常。

修正后代码

import { useEffect, useState } from 'react';
import { useNavigate } from 'react-router-dom';

function Login() {
  const [Username, setUsername] = useState('');
  const [Password, setPassword] = useState('');
  const navigate = useNavigate();

  useEffect(() => {
    if (localStorage.getItem('user-info')) {
      navigate('/nxt');
    }
  }, [navigate]);

  async function login() {
    try {
      const reqParams = { Username, Password };
      const res = await fetch('http://api.kyc365pro.com:6061/login', {
        method: 'POST',
        headers: {
          'Content-Type': 'application/json',
          Accept: 'application/json',
        },
        body: JSON.stringify(reqParams),
      });

      // 处理异常状态
      if (!res.ok) {
        if (res.status === 401) {
          alert('用户名或密码错误');
          return;
        }
        throw new Error(`请求失败,状态码:${res.status}`);
      }

      const result = await res.json();
      localStorage.setItem('user-info', JSON.stringify(result));
      navigate('/nxt');
    } catch (err) {
      console.error('登录异常:', err);
      alert('登录失败,请检查网络后重试');
    }
  }

  return (
    <div>
      <h1>Login page</h1>
      <label>Username</label>
      <input
        type='text'
        placeholder='Username'
        onChange={(e) => setUsername(e.target.value)}
      />
      <br />
      <label>Password</label>
      <input
        type='password'
        placeholder='Password'
        onChange={(e) => setPassword(e.target.value)}
      />
      <br />
      <button onClick={login}>Login</button>
    </div>
  );
}

export default Login

提示:如果修改后控制台报跨域错误,不要切回no-cors模式,必须由后端配置CORS规则解决,no-cors模式无法读取响应内容,不可能满足登录业务需求。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.29 10:57:27