javascript - 如何防止 jQuery Ajax 中的数据循环?

标签 javascript jquery html ajax jquery-select2

这是关于使用 Select2 插件、Ajax 和 API 分配多个用户。这种情况,我有一个包含 2 个具有不同指向 URL 的 Ajax 的函数。目前,我已经预先选择了存储在数据库中的用户。该选择是在模态中使用 Select2 。那么现在当 Modal 打开时会发生什么,第一个 Ajax 将加载 URL /all_user 以显示数据库中的所有用户。之后,第二个 Ajax 将加载 URL /activity 以获取并加载同一 Modal 中其他字段的信息。两个 URL 并行运行。

URL /all_user 成功显示所有用户。 URL /activity 也成功显示预选用户。但是,当我关闭 Modal 并在不刷新页面的情况下重新打开同一个 Modal 时,它肯定会加载包含 2 个 Ajax 的相同函数,如上所述。

仅供引用,在/activity中,自从我从数据库接收字符串以来,我已经做了一个从字符串转换为数组的函数,因此需要在Select中显示之前进行转换。

所以问题是数据将重复 2 倍,当我关闭并重新打开时,数据将重复 3 倍。如何防止重复?

下面是/activity中预选的Select2

enter image description here

下面是成功显示所有用户的/all_user

enter image description here

因此,当 Modal 关闭并重新打开时,就会发生重复。

enter image description here

HTML

<select type="text" class="form-control mySelect" id="editOwner" name="editOwner" multiple="multiple"></select>

选择2初始化

var mySelect = $('.mySelect').select2({
   allowClear: true,
   placeholder: "Search Owner...",
   minimumResultsForSearch: -1,
   width: 600,
});

JS

<span onclick='editOwner(&quot;"+value3.l3_id+"&quot;)'></span>

function editOwner(id){

    activity_id = id;

    $.ajax ({
        url: '/all_user',
        crossDomain: true,
        type: "POST",
        dataType : 'json',
        cache: false,
        processData: true,
        data: 'data',
        success: function(response){
            for (var i = 0; i < response.data.length; i++) { 
                $("#editOwner").append($("<option>", {
                    response: response.data[i].fullname,
                    text: response.data[i].fullname
                }));
            }
        }
    });

    $.ajax({
        url : '/activity',
        crossDomain: true,
        type: "POST",
        dataType : 'json',
        cache: false,
        processData: true,
        data: {task_id: activity_id}},
        success: function(response){
                if (response.status == "Success"){
                    $("#editOwner").val(response.data[0]["task_owner"]).attr("readonly",false);

                    $(response.data).each(function(key,value){
                        var owners = value.task_owner.split(',');
                        $(owners).each(function(k,v){
                            $("#editOwner").append($("<option selected>", {
                                response: v,
                                text: v
                            }));
                        });
                        $("#editOwner").val(owners).trigger("change");
                    });

                }
                else {}
        },
        error: function(e){}
    });

    $('#editOwnerModal').modal('show');    
}

最佳答案

这是因为您正在调用:

editOwner(id);

在包含 ID 为 #editOwner 的选择的范围的点击事件上。

像这样:

  <body>
    <select id="cars" style="display: block">
      <option value="volvo">Volvo</option>
      <option value="saab">Saab</option>
      <option value="opel">Opel</option>
      <option value="audi">Audi</option>
    </select>

    <script type="text/javascript" src="jquery-3.4.1.min.js"></script>
    <script type="text/javascript">
      function addCar ()
      {
        $("#cars").append
        (
          $("<option>", { response: "Ford", text: "Ford" })
        );
      }

      $("#cars").on
      (
        "click",
        addCar
      );

    </script>
  </body>

每次打开和关闭 ID 为 #editOwner 的 select 元素时,都会向 select 元素附加一个新选项。您可以通过添加以下内容轻松解决此问题:

$("#editOwner").unbind();

