来源 | urlify.cn/InYfyu
1 背景
用户本地有一份txt或者csv文件,无论是从业务数据库导出、还是其他路子获取,当须要利用蚂蚁的大数据剖析工具进行数据加工、挖掘和共创运用的时候,首先要将本地文件上传至ODPS,普通的小文件通过浏览器上传至做事器,做一层中转便可以实现,但当这份文件非常大到了10GB级别,我们就须要思考另一种形式的技能方案了,也便是本文要阐述的方案。
技能哀求紧张有以下几方面:
支持超大数据量、10G级别以上稳定性:除网络非常情形100%成功准确性:数据无丢失,读写准确性100%效率:1G文件分钟级、10G文件小时级体验:实时进度感知、网络非常断点续传、定制字符分外处理2 文件上传选型
文件上传至ODPS基本思路是先文件上传至某中转区域存储,然后同步至ODPS,根据存储介质可以分为两类,一类是运用做事器磁盘,另一类类是中间介质,OSS作为阿里云推举的海量、安全低本钱云存储做事,并且有丰富的API支持,成为中间介质的首选。而文件上传至OSS又分为web直传和sdk上传两种方案,因此上传方案有如下三种,详细优缺陷比拟如下:
蚂蚁的文本上传功能演进过程中对第一种、第二种方案均有实践,缺陷比较明显,如上表所述,不知足业务需求,因此大文件上传终极方案是方案三。
3 整体方案
以下是方案三的整体过程示意图。
要求步骤如下:
用户向运用做事器取到上传policy和回调设置。运用做事器返回上传policy和回调。用户直接向OSS发送文件上传要求。 等文件数据上传完,OSS给用户Response前,OSS会根据用户的回调设置,要求用户的做事器。如果运用做事器返回成功,那么就返回用户成功,如果运用做事器返回失落败,那么OSS也返回给用户失落败。这样确保了用户上传成功,运用做事器已经收到关照了。运用做事器给OSS返回。OSS将运用做事器返回的内容返回给用户。启动后台同步引擎实行oss到odps的数据同步。同步实时进度返回返回给运用做事器,同时展示给用户。4 技能方案
4.1 上传
OSS供应了丰富的SDK,有大略上传、表单上传、断点续传等等,对付超大文件供应的上传功能建议采取断点续传办法,优点是可以对大文件并行分片上传,利用OSS的并行处理能力,中间停息也可以从当前位置连续上传,网络环境影响可以降到最低。
4.2 下载
OSS文件下载同样也有多种办法,普通下载、流式下载、断点续传下载、范围下载等等,若直接下载到本地同样建议断点续传下载,但我们的需求并不仅仅是下载文件本地存储,而是读取文件做数据从OSS到ODPS的同步,因此不做中间存储,直接边读变写,一方面采取OSS流式读取,一方面ODPS tunnel上传,用多线程读写办法提高同步速率。
4.3 两阶段数据转移
文件从本地到ODPS可以分为两个阶段,第一阶段前端分片断点续传将本地文件上传至OSS,第二阶段后端流式读写将数据从OSS同步至ODPS,如下图所示:
涉及技能点:
4.3.1 前端,js sdk带STS token 安全上传
在须要上传的文件较大时,可以通过multipartUpload接口进行分片上传。分片上传的好处是将一个大要求分成多个小要求来实行,这样当个中一些要求失落败后,不须要重新上传全体文件,而只须要上传失落败的分片就可以了。一样平常对付大于100MB的文件,建议采取分片上传的方法,每次进行分片上传都建议重新new一个新的OSS实例。
阿里云分片上传流程紧张会调用3个api,包含
InitiateMultipartUpload, 分片任务初始化接口。UploadPart, 单独的分片上传接口。CompleteMultipartUpload, 分片上传完成后任务完成接口临时访问凭据是通过阿里云Security Token Service(STS)来实现授权的一种办法。实在现请拜会STS Java SDK。临时访问凭据的流程如下:
客户端向做事器端发起得到授权的要求。做事器端先验证客户真个合法性。如果是合法客户端,那么做事器端会利用自己的AccessKey来向STS发起一个要求授权的要求,详细可以参考访问掌握。做事器端获取临时凭据之后返回给客户端。客户端利用获取的临时凭据来发起向OSS的上传要求,更详细的要求布局可以参考临时授权访问。客户端可以缓存该凭据用来上传,直到凭据失落效再向做事器端要求新的凭据。4.3.2 后端,多线程流式读写
OSS端:如果要下载的文件太大,或者一次性下载耗时太长,可以多线程流式下载,一次处理部分内容,直到完成文件的下载。ODPS端:tunnel sdk对OSS流式数据直接写入,一次完全的数据写入流程常日包括以下步骤:先对数据进行划分;
为每个数据块指定 block id,即调用 openRecordWriter(id);然后用一个或多个线程分别将这些 block 上传上去, 并在某个 block 上传失落败往后,须要对全体 block 进行重传;在所有 block 都上传往后,向做事端供应上传成功的 blockid list 进行校验,即调用 session.commit([1,2,3,…]) 而由于做事端对block管理,连接超时等的一些限定,上传过程逻辑变得比较繁芜,为了简化上传过程,SDK供应了更高等的一种RecordWriter——TunnelBufferWriter。5 实现过程及压测
太多了,可以参考我写的这篇文章:http://blog.ncmem.com/wordpress/2019/08/09/%e5%a4%a7%e6%96%87%e4%bb%b6%e4%b8%8a%e4%bc%a0%e8%a7%a3%e5%86%b3%e6%96%b9%e6%a1%88/
6 总结
实测结果显示,本文的上传方案实现了第一节提出的几点技能哀求,如下:
支持超大数据量、10G级别以上没有任何压力,紧张是前端在分片上传设置好分片限额即可(最大10000片,每片最大100G),目前设置每片1M知足10G需求。稳定性:实测不雅观察网络非常情形较少,文件内容正常情形下100%成功。准确性:实测数据无丢失,读写准确性100%。效率:办公网带宽1.5M/s的情形下1G文件分钟级、10G文件小时级,实际速率视用户真个当前网络带宽变革。体验:实时进度感知、网络非常断点续传、定制字符分外处理等高等功能可以提升用户体验。