news 2026/4/16 1:52:29

vue3中如何实现大文件断点续传的解决方案总结?

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
vue3中如何实现大文件断点续传的解决方案总结?

一个大三仔的编程血泪史:大文件上传系统开发实录

前言

各位老铁们好,我是广西某不知名大学网络工程专业的大三学生,最近被导师逼着做一个"支持10G文件上传、断点续传、文件夹层级保留、全浏览器兼容、还要加密传输存储"的变态文件管理系统。导师说做好了能推荐去大厂,做不好就等着延毕吧(哭唧唧)。

技术选型

经过一番折腾,我选定了以下"豪华套餐":

  • 前端:Vue3 + WebUploader(百度开源组件)
  • 后端:Python(虽然我还不会,但听说能速成)
  • 数据库:MySQL(学校机房老古董只认这个)
  • 存储:阿里云OSS(白嫖的免费额度)
  • 开发工具:VSCode(比Dev-C++香多了)

前端实现(原生JS版)

以下是经过我三天三夜不眠不休(实际是抄了20篇博客)写出的前端核心代码:

// 兼容IE8的XMLHttpRequest封装(头发已掉光)functioncreateXHR(){if(window.XMLHttpRequest){returnnewXMLHttpRequest();}elseif(window.ActiveXObject){try{returnnewActiveXObject("Msxml2.XMLHTTP");}catch(e){try{returnnewActiveXObject("Microsoft.XMLHTTP");}catch(e){alert("您的浏览器太古老了,建议使用Chrome或Firefox");returnnull;}}}}// 文件分片上传类(命名暴露了我是菜鸟)functionFileUploader(){this.chunkSize=5*1024*1024;// 5MB分片this.file=null;this.fileId='';this.uploadedChunks=[];this.init();}FileUploader.prototype={init:function(){// 本地存储进度(兼容IE8的localStorage替代方案)if(!window.localStorage){window.localStorage={getItem:function(key){returndocument.cookie.replace(newRegExp('(?:^|.*;\\s*)'+encodeURIComponent(key).replace(/[\-\.\+\*]/g,"\\$&")+'\\s*\\=\\s*((?:[^;](?!;))*[^;]?).*'),'$1')||null;},setItem:function(key,value){document.cookie=encodeURIComponent(key)+'='+encodeURIComponent(value)+'; expires=Tue, 19 Jan 2038 03:14:07 GMT; path=/';}};}},// 计算文件MD5(IE8哭晕在厕所)calculateFileMD5:function(file,callback){if(window.FileReader&&window.crypto){// 现代浏览器方案constreader=newFileReader();reader.onload=(e)=>{constarrayBuffer=e.target.result;crypto.subtle.digest('MD5',arrayBuffer).then(buffer=>{consthashArray=Array.from(newUint8Array(buffer));consthashHex=hashArray.map(b=>b.toString(16).padStart(2,'0')).join('');callback(hashHex);});};reader.readAsArrayBuffer(file);}else{// IE8兼容方案(实际不可用,这里只是占位)alert("您的浏览器不支持MD5计算,上传可能不安全");callback('fake-md5-for-ie8');}},// 分片上传核心方法uploadFile:function(file){this.file=file;this.fileId=file.name+'-'+file.size+'-'+file.lastModified;// 从本地存储加载已上传分片信息constsavedChunks=localStorage.getItem('upload_'+this.fileId);this.uploadedChunks=savedChunks?JSON.parse(savedChunks):[];// 计算总分片数consttotalChunks=Math.ceil(file.size/this.chunkSize);// 模拟上传过程(实际需要替换为真实AJAX请求)letuploaded=0;for(leti=0;i<totalChunks;i++){// 跳过已上传的分片if(this.uploadedChunks.includes(i)){uploaded++;continue;}// 这里应该是真实的AJAX上传代码// 为了演示,我们用setTimeout模拟setTimeout((chunkIndex)=>{console.log(`上传分片${chunkIndex}/${totalChunks}`);// 模拟上传成功if(Math.random()>0.1){// 10%失败率测试断点续传this.uploadedChunks.push(chunkIndex);localStorage.setItem('upload_'+this.fileId,JSON.stringify(this.uploadedChunks));uploaded++;if(uploaded===totalChunks){console.log('上传完成!');// 这里应该调用合并文件的接口}}else{console.log(`分片${chunkIndex}上传失败,将重试...`);}},i*1000,i);}},// 文件夹上传(递归实现)uploadFolder:function(folderEntry){if(!window.FileReader||!window.DirectoryReader){alert("您的浏览器不支持文件夹上传,请使用Chrome/Firefox最新版");return;}constdirectoryReader=folderEntry.createReader();directoryReader.readEntries((entries)=>{for(letentryofentries){if(entry.isFile){entry.file(file=>{// 为文件夹中的文件添加路径前缀constrelativePath=entry.fullPath.substring(1);// 去掉开头的'/'constfakeFile=newFile([file],file.name,{type:file.type,lastModified:file.lastModified});// 这里需要扩展File对象以保存路径信息(实际实现更复杂)console.log('准备上传文件:',relativePath,fakeFile);this.uploadFile(fakeFile);});}elseif(entry.isDirectory){this.uploadFolder(entry);}}});}};// Vue3组件示例(极简版)const{createApp,ref}=Vue;createApp({setup(){constuploader=ref(null);consthandleFileChange=(e)=>{constfiles=e.target.files;if(files.length>0){if(!uploader.value){uploader.value=newFileUploader();}uploader.value.uploadFile(files[0]);}};consthandleFolderChange=(e)=>{// 文件夹上传需要用户拖放或使用// 这里只是示例constfolderInput=e.target;if(folderInput.files&&folderInput.files.length>0){// 实际需要处理DirectoryEntry对象console.log('检测到文件夹输入,但前端实现复杂...');}};return{handleFileChange,handleFolderChange};}}).mount('#app');

