大文件分段上传断点存续,MD5,跨端技术,哪里的上传都是一样的
我正在参加跨端技术专题征文活动,详情查看:juejin.cn/post/710123…
前言
文件上传刚开始感觉好麻烦,还有续存断点,还有检查文件是否上传过,不必重复上传,而且框架的一些上传组件跟公司自己用到逻辑也不一样。所以还是废了一点事儿的,那么就好好了解下文件上传
安装
npm i spark-md5
页面中引用
import SparkMD5 from 'spark-md5'
具体使用方法
支持异步调用fileMd5(file).then((res)=>console.log(res))
,返回md5和文件大小
import SparkMD5 from "spark-md5";
export default function fileMd5(file) {
return new Promise(resolve => {
// 创建md5对象
const spark = new SparkMD5.ArrayBuffer();
// 读取文件内容
const fileReader = new FileReader();
// 文件加载
fileReader.onload = function(e) {
// 添加buffer数组
spark.append(e.target.result);
const md5 = spark.end();
resolve({
md5,
size: file.size
});
}
fileReader.onerror = function() {
console.warn("fileReader.onerror is error");
};
});
}
但是当文件特别大的时候就需要断点存续了,分段上传,上传大文件时,将大文件分解为一段一段的,然后上传至服务器,服务器将所有分解的文件组合成最初的大文件,实现大文件上传。
我们公司上传逻辑是这样的
- fileCheck:先检查文件是否上传过,上传过就直接返回文件地址,不用再重复上传了
- fileChunkCheck:没有上传过,检查文件的片段有没有上传过,避免重复上传浪费资源浪费时间
- fileChunkUpload:层层检查,这步才开始真正的上传。
import SparkMD5 from "spark-md5";
export default function chunkFileMd5(file) {
return new Promise(resolve => {
/**
* 生成MD5
*/
const dataArr = [];
const blobSlice = File.prototype.slice || File.prototype.mozSlice || File.prototype.webkitSlice;
//分段的大小 5MB
const chunkSize = 1048576 * 5;
// 计算多少段
const chunks = Math.ceil(file.size / chunkSize);
let currentChunk = 0;
const sparkAll = new SparkMD5.ArrayBuffer();
const spark = new SparkMD5.ArrayBuffer();
const fileReader = new FileReader();
fileReader.onload = function(e) {
// 添加数组buffer
spark.append(e.target.result);
// 添加数组buffer
sparkAll.append(e.target.result);
currentChunk++;
const md5 = spark.end();
dataArr.push({
//分段下标
currentChunk,
//分段总数
chunks,
md5,
blob,
size: ((start + chunkSize) >= file.size) ? (file.size % chunkSize) : chunkSize
});
//判断是否结束
if (currentChunk < chunks) {
//进行下一段
loadNext();
} else {
//总的结束
const md5 = sparkAll.end();
//返回结果
resolve({
md5,
size: file.size,
//分段数组
dataArr,
chunkSize
});
}
};
fileReader.onerror = function() {
console.warn("fileReader.onerror is error");
};
//分段开始
var start = null;
//分段结束
var end = null;
//分段文件
var blob = null;
function loadNext() {
start = currentChunk * chunkSize;
end = ((start + chunkSize) >= file.size) ? file.size : start + chunkSize;
blob = blobSlice.call(file, start, end);
//读取分段文件
fileReader.readAsArrayBuffer(blobSlice.call(file, start, end));
}
//默认开始
loadNext();
});
}
总结
这两个方法我一直在用,pc端的上传,小程序的上传,移动端的上传直接复制过去就好了。MD5是一种加密工具,但是在文件上传这里,我理解成文件的id,像这样检查文件是否上传过,直接传这个id就好了,方便很多也不会出错。
这次内容就总结到这里。我的文章都是学习过程中的总结,共同进步学习,如果发现错误,也欢迎留言指出,我及时更正。
转载自:https://juejin.cn/post/7103799605623521294