Как предотвратить зацикливание данных в jQuery Ajax? - PullRequest
2 голосов
/ 30 марта 2020

Это касается назначения нескольких пользователей с использованием плагина Select2, Ajax и API. Ситуация, у меня есть функция, которая содержит 2 Ajax с разными указанными URL. В настоящее время я предварительно выбрал пользователя, который хранится в БД. Выбор использует Select2 в модальном. Итак, что происходит сейчас, когда открыт модал, 1-й Ajax загрузит URL /all_user, чтобы отобразить всех пользователей в БД. После этого 2nd Ajax загрузит URL /activity, чтобы получить и загрузить информацию для других полей в том же Модальном. Оба URL работают параллельно.

URL /all_user успешно, чтобы отобразить всех пользователей. URL /activity также успешно отображает предварительно выбранного пользователя. Тем не менее, когда я закрываю модальный и снова открываю тот же модальный без refre sh страницы, он определенно загрузит ту же функцию, которая содержит 2 Ajax, как упомянуто выше.

FYI, в /activity У меня есть функция для преобразования из String в Array, так как я получил в String из БД, поэтому необходимо преобразовать перед отображением в Select.

Таким образом, проблема в том, что данные будут дублироваться 2x, когда я закрою и снова открою, он будет дублироваться 3 раза. Как предотвратить дублирование?

Ниже предварительно выбраны Select2 in /activity.

enter image description here

Ниже /all_user, которые успешно отображаются все пользователи

enter image description here

Поэтому, когда Модал закрывается и открывается снова, происходит дублирование.

enter image description here

HTML

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

SELECT2 INIT

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');    
}

1 Ответ

0 голосов
/ 30 марта 2020

Это потому, что вы звоните:

editOwner(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>

Каждый раз, когда вы открываете и закрываете элемент select с идентификатором #editOwner, вы добавляете новую опцию к элементу 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>

Если нет причины, по которой вам нужно вызвать ajax с событием onclick, которое вам действительно не следует, но если вам нужно, вы должны вызвать $ ("# editOwner" ) .unbind (); в конце editOwner (id); как это:

Edit: увидел, что вы вызывали editOwner (id) с диапазоном, который имел событие onclick. Просто добавьте к этому идентификатор и вызовите $ ("# 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");

  }
...