文件分片上传

文章介绍了如何通过将大文件分割成小块并使用多个worker线程并发上传,以提高上传速度并降低网络中断导致的重传风险。同时提及了使用MD5对分块进行加密以确保数据完整性的部分。
摘要由CSDN通过智能技术生成

当遇到文件太大、网络不好等情况时,如果发生连接中断、挂掉,那整个文件就白传,需要重头再传,这是非常不人性化的用户体验。所以我们可以根据网络情况将文件分成小碎片,最后在服务端将碎片合并,以降低网络传输中断带来的风险。

使用worker开启更多线程,优化上传速度

index.js
const fileDom = document.querySelector('input')
//设置文件分块大小
const CHUNK_SIZE = 2 * 1024
//本机可开启最多线程数量
const MAX_WORKER = navigator.hardwareConcurrency || 4
let finished = 0
const result = []
// 在回调里获取文件总大小,计算分片数量
fileDom.onchange = function (e) {
    const file = e.target.files[0]
    const chunkLength = Math.ceil(file.size / CHUNK_SIZE)
    //计算出每个worker可处理分片数量
    const count = Math.ceil(chunkLength / MAX_WORKER)
    for (let i = 0; i < MAX_WORKER; i++) {
        const myWorker = new Worker('./fileWorker.js', { type: 'module' })
        const startIndex = i * count
        let endIndex = startIndex + count
        if (endIndex > chunkLength) {
            endIndex = chunkLength
        }
        myWorker.postMessage([file, CHUNK_SIZE, startIndex, endIndex])
        myWorker.onmessage = function (e) {
            //完成一个 关闭一个
            finished++
            myWorker.terminate()
            e.data.forEach(element => {
                result[element.index] = element
            });
            if (finished === MAX_WORKER) {
                // 处理后续上传任务
                console.log(result, '最后输出result')
            }
        }
    }
}
 fileWorker.js
//最后可使用md5文件进行加密 得到hash值
// import SparkMD5 from 'spark-md5'
// addEventListener("message", (e) => {
//     console.log(e.data, 'e')
// });
//等价于下面的事件
self.onmessage = async function (e) {
    // console.log(e.data, 'e')
    const [file, CHUNK_SIZE, startIndex, endIndex] = e.data
    const result = []
    for (let i = startIndex; i < endIndex; i++) {
        const chunk = await getChunk(file, CHUNK_SIZE, i)
        result.push(chunk)
    }
    self.postMessage(result)
}
function getChunk (file, size, index) {
    const hash1 = new SparkMD5()
    console.log(hash1, 'hash1')
    return new Promise((resolve) => {
        const start = index * size
        const end = start + size
        const chunkFile = file.slice(start, end)
        const fr = new FileReader()
        fr.onload = function (e) {
            // const arrBuffer = e.target.result
            // const hash = new SparkMD5.ArrayBuffer()
            resolve({
                start, end, chunkFile, index
            })
        }
        fr.readAsArrayBuffer(chunkFile)
    })
}

那个hash值没加上,后续完善 

  • 16
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
ElementUI 是一套基于 Vue.js 的组件库,它提供了丰富的 UI 组件来构建 Web 应用程序。要实现文件分片上传,我们可以利用 ElementUI 中的 Upload 组件配合一些其他的技术来实现。 首先,我们需要在页面中引入 ElementUI 的样式以及相关的 JavaScript 文件。然后,我们可以使用 ElementUI 的 Upload 组件创建一个文件上传的区域。 在 Upload 组件中,我们需要设置一些参数来实现文件分片上传。具体包括以下几个参数: 1. `action`:指定上传的 API 接口,需要根据后端的实际接口进行配置。 2. `headers`:设置请求头,常见的有 token 等认证信息。 3. `auto-upload`:设置为 false,禁用自动上传,我们需要手动控制上传过程。 4. `multiple`:是否支持多文件上传。 5. `on-success`:上传成功后的回调函数,可以在这里处理上传成功后的逻辑。 接下来,我们需要使用 JavaScript 来实现文件分片上传。可以使用 FileReader 对象来读取文件,使用 Blob 对象来切分文件。然后,我们可以利用 XMLHttpRequest 对象来发送分片请求,并监听其上传进度。 在每个分片上传成功后,我们需要记录已上传分片,并检查是否需要继续上传下一个分片。当所有分片上传完成后,我们可以调用后端接口来进行文件的合并。 需要注意的是,文件分片上传涉及到文件切分、上传进度的监听、文件合并等复杂的操作,需要在前端和后端共同配合完成。 总之,通过结合 ElementUI 的 Upload 组件和其他相关技术,我们可以实现文件分片上传功能,提高文件上传的效率和稳定性。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值