jsPDF - 发送 PDF 到服务器后出现损坏

6
我使用javascript库jsPDF生成了一个包含文字和图片的pdf文件。然后我想将该文件发送到服务器,以便通过电子邮件发送。问题是到达服务器的文件已损坏,无法打开或者pdf上的图片无法查看。
我的代码如下: ``` var pdf = btoa(doc.output()); ``` 这会出现错误:Uncaught InvalidCharacterError: Failed to execute 'btoa' on 'Window': The string to be encoded contains characters outside of the Latin1 range.
var pdf = btoa(encodeURIComponent(doc.output()));
var data = new FormData();
data.append("data" , pdf);
var xhr = new XMLHttpRequest();
xhr.open( 'post', '/url', true );
xhr.send(data);

我也尝试了其他方法,如下所示: var pdf = btoa(encodeURIComponent(doc.output('blob'))); - 无法打开文件 var pdf = btoa(doc.output('blob')); - 无法打开文件 var pdf = btoa(unescape(encodeURIComponent(doc.output()))); - 文件可以打开,但图像显示为灰色线条
注:我正在使用Laravel 5。服务器代码:
$data = base64_decode($_POST['data']);
$fname = "test.pdf"; 
$file = fopen("pdf/" .$fname, 'w'); 
fwrite($file, $data); 
fclose($file);

SOLUTION:
解决方案:
js代码:
var blob = doc.output('blob');
var fd = new FormData();
fd.append('data', blob);
$.ajax({
   type: 'POST',
   url: '/url',
   data: fd,
   processData: false,
   contentType: false
}).done(function(data) {
   console.log(data);
});

服务器代码:

if(!empty($_FILES['data'])){
    move_uploaded_file(
        $_FILES['data']['tmp_name'],
        public_path() . '/test.pdf'
    );
    return "Pdf was successfully saved.";
} else {
    return "No Data Sent";
}
1个回答

4

btoa在ASCII字节范围内出现了问题...JavaScript无法包含所有字符。这就是为什么你不应该使用FileReader的readAsBinaryString的原因...正确处理二进制,不要将其作为字符串或~3倍大的base64字符串,而是作为Blob、ArrayBuffer或类型化数组,这样结果会很好。

var blob = doc.output('blob')
xhr.send(blob)

我在后端尝试了没有base64_decode的方法,但它并不起作用。没有错误,但也没有文件。 - mad scientist
调试后发现,当我将 blob 发送到服务器时,$_POST['data'] 中没有任何内容。如果我发送一个简单的字符串,它可以正常工作。发送 doc.output('blob') 无法正常工作。 - mad scientist
从你的回答中找到了解决方案,谢谢。我已经更新了帖子。 - mad scientist

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接