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

为何Ajax请求被触发两次?附Django前后端相关代码

Ajax请求触发两次的原因及解决办法

核心原因分析

  1. 事件重复绑定
    如果你的JS脚本被重复引入(比如模板中多次加载同一个JS文件),$('body').on('click','td', ...)会被绑定多次,导致每次点击td都会触发多轮Ajax请求。

  2. Bootstrap Tooltip的额外事件干扰
    你的td标签添加了data-toggle="tooltip"属性,Bootstrap Tooltip组件在初始化或交互过程中,可能会触发额外的点击事件(即使默认触发方式是hover,某些场景下也会因元素交互产生二次事件)。

  3. 事件委托范围过大+无过滤逻辑
    绑定在body上的td点击事件范围太广,且没有判断当前点击的td是否包含目标id,导致无id的td也会触发请求,同时可能在事件冒泡过程中被重复捕获。


针对性解决办法

1. 避免事件重复绑定

给事件添加命名空间,或者先解绑再绑定,确保事件只绑定一次:

// 先解绑同名命名空间的事件,再绑定
$('body').off('click.tdToggle').on('click.tdToggle','td', function(e) {
    e.stopPropagation();
    var _id = $(this).attr('id');
    // 只处理带有id的td,过滤无效点击
    if (!_id) return;
    
    $.ajax({
        type: 'POST',
        url: "{% url 'monitoring:deactivate_dcf' %}",
        data: { "id" : _id },
        dataType: 'json', // 后端返回Json,直接设为json无需手动parse
        success: function (response) {
            // 同步更新页面显示,避免状态不一致
            $(this).text(response.deactivated);
        },
        error: function(xhr) {
            console.log(xhr.responseText);
        }
    });
});

2. 消除Tooltip的事件干扰

显式指定Tooltip的触发方式为hover,避免点击触发额外事件:

<td data-toggle="tooltip" data-placement="top" title="" data-trigger="hover">{{ dcf.ide }}</td>
<td data-toggle="tooltip" data-placement="top" title="" data-trigger="hover" id="{{ dcf.ide }}">{{ dcf.deativated }}</td>

3. 优化后端逻辑(减少冗余查询+避免竞态)

当前后端多次查询数据库,且未处理并发请求问题,可优化为:

@login_required
@csrf_exempt
def deactivate_dcf(request):
    if request.is_ajax() and request.method == "POST":
        datacorrection_id = request.POST.get("id")
        try:
            # 加行锁避免并发请求导致状态混乱
            dcf = DataCorrection.objects.select_for_update().get(ide=datacorrection_id)
            dcf.deativated = not dcf.deativated
            dcf.save()
            # 返回更新后的状态,方便前端同步页面
            return JsonResponse({"response": "success", "deactivated": dcf.deativated}, status=200)
        except DataCorrection.DoesNotExist:
            return JsonResponse({"response": "failed","exist":"datacorrection not exist"}, status=404)
    return JsonResponse({"response":"not_ajax"}, status=200)

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.19 08:40:32