方式2,base64
这种方式主要
通过filereader,用readAsDataURL把files文件列表的文件一个个读取成base64
每次读取好了就会触发它的onload事件
要注意的是,filereader每次只能读取一个文件,所以这里才用这种长度判断
的方式不停的循环读取 参考这篇博客 https://www.cnblogs.com/jiangwei-gx/p/7760692.html
filereader可以把files文件列表的文件,读取成各种不同的格式,如二进制.文本.dataurl(也就是base64)等,关于filereader更多详情 可以去MDN或者看看这篇博客https://www.cnblogs.com/fqh123/p/10221948.html
前端代码
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
</head>
<body>
<input type="file" id="inputa" multiple>
<script src="https://cdn.bootcdn.net/ajax/libs/jquery/3.5.1/jquery.js"></script>
<script>
let inputa = document.getElementById("inputa")
// 这种读取多个文件会报错
// inputa.onchange = function () {
// let reader = new FileReader()
// reader.onloadend = function (res) {
// console.log('res', res)
// }
// for (const file of this.files) {
// reader.readAsDataURL(file)
// }
// }
inputa.onchange = function () {
let imgarr = []
let fileLength = 0;
let reader = new FileReader();
reader.readAsDataURL(this.files[fileLength])
let that = this
// 通过filereader,用readAsDataURL把files文件列表的文件一个个读取成base64
// 每次读取好了就会触发它的onload事件
// 要注意的是,filereader每次只能读取一个文件,所以这里才用这种长度判断
// 的方式不停的循环读取
reader.onload = function (res) {
if (res.target.result) {
console.log("完成" + that.files[fileLength].name, that.files);
// console.log(res.target.result)
imgarr.push(res.target.result)
fileLength++;
if (fileLength < that.files.length) {
reader.readAsDataURL(that.files[fileLength])
} else {
console.log('imgarr', imgarr)
// 如果没有, 说明全部图片读取完毕, 那就发ajax
$.ajax({
url: "http://localhost/upload",//请求路径
type: "POST",
data: JSON.stringify(imgarr),
dataType: 'JSON',
// contentType: "application/x-www-form-urlencoded",
contentType: "application/json;charset=utf-8",
// contentType: false,//不设置请求头,
// 这样浏览器就会根据传入的data来判断contentType,
// 所以可以看到传输的方式是binary二进制的
// processData: false,//同上同理
success(data) {
if (200 == data.code) {
console.log("上传成功!");
console.log(data)
} else {
console.log("上传失败!");
console.log(data)
}
},
error() {
console.log("与服务器通信发生错误");
}
})
}
}
}
}
</script>
</body>
</html>
后端代码
和 上传文件的几种方式(上)里的一致
这里也有个要注意的点,和第一种上传文件的方式--file的区别,第一种主要用了formdata来处理files文件列表的每个文件,利用了formdata格式化数据成二进制,然后传输过去,binary二进制传输
而这里其实是利用了filereader,利用filereader把文件一个个读取成base64字符串,然后我再push到数组中,然后通过JSON.stringify(imgarr),把数组json化,就可以通过ajax的data传过去了
还有个要注意的点是,这里也有请求头的区别,不同于第一种上传文件的方式--file的设置或者不设置请求头
这里主要是设置两种不同的请求头的区别
第一种 application/json;charset=utf-8 如图
这种传过去是什么就是什么,我把base64放数组里JSON.stringify传过去,接收到就是数组
第二种 application/x-www-form-urlencoded 如图
可以看到我传过去的数组,变成了键名,然后键值是空
不过这样放就不会有这种问题了...如图,data里放一个对象,这样就有键值对
这样就没有,如图
那么就很明了了,application/x-www-form-urlencoded这个请求头
如果data里你不传对象,而是别的,那么会整体作为一个键....