Search code examples
phpjqueryajaxlaravelmultipartform-data

CSRF token mismatch when setting processData: false, contentType: false,


Hey guys I'm trying to send files to Laravel server using ajax for that i need to create form data and send it with the ajax request and in order to prevent illegal invocation i need to set these

 processData: false,
 contentType: false,

heres my code->

$("#saveChanges").click(function () {
    let formData = new FormData();

    formData.append("banner", $("input[name='banner']"));

    $.ajax({
        url: "/save/website/data",
        type: "POST",

        data: {
            pickUpBtnColor: $("input[name='pickUpBtnColor']").val(),
            banner: $("input[name='banner']").val(),
            logo: $("input[name='logo']").val(),
            _token: $('meta[name="csrf"]').attr("content"),
            formData: formData,
        },
        processData: false,
        contentType: false,
        success: function (data) {
            console.log(data);
        },
        error: function (error) {
            console.log(error);
        },
    });
});

But when i set these my csrf is also ignored and the server responds with "CSRF token mismatch." Any one has a solution?


Solution

  • The issue is because you need to place all the form field values within a single FormData object and send that in the request.

    $("#saveChanges").click(function() {
      let formData = new FormData();
      formData.append("banner", $("input[name='banner']"));
      formData.append('pickUpBtnColor', $("input[name='pickUpBtnColor']").val());
      formData.append('banner', $("input[name='banner']").val());
      formData.append('logo', $("input[name='logo']").val());
      formData.append('_token', $('meta[name="csrf"]').attr("content");
    
      $.ajax({
        url: "/save/website/data",
        type: "POST",
        data: formData,
        processData: false,
        contentType: false,
        success: function(data) {
          console.log(data);
        },
        error: function(error) {
          console.log(error);
        },
      });
    });
    

    Note that you could potentially simplify this if your input elements are contained within a form; hook to the submit event of the form element instead of the click of the button, and then call let formData = new FormData(referenceToYourFormHere);. There is no need for the append() calls when using the constructor in this manner.