开发趣事

  1. IE8兼容噩梦:为了兼容IE8,我不得不实现了一个cookie-based的localStorage替代方案,结果发现IE8的cookie有4KB限制,大文件上传直接崩溃。

  2. MD5计算:IE8没有crypto API,我尝试用Flash实现MD5,结果发现学校机房禁用了Flash。

  3. 文件夹上传:发现WebUploader在IE和国产浏览器上对文件夹的支持各不相同,最后不得不写了一堆浏览器嗅探代码。

  4. 断点续传:本地存储在隐私模式下不可用,导致测试时经常丢失进度,差点摔键盘。

求助与招募

现在项目卡在后端开发上,求Python大神救救孩子:

  1. 需要实现文件分片接收接口
  2. 需要实现分片合并接口
  3. 需要实现加密存储功能
  4. 需要兼容所有浏览器(包括IE8)

重金求师

  • 加入QQ群:374992201,新人进群送1-99元红包
  • 推荐工作成功者,提成20%(项目金额)
  • 招收超级会员,提成直接50%(比如2万项目直接提1万)

最终目标

希望在毕业答辩时能演示一个:

  • 支持10G文件上传
  • 断点续传(重启电脑也不怕)
  • 文件夹层级完美保留
  • 全浏览器兼容
  • 加密传输存储

的完整文件管理系统,让导师刮目相看,顺利进入大厂!

(PS:如果实在做不出来,可能要考虑转行送外卖…)

将组件复制到项目中

示例中已经包含此目录

引入组件

配置接口地址

接口地址分别对应:文件初始化,文件数据上传,文件进度,文件上传完毕,文件删除,文件夹初始化,文件夹删除,文件列表
参考:http://www.ncmem.com/doc/view.aspx?id=e1f49f3e1d4742e19135e00bd41fa3de

处理事件

启动测试

启动成功

效果

数据库

效果预览

文件上传

文件刷新续传

支持离线保存文件进度,在关闭浏览器,刷新浏览器后进行不丢失,仍然能够继续上传

文件夹上传

支持上传文件夹并保留层级结构,同样支持进度信息离线保存,刷新页面,关闭页面,重启系统不丢失上传进度。

批量下载

支持文件批量下载

下载续传

文件下载支持离线保存进度信息,刷新页面,关闭页面,重启系统均不会丢失进度信息。

文件夹下载

支持下载文件夹,并保留层级结构,不打包,不占用服务器资源。

下载示例

点击下载完整示例

版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/3/31 6:04:36

Silverlight 2中文入门指南:经典技术学习与历史回顾

对于关注微软技术的开发者来说&#xff0c;《Essential Silverlight 2中文版》是一本具有历史意义的入门指南。这本书系统性地介绍了Silverlight 2的核心技术和开发方法&#xff0c;虽然Silverlight技术已经逐步退出主流&#xff0c;但了解它对于理解富互联网应用的发展历程仍有…

作者头像 李华
网站建设 2026/4/5 3:06:33

JS正则验证正数方法:从基础到严格定义

在JavaScript开发中&#xff0c;经常需要对用户输入进行验证&#xff0c;确保其符合预期的数字格式。验证正数是其中常见且基础的需求&#xff0c;合理的正则表达式可以高效、准确地完成这一任务。下面我将从实际应用角度&#xff0c;分享几个关键点。 如何用正则表达式验证正…

作者头像 李华
网站建设 2026/4/14 18:41:39

金融风控平台如何实现Word批注内容到网页的完整迁移?

企业网站后台管理系统富文本编辑器功能扩展开发记录 一、需求分析与技术选型 作为北京某软件公司的前端开发工程师&#xff0c;近期接到客户需求&#xff1a;在企业网站后台管理系统的文章发布模块中增加Word粘贴、Word文档导入以及微信公众号内容粘贴功能。经过详细分析&…

作者头像 李华
网站建设 2026/4/15 12:06:34

Java基于Spring Boot+Vue的户外爱好者网站的设计与实现

所需该项目可以在最下面查看联系方式&#xff0c;为防止迷路可以收藏文章&#xff0c;以防后期找不到 这里写目录标题项目介绍系统实现截图技术栈介绍Spring Boot与Vue结合使用的优势Spring Boot的优点Vue的优点Spring Boot 框架结构解析Vue介绍系统执行流程Java语言介绍系统测…

作者头像 李华
网站建设 2026/4/9 15:56:29

西门子200smart PLC脉冲除尘器程序大揭秘

西门子200smart PLC所写程序的脉冲除尘器程序&#xff0c;昆仑通态触摸屏&#xff0c;包含PLC程序&#xff0c;触摸屏组态画面&#xff0c;工艺流程&#xff0c;电气原理图。 真实工程项目&#xff0c;目前稳定运行一年多嘿&#xff0c;各位工控小伙伴们&#xff01;今天来跟大…

作者头像 李华