最近更新时间:2024-01-17 19:29:50
当文件大小超过5GB时,适用分块上传方式。分块上传包括三个步骤:
初始化
上传分块
合并分块
如下所示为分块上传标准代码流程:
// 1.初始化
client.object.multitpart_upload_init({
Bucket: '<bucketName>',
Key: '<objectKey>', // 必填
ACL: '', // 访问控制,非必填
StorageClass: '', // 存储类型,非必填
headers: {} // 非必填
}, function (rerr, data, response, body) {
console.log(data) // data中会包含后续上传需要的UploadId
})
// 2.上传分块
// notice: 上传分块前需要自行对文件进行分块处理
client.object.upload_part({
Bucket: '<bucketName>',
Key: '<objectKey>', // 必填
PartNumber: '', // 必填, 上传的块id
UploadId: '', // 必填, 上传的uploadid
Body: '' // 必填, 分块数据
}, function (rerr, data, response, body) {
console.log(response.statusCode) // 上传成功返回200
console.log(response.headers.etag) // 上传成功返回etag,后面合并分块会用到
})
// 3.合并分块
client.object.upload_complete({
Bucket: '<bucketName>',
Key: '<objectKey>', // 必填
UploadId: '', // 必填, 上传的uploadid
Body: '' // 必填, 所有分块数据的集合,以xml格式传递
}, function (rerr, data, response, body) {
console.log(data)
})
如下所示为完整的分块上传示例:
function upload() {
const bucket = '' // 上传的桶
const key = '' // 上传的key
const filePath = '' // 文件路径
const chunkSize = 5*1024*1024 // 分块大小
const contentType = '' // 文件类型
let uploadId = '' // 上传id
const fileSize = 100*1025*1024 // 文件大小
const count = parseInt(fileSize / chunkSize) + ((fileSize % chunkSize == 0 ? 0: 1)); // 总块数
const initParams = {
Key: key,
Bucket: bucket
}
client.object.multitpart_upload_init(initParams, function (err, data, res, body) {
data = util.xml2json.parser(data) // util为sdk内部的工具类
uploadId = data.InitiateMultipartUploadResult.UploadId
console.log(`获取到上传id: ${uploadId}`)
client.config({
dataType: 'xml'
});
let chunkNum = 0;
let etags = [] // 存放上传成功的分块etag
console.log('开始分块上传...')
up();
function up() {
let start = chunkNum * chunkSize
console.log(`开始上传 第${chunkNum} 块文件...`)
// 是否全部上传
if (chunkNum < count) {
util.getChunk(filePath, chunkSize, start, function (buffer) {
const params = {
Bucket: bucket,
Key: key,
UploadId: uploadId,
PartNumber: chunkNum + 1, // 传值从1开始
Body: buffer,
Type: contentType
}
console.log('分块上传参数:', params)
client.object.upload_part(params, function (err, data, res, body) {
if (err) {
throw err;
} else {
const etag = res.headers.etag;
console.log(`上传成功,获取etag信息:${etag}`)
etags.push(etag)
chunkNum++;
up();
}
})
})
} else {
// 合并上传的分块
const params = {
Bucket: bucket,
Key: key,
PartNumber: count,
Type: contentType,
UploadId: uploadId,
Body: util.generateCompleteXML(arr) // 将分块数据转成xml
}
console.log('合并参数:', params)
client.object.upload_complete(params, function (err, data, res, body) {
if (err) throw err;
console.log('上传成功,合并文件:', err, data)
})
}
}
});
}
注:
该完整示例没有对异常做处理,是一种理想情况下的场景。建议结合自身的业务调整逻辑。有关异常处理的详情,请参见文档:SDK异常处理。
有关分块上传的API详情,请参见文档:Initiate Multipart Upload、Upload Part、Complete Multipart Upload。
纯净模式