jQuery - Незаконный вызов

108

jQuery v1.7.2

У меня есть эта функция, которая при выполнении выдает следующую ошибку:

Uncaught TypeError: Illegal invocation

Вот функция:

$('form[name="twp-tool-distance-form"]').on('submit', function(e) {
    e.preventDefault();

    var from = $('form[name="twp-tool-distance-form"] input[name="from"]');
    var to = $('form[name="twp-tool-distance-form"] input[name="to"]');
    var unit = $('form[name="twp-tool-distance-form"] input[name="unit"]');
    var speed = game.unit.speed($(unit).val());

    if (!/^\d{3}\|\d{3}$/.test($(from).val()))
    {
        $(from).css('border-color', 'red');
        return false;
    }

    if (!/^\d{3}\|\d{3}$/.test($(to).val()))
    {
        $(to).css('border-color', 'red');
        return false;
    }

    var data = {
        from : from,
        to : to,
        speed : speed
    };

    $.ajax({
        url : base_url+'index.php',
        type: 'POST',
        dataType: 'json',
        data: data,
        cache : false
    }).done(function(response) {
        alert(response);
    });

    return false;
});

Если я удалю dataиз вызова ajax, он будет работать .. любые предложения?

Спасибо!

йода
источник
попробуйте удалить fromиз данных. Возможно, это противоречит jquery от
gopi1410
6
Вы понимаете, что пытаетесь протолкнуть объекты jQuery, а не JSON, верно?
asawyer
18
У меня часто случается, когда я забываю .val () на каком-то объекте jQuery ...
userfuser

Ответы:

118

Я думаю, вам нужны строки в качестве значений данных. Вероятно, что-то внутри jQuery неправильно кодирует / сериализует объекты To & From.

Пытаться:

var data = {
    from : from.val(),
    to : to.val(),
    speed : speed
};

Обратите внимание также на строки:

