我已经尝试了几天,现在建立一个文件上传使用AJAX和PHP。我能够上传图像没有任何问题。但每当涉及到PDF,我最终与空白页。
下面是我使用FileReader时的尝试:
for(const [key, file] of Object.entries($('input').prop('files'))){
const reader = new FileReader()
reader.onload = function(event){
var object = {
name:file.name,
size:file.size,
type:file.type,
content:reader.result,
}
API.post("file/upload/?csrf="+CSRF,object,{
success:function(result,status,xhr){
console.log(result)
}
})
}
reader.readAsDataURL(file)
}
在PHP中:
// $_POST['content'] = base64_decode(str_replace('data:' . $_POST['type'] . ';base64,', '', $_POST['content']));
// $_POST['content'] = base64_decode($_POST['content']);
$_POST['content'] = base64_decode(urldecode($_POST['content']));
我得到的结果是:
- 上传图像:好的!
- 上传单页PDF:PDF文件仅包含空白页。
- 使用3种方法(readAsDataURL、readAsBinaryString、readAsText)的结果相同。
- 使用readAsText我不断得到:
Failed to execute 'btoa' on 'Window': The string to be encoded contains characters outside of the Latin1 range.
使用phpMyAdmin 5在SQL中保存后进行验证。
预期结果应该是正确保存任何文件类型。
注意:API类只是一个包含$. post参数的小类,所以我不必一直输入它们。
1条答案
按热度按时间n3h0vuf21#
第一个问题是我在SQL中存储二进制数据,而SQL并不适合这种类型的使用,这导致SQL数据库损坏了二进制数据。
因此,我使用本地存储的二进制文件(.bin)和SQL重新设计了我的文件存储,以提供文件的所有 meta数据,包括路径和更高级的ACL。
为了保护数据,我使用了重写规则
RewriteRule ^data/.*$ - [F,L]
。这防止用户直接访问二进制数据。因此保护了文件。更改完成后,我就可以通过应用程序的API保存文件,使用
readAsDataURL
方法检索编码的二进制数据并将其发送到PHPAPI。