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

Django项目PUT请求后页面刷新致CSRFToken暴露的AJAX问题排查

解决Django表单PUT提交后页面刷新及CSRF Token暴露问题

嘿,我看你折腾了好几种方法还是没搞定页面刷新的问题,核心原因其实是异步表单提交的回调逻辑没处理好,浏览器没法识别你的阻止指令。我帮你梳理下问题,再给你修正后的代码:

问题根源拆解

  1. async函数的返回值坑:浏览器的onsubmit事件只认布尔值来阻止默认行为,但async函数默认返回Promise,哪怕你写了return false,也会被包装成Promise,浏览器根本不买账,默认的表单提交还是会触发。
  2. 无效的函数调用:代码里的edit_prod.handleForm()完全没定义,属于多余的无效代码,反而可能打乱逻辑。
  3. 没捕获事件对象:你没拿到表单提交的事件实例,没法直接用最可靠的event.preventDefault()来阻断刷新。
  4. 表单赋值错误:给输入框用innerHTML赋值是错的,表单元素得用value属性来设置内容。

修复后的完整代码

// 定义表单提交使用的全局变量
var id, upt_prodName, upt_prodPrice, upt_prodDescpt;

// 填充文本区域以允许用户更新产品信息的代码块
const editProd_view = (response) => {
  let prod_id = response.id;
  let edit_name = response.name;
  let edit_price = response.price;
  let edit_descpt = response.description;
  
  // 修正:表单元素用value赋值,不是innerHTML
  document.querySelector("#prod_idUpt").innerHTML = prod_id;
  document.querySelector("#editProdName").value = edit_name;
  document.querySelector("#editProdPrice").value = edit_price;
  document.querySelector("#editProdDescpt").value = edit_descpt;
  
  id = prod_id;

  // 提交时发送产品信息以更新产品
  document.querySelector("#editProd_form").onsubmit = async (event) => {
    // 第一步:立即阻止默认提交行为,这是最可靠的方式
    event.preventDefault();
    
    try {
      // 获取文本区域中的所有值以更新内容
      upt_prodName = document.getElementById("editProdName").value;
      upt_prodPrice = document.getElementById("editProdPrice").value; // 统一变量名,避免提交数据错误
      upt_prodDescpt = document.getElementById("editProdDescpt").value;

      // 修正:await和then不要混用,保持代码清晰
      const res = await fetch(`/editProduct/${id}`, {
        method: "PUT",
        headers: {
          "Content-Type": "application/json",
          "X-CSRFToken": getCookie("csrftoken"),
        },
        body: JSON.stringify({
          name: upt_prodName,
          description: upt_prodDescpt,
          price: upt_prodPrice,
        }),
      });
      
      const result = await res.json();
      console.log("result ->", result);
      
      // 这里可以加提交成功后的逻辑,比如关闭编辑弹窗、刷新产品列表等
    } catch (err) {
      console.error("err", err);
    }
  };
  
  return false;
};

// 确保getCookie函数正常工作(如果还没定义的话)
function getCookie(name) {
  let cookieValue = null;
  if (document.cookie && document.cookie !== '') {
      const cookies = document.cookie.split(';');
      for (let i = 0; i < cookies.length; i++) {
          const cookie = cookies[i].trim();
          if (cookie.substring(0, name.length + 1) === (name + '=')) {
              cookieValue = decodeURIComponent(cookie.substring(name.length + 1));
              break;
          }
      }
  }
  return cookieValue;
}

核心修复点说明

  • 优先用event.preventDefault():把这个放在异步逻辑最开头,不管后续代码执行情况如何,都能直接阻断页面刷新。
  • 修正表单赋值方式:输入框、文本域这类表单元素必须用value属性设置内容,innerHTML是给普通标签用的。
  • 统一变量名:之前的new_prodPrice和全局变量upt_prodPrice不一致,会导致提交的数据错误,现在统一成同一个变量。
  • 简化异步代码:await和.then()混用会让逻辑混乱,统一用await让代码更易读。

这样修改后,表单就会通过AJAX完成PUT请求,不会触发页面刷新,CSRF Token也就不会暴露在URL里了。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.11 08:22:18