$(from).css(...
$(to).css(

Вам не нужна оболочка jQuery, поскольку To и From уже являются объектами jQuery.

LessQuesar
источник
2
Спасибо, забыл, что я загрузил объекты вместо строк, обычно я загружаю строки :)
yoda
3
Этот подход мне помогает. Я $from = $('#from');называю свои переменные так: Это помогает мне помнить, что они представляют собой объект jQuery, который помогает избежать вызова метода для чего-то, что является строкой, или попыток манипулировать строкой .toString()или чем-то еще, когда это объект jQuery.
timbrown
У меня .val()отсутствовала деталь, поэтому она не передавала значение.
SharpC
109

Попробуйте установить processData: false в таких настройках ajax

$.ajax({
    url : base_url+'index.php',
    type: 'POST',
    dataType: 'json',
    data: data,
    cache : false,
    processData: false
}).done(function(response) {
    alert(response);
});
Хусто
источник
8
By default, data passed in to the data option as an object (technically, anything other than a string) will be processed and transformed into a query string, fitting to the default content-type "application/x-www-form-urlencoded". If you want to send a DOMDocument, or other non-processed data, set this option to false.
BOTJr.
Вам также может потребоваться добавить contentType: false. Я сделал при загрузке файла. См stackoverflow.com/questions/21044798/...
khylo
18

Просто для записи это также может произойти, если вы попытаетесь использовать необъявленную переменную в таких данных, как

var layout = {};
$.ajax({
  ...
  data: {
    layout: laoyut // notice misspelled variable name
  },
  ...
});
Иван Иванич
источник
1
Спасибо за это!! Это было то место, где меня блокировали.
Мэтт Зеленак
13

Если вы хотите отправить форму с использованием Javascript FormData API с загрузкой файлов, вам необходимо установить следующие два параметра:

processData: false,
contentType: false

Вы можете попробовать следующее:

//Ajax Form Submission
$(document).on("click", ".afs", function (e) {
    e.preventDefault();
    e.stopPropagation();
    var thisBtn = $(this);
    var thisForm = thisBtn.closest("form");
    var formData = new FormData(thisForm[0]);
    //var formData = thisForm.serializeArray();

    $.ajax({
        type: "POST",
        url: "<?=base_url();?>assignment/createAssignment",
        data: formData,
        processData: false,
        contentType: false,
        success:function(data){
            if(data=='yes')
            {
                alert('Success! Record inserted successfully');
            }
            else if(data=='no')
            {
                alert('Error! Record not inserted successfully')
            }
            else
            {
                alert('Error! Try again');
            }
        }
    });
});
Баблу Ахмед
источник
Не могли бы вы объяснить, что делают эти два варианта?
rahim.nagori
2

В моем случае я просто изменил

Примечание: это в случае Django, поэтому я добавил csrftoken. В вашем случае это может не понадобиться.

Добавлено contentType: false,processData: false

Закомментирован "Content-Type": "application/json"

$.ajax({
    url: location.pathname, 
    type: "POST",
    crossDomain: true,
    dataType: "json",
    headers: {
        "X-CSRFToken": csrftoken,
        "Content-Type": "application/json"
    },
    data:formData,
    success: (response, textStatus, jQxhr) => {

    },
    error: (jQxhr, textStatus, errorThrown) => {

    }
})

к

$.ajax({
    url: location.pathname, 
    type: "POST",
    crossDomain: true,
    dataType: "json",
    contentType: false,
    processData: false,
    headers: {
        "X-CSRFToken": csrftoken
        // "Content-Type": "application/json",
    },
    data:formData,
    success: (response, textStatus, jQxhr) => {

    },
    error: (jQxhr, textStatus, errorThrown) => {

    }
})

и это сработало.

Hygull
источник
2

В моем случае я не определяю все переменные, которые я передаю данным в ajax.

var page = 1;

$.ajax({
    url: 'your_url',
    type: "post",
    data: { 'page' : page, 'search_candidate' : search_candidate }
    success: function(result){
        alert('function called');
    }
)}

Я только что определил переменную var search_candidate = "candidate name";и ее работу.

var page = 1;
var search_candidate = "candidate name"; // defined
$.ajax({
    url: 'your_url',
    type: "post",
    data: { 'page' : page, 'search_candidate' : search_candidate }
    success: function(result){
        alert('function called');
    }
)}
Раджеш Харатмол
источник
0

Моя проблема не связана с processData. Это произошло потому, что я отправил функцию, которую нельзя вызвать позже, applyпотому что у нее недостаточно аргументов. В частности , я не должен был использовать в alertкачестве errorобратного вызова.

$.ajax({
    url: csvApi,
    success: parseCsvs,
    dataType: "json",
    timeout: 5000,
    processData: false,
    error: alert
});

См. Этот ответ для получения дополнительной информации о том, почему это может быть проблемой: Почему определенные вызовы функций в JavaScript называются «незаконными вызовами»?

Я смог обнаружить это, добавив a console.log(list[ firingIndex ])в jQuery, чтобы я мог отслеживать, что он запускает.

Это было исправление:

function myError(jqx, textStatus, errStr) {
    alert(errStr);
}

$.ajax({
    url: csvApi,
    success: parseCsvs,
    dataType: "json",
    timeout: 5000,
    error: myError // Note that passing `alert` instead can cause a "jquery.js:3189 Uncaught TypeError: Illegal invocation" sometimes
});
Убершмекель
источник
0

В моем случае (с использованием webpack 4) в анонимной функции, которую я использовал в качестве обратного вызова.

Мне пришлось использовать window.$.ajax()вместо того, чтобы $.ajax()иметь:

import $ from 'jquery';
window.$ = window.jQuery = $;
Зандервар
источник
0

Также это тоже причина: если вы создали коллекцию jQuery (через .map () или что-то подобное), вам не следует использовать эту коллекцию в данных .ajax (). Потому что это все еще объект jQuery , а не простой массив JavaScript . Вы должны использовать .get () в и, чтобы получить простой массив js, и должны использовать его для настройки данных в .ajax ().

Бурак ТАРХАНЛИ
источник