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

Razor MVC中JS Ajax调用Action发布后返回302错误如何解决

问题产生原因

302是HTTP协议中的重定向状态码,你的场景下触发302的原因主要有3个:

  • 接口返回逻辑不匹配Ajax调用规则
    你在服务端Action里无论执行成功还是失败,都返回RedirectToAction结果,这个结果天生会让MVC框架返回302状态码,附带目标地址到Location响应头。普通表单提交可以正常识别这个响应自动跳转,但Ajax请求默认只会自动跟随重定向拿到最终页面的HTML内容,和你前端配置的dataType: "json"预期的JSON格式完全不匹配,就会触发请求失败。
  • Session空值触发认证拦截
    你代码里直接读取Session里的门店编码、用户名,没有做空值判断。发布环境IIS的Session默认超时时间是20分钟,用户停留时间过长Session过期后,请求还没走到你的Buy方法逻辑,就会被框架的认证/授权模块拦截,自动返回302跳转到登录页,这也是发布后才频繁出现问题的核心原因——本地调试时Session一直有效,不会触发这个拦截。
  • 硬编码路径适配性差
    前端写死了请求路径/TessileCart/Buy,如果发布时站点部署在IIS虚拟目录下(不是网站根路径),这个路径会匹配不到对应的路由,被IIS错误模块拦截重定向到404页/首页,也会返回302状态码。
解决方法

根据你的业务场景二选一即可:

方案1:保留Ajax调用,修正前后端交互逻辑(推荐)

  • 服务端修改:不要给Ajax请求返回重定向结果,统一返回JSON格式的状态与跳转地址,加上Session空值校验,避免被框架拦截。
    修正后的服务端代码参考:
    [HttpPost]
    public ActionResult Buy(string offerType, string requestPath, string currency)
    {
        try
        {
            // 提前校验Session有效性,避免空引用触发框架跳转
            if (Session[Global.CodStore] == null || Session[Global.UserName] == null)
            {
                return Json(new { success = false, redirectUrl = Url.Action("Login", "Account"), msg = "登录状态已过期,请重新登录" });
            }
            decimal codStore = Convert.ToDecimal(Session[Global.CodStore]);
            string userName = Session[Global.UserName].ToString();
          
            cartRep.CheckOut(codStore, userName, System.Web.HttpContext.Current, currency);
            return Json(new { success = true, redirectUrl = Url.Action("Index", "Home", new { offerType = offerType }) });
        }
        catch (Exception ex)
        {
            Global.log.WriteLog(this.GetType().Name, "Buy", "", ex, Session[Global.UserName]?.ToString() ?? "Anonymous");
            return Json(new { success = false, redirectUrl = Url.Action("Index", "Cart", new { offerType = offerType, requestPath = requestPath, error = Global.ErrorMex }) });
        }
    }
    
  • 前端修改:用Razor内置的Url.Action生成请求地址适配虚拟目录部署,去掉多余的contentType配置(你没有传JSON格式的请求体,不需要这个头),根据服务端返回的结果执行跳转。
    修正后的前端代码参考:
    $("#buyButton").click(function () {
        $.ajax({
            type: "POST",
            url: '@Url.Action("Buy", "TessileCart")',
            data: {
                offerType: '@ViewBag.offerType',
                requestPath: '@ViewBag.requestPath',
                currency: currentCurrency
            },
            dataType: "json",
            error: function () {
                alert("请求提交失败,请刷新页面后重试");
            },
            success: function (res) {
                if (res?.redirectUrl) {
                    window.location.href = res.redirectUrl;
                }
            }
        });
    });
    
  • 额外配置检查:发布环境检查站点认证规则,如果Buy接口需要登录才能访问,给接口加[Authorize]特性,同时在全局配置里指定登录页路径,避免拦截时跳转到系统默认路径。

方案2:去掉Ajax,直接用普通表单提交

如果提交后不需要做无刷新提示,完全没必要用Ajax,直接把按钮放在form表单里,设置表单的action为Buy接口地址,method为post,点击按钮直接提交表单即可。这种场景下服务端的RedirectToAction可以正常工作,不会出现格式不匹配问题,开发成本更低。


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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.26 12:24:58