你可能不知道的大文件上传

前言:大文件上传的普遍方案基本都是分片上传,如果把文件上传看做是一个不可分割的事务,那么分片的目标就是把一个大事务划分为一个个小事务; 1. BFF层(Backend for Frontend) BFF层 (Backend for Fron...

这篇文章已从掘金同步到个人博客,原始发布地址为 掘金原文

前端领秀-公众号.png

1. BFF层(Backend for Frontend)

image.png

2.如何减少页面阻塞?

分片上传的第一个首要目标就是尽量避免相同的分片重复上传。服务器必须要能够识别来自各个客户端的上传请求。

服务器如何识别哪些分片是相同的?

image.png

客户端需要做两件事:

image.png

为了解决这个问题,理想状态下,每次上传的大文件都是最新的,这样就无需等待整体hash的计算结果,直接上传分片就行,同时可以把分片操作使用多线程+异步的方式进行处理。

image.png

第一次上传有了前几个分片之后,中断后继续上传,发现上一次上传的几个分片已经存在,直接快进到第4个分片,不管中断多少次,直到上传完成为止;

这样做的好处是:页面完全无阻塞,也无需等待整体haah即可启动上传

3.前后端如何协调?

3.1.创建文件协议

当客户端发送分片到服务端的时候,需要告知服务器分片属于哪一次文件上传,因此需要一个唯一标识来表示某一次文件上传。

如何获取文件上传的标识?

image.png

3.2.haah校验

客户端需要校验单个分片或整个文件的hash,服务器需要告知客户端目前具体情况。

image.png

3.3.分片数据上传

分片数据通过二进制上传到服务器,服务把分片保存起来; image.png

3.4.分片合并

所有分片全部上传后,通过该协议请求服务器完成合并。

image.png

4.如何保证分片不重复?

这里的重复指的是:不保存、不上传重复分片。这就必须要求分片 跨文件唯一,并且 永不删除

image.png 也就是说:服务器并不保存合并之后的文件,仅记录文件中的分片顺序

4.1 合并分片到底做了什么?

合并会造成很多问题,最主要的是:极其耗时、数据冗余,所以服务器并不发生真正的合并,而是在数据库中记录文件中包含的分片。因此,合并操作时,服务器仅做简单的处理:

4.2 访问文件怎么办?

由于服务器并未发生真正的文件合并,当后续请求该文件时,服务器需要动态处理,具体做法: