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

AJAX调用后端控制器后始终触发error函数的问题及解决方法

AJAX请求已到达后端但始终触发error回调的问题排查与解决

嘿,我之前也碰到过一模一样的问题!明明后端已经接收到请求并打印了日志,但前端就是死磕error回调,太让人头疼了。咱们来一步步拆解你的代码,找到问题根源。

你的现有代码

前端AJAX代码

<script> 
function showEmpDetails(empid) { 
    console.log(empid); 
    $.ajax({ 
        url: "employeeInfo", 
        type: "POST", 
        data: { empId: empid} , 
        success: function(data) { 
            console.log(data); 
            $("#employeeDetails").html(data); 
        }, 
        error: function () { 
            alert("error"); 
        } 
    }); 
} 
</script>

后端控制器代码

@RequestMapping(value = "/employeeInfo", method = RequestMethod.POST,produces = MediaType.APPLICATION_JSON_VALUE) 
public @ResponseBody String empInfo(@RequestParam("empId") int employeeId, Model model) { 
    Employee findById = employeeMapper.findById(employeeId); 
    model.addAttribute("employee", findById); 
    System.out.println("Hello"); 
    return "EMPINFO"; 
}

问题出在哪?

核心矛盾就在后端声明的返回类型和实际返回内容不匹配:

  • 你在@RequestMapping里设置了produces = MediaType.APPLICATION_JSON_VALUE,这相当于告诉前端:「我给你返回的是JSON格式的数据哦」
  • 但你实际返回的是纯字符串"EMPINFO",这根本不是合法的JSON(合法的JSON字符串需要被双引号包裹,比如"EMPINFO"才是,而你返回的是不带外层双引号的纯文本)

jQuery的AJAX默认会严格按照后端返回的Content-Type头来解析响应。当它看到Content-Type: application/json,就会尝试把响应内容当成JSON解析,结果解析失败,直接触发error回调——哪怕HTTP状态码是200(请求成功)。

另外还有个小冗余:你用了Model model并添加了属性,但因为加了@ResponseBody,Spring会直接把返回值序列化后发给前端,Model里的内容完全不会被用到,这个可以直接删掉。

怎么解决?

给你三个可行的方案,按需选择:

方案1:后端返回合法的JSON(推荐)

既然声明了返回JSON,就老老实实返回符合JSON规范的内容:

方式A:返回JSON格式的字符串

如果确实只需要返回EMPINFO这个标记,就把它包装成合法的JSON字符串:

@RequestMapping(value = "/employeeInfo", method = RequestMethod.POST,produces = MediaType.APPLICATION_JSON_VALUE) 
public @ResponseBody String empInfo(@RequestParam("empId") int employeeId) { 
    Employee findById = employeeMapper.findById(employeeId); 
    System.out.println("Hello"); 
    // 外层加双引号,变成合法的JSON字符串
    return "\"EMPINFO\""; 
}

方式B:直接返回实体对象(更实用)

如果你的目的是返回员工信息,直接返回Employee对象就行,Spring会自动帮你序列化为JSON:

@RequestMapping(value = "/employeeInfo", method = RequestMethod.POST,produces = MediaType.APPLICATION_JSON_VALUE) 
public @ResponseBody Employee empInfo(@RequestParam("empId") int employeeId) { 
    Employee findById = employeeMapper.findById(employeeId); 
    System.out.println("Hello"); 
    return findById; 
}

方案2:修改后端的produces,匹配实际返回类型

如果你确实只需要返回纯文本,那就把produces改成纯文本类型:

@RequestMapping(value = "/employeeInfo", method = RequestMethod.POST,produces = MediaType.TEXT_PLAIN_VALUE) 
public @ResponseBody String empInfo(@RequestParam("empId") int employeeId) { 
    Employee findById = employeeMapper.findById(employeeId); 
    System.out.println("Hello"); 
    return "EMPINFO"; 
}

方案3:前端指定dataType(不推荐,后端规范更重要)

你也可以在前端AJAX里强制指定dataType: "text",告诉jQuery不管后端返回的Content-Type是什么,都按纯文本解析:

$.ajax({ 
    url: "employeeInfo", 
    type: "POST", 
    data: { empId: empid},
    dataType: "text", // 新增这一行
    success: function(data) { 
        console.log(data); 
        $("#employeeDetails").html(data); 
    }, 
    error: function () { 
        alert("error"); 
    } 
}); 

额外排查技巧

以后碰到这类问题,打开浏览器开发者工具(F12),切换到Network标签,找到对应的请求:

  1. 看Response Headers里的Content-Type是不是和后端声明的一致
  2. 看Response里的内容是不是符合对应格式的要求(比如JSON有没有语法错误)
    这招能快速定位绝大多数前后端数据格式不匹配的问题。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.14 07:23:14