I'm trying to send a zip generated by a php server when requested by jquery's $.ajax.
This is my code:
php:
        $file = tempnam($a_folder_path, "zip");
        $zip = new ZipArchive();
        $zip->open($file, ZipArchive::OVERWRITE);
        $zip->addFile($path_to_json, 'data.json');
        $zip->close();
        rename($file, $file . '.zip');
        $filename = basename($file . '.zip');
        $filepath = $file . '.zip';
        while (ob_get_level()) {
            ob_end_clean();
        }
        header("Pragma: public");
        header("Expires: 0");
        header("Cache-Control: public, must-revalidate, post-check=0, pre-check=0");
        header("Content-Description: File Transfer");
        header("Content-type: application/octet-stream");
        header("Content-Disposition: attachment; filename=\"".$filename."\"");
        header("Content-Transfer-Encoding: binary");
        header("Content-Length: ".filesize($filepath));
        ob_end_flush();
        echo file_get_contents($filepath);
        //@readfile($filepath);
javascript:
$.ajax(
        {
            url:    myUrl,                
            type:   'POST',                
            data:   {
                "leData"     : "some_data"
            },
            context: document.body,
            cache:  false,
            success: function(data) {
                console.log(data);
                console.log(data.length);
                var bytes = new Uint8Array(data.length);
                for (var i=0; i<data.length; i++) {
                    bytes[i] = data.charCodeAt(i);
                }
                blob = new Blob([bytes], {type: "application/zip"})
                saveAs(blob, "test.zip");//trying to access data with FileSave.js
                zip.load(data);//trying to access data with JSZip.js
                jsonData = JSON.parse(zip.file('shouldBeThere.json').asText());
            },
            error: function() {
                alert('error');
            }
        }
    );
What happens:
The problem is I have no idea if the problem comes from php or from javascript. I don't know if php is sending a corrupted zip or if javascript isn't reading it right.
I have tried all the php headers combinations and methods i've found on the internet. I have also tried to do things differently in javascript: using an ArrayBuffer instead of Uint8Array, passing bytes instead of data to zip.load(), using {type: "application/octet-stream"} in Blob().
Start Using AJAX Today In our PHP tutorial, we will demonstrate how AJAX can update parts of a web page, without reloading the whole page. The server script will be written in PHP. If you want to learn more about AJAX, visit our AJAX tutorial.
ajax({ type: 'POST', url: 'process. php', data: { text1: val1, text2: val2 }, success: function(response) { $('#result'). html(response); } }); });
I finally found a solution: It has to be specified to ajax the received data type, and then convert this unicode data into characters. Here is my new javascript code:
$.ajax(
    {
        url:    myUrl,                
        type:   'POST',                
        data:   {
            "leData"     : "some_data"
        },
        context: document.body,
        cache:  false,
        dataType: 'text',                                   //solution code
        mimeType: 'text/plain; charset=x-user-defined',     //solution code
        success: function(data) {
            console.log(data);
            console.log(data.length);
            newContent = "";                                //solution code
            for (var i = 0; i < data.length; i++) {         //solution code
                newContent += String.fromCharCode(data.charCodeAt(i) & 0xFF); //solution code
            } 
            var bytes = new Uint8Array(newContent.length);                     //modified
            for (var i=0; i<newContent.length; i++) {                          //modified
                bytes[i] = newContent.charCodeAt(i);                           //modified
            }
            blob = new Blob([bytes], {type: "application/zip"})
            saveAs(blob, "test.zip");
            zip.load(newContent);                                              //modified
            jsonData = JSON.parse(zip.file('shouldBeThere.json').asText());
        },
        error: function() {
            alert('error');
        }
    }
);
My php code was fine, it even worked without headers. Here is the minimal php code I need:
 $file = tempnam($a_folder_path, "zip");
    $zip = new ZipArchive();
    $zip->open($file, ZipArchive::OVERWRITE);
    $zip->addFile($path_to_json, 'data.json');
    $zip->close();
    rename($file, $file . '.zip');
    echo file_get_contents($file . '.zip');
Solution inspired by this
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With