像这样:

  <body>
    <select id="cars" style="display: block">
      <option value="volvo">Volvo</option>
      <option value="saab">Saab</option>
      <option value="opel">Opel</option>
      <option value="audi">Audi</option>
    </select>

    <script type="text/javascript" src="jquery-3.4.1.min.js"></script>
    <script type="text/javascript">
      function addCar ()
      {
        $("#cars").append
        (
          $("<option>", { response: "Ford", text: "Ford" })
        );

        // Add this to remove the onclick events for #cars so it will only run one time.
        $("#cars").unbind();
      }

      $("#cars").on
      (
        "click",
        addCar
      );
    </script>
  </body>

或者更好的是,您可以通过根本不使用 onclick 事件调用该函数来仅运行该函数一次,如下所示:

  <body>
    <select id="cars" style="display: block">
      <option value="volvo">Volvo</option>
      <option value="saab">Saab</option>
      <option value="opel">Opel</option>
      <option value="audi">Audi</option>
    </select>

    <script type="text/javascript" src="jquery-3.4.1.min.js"></script>
    <script type="text/javascript">
      function addCar ()
      {
        $("#cars").append
        (
          $("<option>", { response: "Ford", text: "Ford" })
        );
      }
    </script>

    <script type="text/javascript">
      addCar();
    </script>
  </body>

除非有原因需要使用 onclick 事件调用 ajax,否则您确实不应该这样做,但如果需要,您应该调用 $("#editOwner").unbind();在 editOwner(id) 的末尾;像这样:

Edit: Saw that you were calling editOwner(id) with a span that had a onclick event. Just add an ID to that and call $("#mySpan").prop("onclick", null).off("click");

      <span id="#mySpan" onclick='editOwner(&quot;"+value3.l3_id+"&quot;)'></span>

      function editOwner(id){

      activity_id = id;

      $.ajax ({
          url: '/all_user',
          crossDomain: true,
          type: "POST",
          dataType : 'json',
          cache: false,
          processData: true,
          data: 'data',
          success: function(response){
              for (var i = 0; i < response.data.length; i++) { 
                  $("#editOwner").append($("<option>", {
                      response: response.data[i].fullname,
                      text: response.data[i].fullname
                  }));
              }
          }
      });

      $.ajax({
          url : '/activity',
          crossDomain: true,
          type: "POST",
          dataType : 'json',
          cache: false,
          processData: true,
          data: {task_id: activity_id}},
          success: function(response){
                  if (response.status == "Success"){
                      $("#editOwner").val(response.data[0]["task_owner"]).attr("readonly",false);

                      $(response.data).each(function(key,value){
                          var owners = value.task_owner.split(',');
                          $(owners).each(function(k,v){
                              $("#editOwner").append($("<option selected>", {
                                  response: v,
                                  text: v
                              }));
                          });
                          $("#editOwner").val(owners).trigger("change");
                      });

                  }
                  else {}
          },
          error: function(e){}
      });

      $('#editOwnerModal').modal('show');   

      // Try adding this.
      //$("#editOwner").unbind();

      // Or this if you want to use onclick as an attribute.
      $("#mySpan").prop("onclick", null).off("click");

  }

关于javascript - 如何防止 jQuery Ajax 中的数据循环?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/60926129/

相关文章:

javascript - 如何将不同尺寸的点击坐标转换为320尺寸尺寸?

javascript - 如何使用 jquery 从 HTML 中排除 thead 、 tfoot 和 input[type=checkbox] ?

javascript - 如何使用 javascript 动态删除在 html 中创建的输入表单

javascript - 在 getElementById 之后,getElementByClass 不链接到 DOM

javascript - 如何分割字符串中的空格(跨浏览器安全)

javascript - 如何对齐左侧和全高侧导航菜单

javascript - 不要从表 td 第一个子元素中删除内容

javascript - 谷歌可视化 : filtered selection items

javascript - 使用 REST API 的下拉列表未显示(在控制台日志中显示)

javascript - 在 TinyMCE 中设置默认字体大小失败