1

I there,

I will try to be clear, i want to add an input file to a testimonial module of Prestashop.

The JS Code before my intervention was like this :

  $("#testimonialForm").submit(function(event){
event.preventDefault();
var form_data = $(this).serialize();

$.ajax({
  type: 'POST',
  cache: false,
  dataType: 'json',
  url: '',
  data: form_data+'&fc=module&module=csoft_testimonials&controller=addtestimonial&action=addTestimonial&ajax=true',
  success: function(msg){
    console.log(msg);
    switch(msg) {
      case "field_error":
        $(".alert").html(field_error).addClass("alert-danger").slideDown("fast");
        break;
      case "review_exist":
        $(".alert").html(review_exist).addClass("alert-warning").slideDown("fast");
        break;
      case "success":
        $(".alert").html(success).removeClass("alert-danger");
        $(".alert").html(success).addClass("alert-success").slideDown("fast");
        $("#testimonial_submitter_name").val("");
        $("#testimonial_submitter_email").val("");
        $("#testimonial_title").val("");
        $("#testimonial_main_message").val("");
        break;
      case "DB_error":
        $(".alert").html(DB_error).addClass("alert-danger").slideDown("fast");
        break;
      default:
        $(".alert").html(other).addClass("alert-danger").slideDown("fast");
    }
  }
});  });

And after :

 $("#testimonialForm").submit(function(event){
event.preventDefault();

var formData = new FormData($('#testimonialForm')[0]);
formData.append('testimonial_img', $('input[type=file]')[0].files[0]);

$.ajax({
  type: 'POST',
  contentType: false,
  processData: false,
  url: '',
  data: formData+'&fc=module&module=csoft_testimonials&controller=addtestimonial&action=addTestimonial&ajax=true',
  success: function(msg){
    console.log(msg);

    switch(msg) {
      case "field_error":
        $(".alert").html(field_error).addClass("alert-danger").slideDown("fast");
        break;          
      case "img_error":
        $(".alert").html(img_error).addClass("alert-danger").slideDown("fast");
        break;
      case "review_exist":
        $(".alert").html(review_exist).addClass("alert-warning").slideDown("fast");
        break;
      case "success":
        $(".alert").html(success).removeClass("alert-danger");
        $(".alert").html(success).addClass("alert-success").slideDown("fast");
        $("#testimonial_submitter_name").val("");
        $("#testimonial_submitter_email").val("");
        $("#testimonial_title").val("");
        $("#testimonial_main_message").val("");
        break;
      case "DB_error":
        $(".alert").html(DB_error).addClass("alert-danger").slideDown("fast");
        break;
      default:
        $(".alert").html(other).addClass("alert-danger").slideDown("fast");
    }
  }
});  });

As you can see, normally the php script give json answers like : img_error, but now, the "msg" var who is sent to the console log give me the entire html page.

On the php side, this is what I have :

    $order_id = Tools::getValue('id_order');
if (!Validate::isMessage($order_id) && strlen($order_id) == 9) {
  $result = "field_error";
}
$customer_id = Tools::getValue('customer_id');
if (!Validate::isInt($customer_id)) {
  $result = "field_error";
}

$note = Tools::getValue('testimonial_note');
if (!Validate::isInt($note)) {
  $result = "field_error";
}

$message = Tools::getValue('testimonial_message');
if (!Validate::isMessage($message) OR empty($message)) {
  $result = "field_error";
}

$img = $_FILES['testimonial_img'];
$image = $this->_imgDir . $order_id . '-' . $img['name'];
$image_size = file_exists($image) ? filesize($image) / 1000 : false;
if(!$_FILES['testimonial_img']['size'] && !$image_size)
{
  $result = "img_error";
}

if($model->getTestimonialReferenceOrder($order_id)){
  $result = "review_exist";
}

if ($result != "field_error" && $result != "review_exist" && $result != "img_error"){
  $resp = $model->writeTestimonial($order_id, $customer_id, $note, $message, $model->testimonial_img, $id_shop);

  $result = 'success';
}

die(json_encode($result));

If i try to modify the JS file, it's because in the Php side, $_FILES['testimonial_img'] was giving to me an undefined index error.

Can someone explain to me how I can pass the image info into my php script, without losing the json response from the script?

Yann
  • 31
  • 5
  • if you get the full page back, check if the address of the endpoint is correct. you can further inspect the request and response with the network tools in your browser which can capture the actual traffic so you get a better insight into the network activity. – hakre Jul 05 '21 at 21:42
  • i think the address is correct because the problem is not present if i use dataType: 'json' and serialize() – Yann Jul 06 '21 at 02:16
  • that makes sense. Can't you keep it? Do you set the content-type header with the JSON response from PHP? – hakre Jul 06 '21 at 06:46
  • I cant understand why, but ive found the solution, you was right, address problem, see : url: '?id_order='+order_ID+'&fc=module&module=csoft_testimonials&controller=addtestimonial&action=addTestimonial&ajax=true', data: formData, if i pass my values in url, that work, but are you able to explain me why before it worked by passing them in data: ? – Yann Jul 06 '21 at 10:30
  • I would need to guess, and my guess would be that the request method changed from GET to POST for the FormData. You can restore the previous version and then compare the original request with the "broken" one. The network tab is normally helpful for that. Documentation of the jQuery ajax function in use might also then provide you with more detailed insights (and for the interaction with FormData). – hakre Jul 06 '21 at 10:54
  • Also I would take care with string concatenation when building the URL. Encode the variable values properly (if it's part of a query parameter, use the proper url encoding mechanisms, javascript itself should cover this in its base-library), it's worth to understand how to build an URL otherwise things can easily break and then you need to verify all parts. Better (en)code it right from the very beginning. ref: https://stackoverflow.com/q/8135132/367456 – hakre Jul 06 '21 at 10:57
  • And sorry for the comment spam, was there anything existing on site which lead you to the solution or was helpful on the way to there? If so, please leave a reference in the comments and let me know. – hakre Jul 06 '21 at 11:00

0 Answers0