Skip to content

Commit 508b35e

Browse files
author
erichmzhang
committed
# 5.5.3
- 修复分块复制过程中,region不同可能导致的问题。 - 获取签名时增加超时机制,如果15秒内未能给出签名,则抛出错误。 - Copy 接口支持自定义头部 - 支持自定义 endpoint 中的 host 部分,以支撑动态加速的需求。
1 parent 87072a4 commit 508b35e

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

47 files changed

+317
-124
lines changed

CHANGELOG.md

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,11 @@
1+
# 5.5.3
2+
- 修复分块复制过程中,region不同可能导致的问题。
3+
- 获取签名时增加超时机制,如果15秒内未能给出签名,则抛出错误。
4+
- Copy 接口支持自定义头部
5+
- 支持自定义 endpoint 中的 host 部分,以支撑动态加速的需求。
6+
17
# 5.5.2
2-
- 加了校验MD开关
8+
- 加了校验MD5开关
39

410
# 5.5.1
511
-将部分文件与 FCUUID 作区分

QCloudCOSXML.podspec

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
Pod::Spec.new do |s|
22
s.name = "QCloudCOSXML"
3-
s.version = "5.5.2"
3+
s.version = "5.5.3"
44
s.summary = "QCloudCOSXML 腾讯云iOS-SDK组件"
55

66
s.homepage = "https://cloud.tencent.com/"
@@ -9,12 +9,12 @@ s.version = "5.5.2"
99
s.source = { :git => "https://github.com/tencentyun/qcloud-sdk-ios.git", :tag => s.version.to_s }
1010
s.ios.deployment_target = '8.0'
1111
s.source_files = 'QCloudCOSXML/Classes/**/*'
12-
s.dependency "QCloudCore",'5.5.2'
12+
s.dependency "QCloudCore",'5.5.3'
1313
s.static_framework = true
1414

1515
s.subspec 'Transfer' do |sbt|
1616
sbt.source_files = 'QCloudCOSXML/Classes/Transfer/**/*','QCloudCOSXML/Classes/Base/*'
17-
sbt.dependency "QCloudCore",'5.5.2'
17+
sbt.dependency "QCloudCore",'5.5.3'
1818
# sbt.static_framework=true
1919
end
2020
end

QCloudCOSXML/Classes/QCloudCOSXML.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,7 @@
2929
#import "QCloudAppendObjectRequest.h"
3030
#import "QCloudGetObjectRequest.h"
3131
#import "QCloudGetObjectRequest+Custom.h"
32+
#import "QCloudPutObjectRequest+Custom.h"
3233
/**
3334
简单复制对象的方法.
3435

QCloudCOSXML/Classes/QCloudCOSXMLVersion.h

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -6,15 +6,15 @@
66

77
#ifndef QCloudCOSXMLModuleVersion_h
88
#define QCloudCOSXMLModuleVersion_h
9-
#define QCloudCOSXMLModuleVersionNumber 505002
9+
#define QCloudCOSXMLModuleVersionNumber 505003
1010

1111
//dependency
12-
#if QCloudCoreModuleVersionNumber != 505002
13-
#error "库QCloudCOSXML依赖QCloudCore最小版本号为5.5.1,当前引入的QCloudCore版本号过低,请及时升级后使用"
12+
#if QCloudCoreModuleVersionNumber != 505003
13+
#error "库QCloudCOSXML依赖QCloudCore最小版本号为5.5.3,当前引入的QCloudCore版本号过低,请及时升级后使用"
1414
#endif
1515

1616
//
1717
FOUNDATION_EXTERN NSString * const QCloudCOSXMLModuleVersion;
1818
FOUNDATION_EXTERN NSString * const QCloudCOSXMLModuleName;
1919

20-
#endif
20+
#endif

QCloudCOSXML/Classes/QCloudCOSXMLVersion.m

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
#import "QCloudCOSXMLVersion.h"
2-
NSString * const QCloudCOSXMLModuleVersion = @"5.5.2";
2+
NSString * const QCloudCOSXMLModuleVersion = @"5.5.3";
33
NSString * const QCloudCOSXMLModuleName = @"QCloudCOSXML";
44
@interface QCloudQCloudCOSXMLLoad : NSObject
55
@end
@@ -26,4 +26,4 @@ + (void) load
2626
#pragma clang diagnostic pop
2727
}
2828
}
29-
@end
29+
@end

QCloudCOSXML/Classes/Transfer/request/QCloudCOSXMLCopyObjectRequest.h

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -92,7 +92,11 @@ typedef void(^CopyProgressBlock)(int64_t partsSent, int64_t totalPartsExpectedTo
9292

9393

9494
@property (nonatomic, weak) QCloudCOSTransferMangerService* transferManager;
95-
95+
/*
96+
在进行HTTP请求的时候,可以通过设置该参数来设置自定义的一些头部信息。
97+
通常情况下,携带特定的额外HTTP头部可以使用某项功能,如果是这类需求,可以通过设置该属性来实现。
98+
*/
99+
@property (strong, nonatomic) NSMutableDictionary* customHeaders;
96100

97101
/**
98102
在对大文件进行复制的过程中,会通过分片的方式进行复制。从该进度回调里可以获取当前已经复制了多少分片。
@@ -101,12 +105,6 @@ typedef void(^CopyProgressBlock)(int64_t partsSent, int64_t totalPartsExpectedTo
101105
*/
102106
- (void)setCopyProgressBlock:(void(^)(int64_t partsSent, int64_t totalPartsExpectedToSent))copyProgressBlock;
103107

104-
/*
105-
在进行HTTP请求的时候,可以通过设置该参数来设置自定义的一些头部信息。
106-
通常情况下,携带特定的额外HTTP头部可以使用某项功能,如果是这类需求,可以通过设置该属性来实现。
107-
例如使用加密等功能时,可以通过设置自定义头部来实现。对于小文件直接复制,该头文件将直接加载生成的 CopyObject 请求中。如果是大文件采用了分块复制的方式,那么该头部会加在 InitialMultipartUpload 和 UploadPartCopy 请求中。
108-
*/
109-
@property (strong, nonatomic) NSDictionary* customHeaders;
110108

111109

112110
/**
@@ -115,4 +113,6 @@ typedef void(^CopyProgressBlock)(int64_t partsSent, int64_t totalPartsExpectedTo
115113
@param QCloudRequestFinishBlock 完成回调
116114
*/
117115
- (void) setFinishBlock:(void (^)(QCloudCopyObjectResult* result, NSError * error))QCloudRequestFinishBlock;
116+
-(void)setCOSServerSideEncyption;
117+
-(void)setCOSServerSideEncyptionWithCustomerKey:(NSString *)customerKey;
118118
@end

QCloudCOSXML/Classes/Transfer/request/QCloudCOSXMLCopyObjectRequest.m

Lines changed: 29 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -38,13 +38,27 @@ - (instancetype)init {
3838
if (!self) {
3939
return nil;
4040
}
41+
_customHeaders = [NSMutableDictionary dictionary];
4142
_fileSize = 0;
4243
_sliceCount = 0;
4344
return self;
4445
}
4546

4647
- (void)fackStart {
4748
QCloudHeadObjectRequest* headObjectRequest = [[QCloudHeadObjectRequest alloc] init];
49+
NSMutableDictionary *customHeaders = [NSMutableDictionary dictionary];
50+
if (self.customHeaders) {
51+
if ([self.customHeaders objectForKey:@"x-cos-copy-source-server-side-encryption-customer-algorithm"]) {
52+
customHeaders[@"x-cos-server-side-encryption-customer-algorithm"] =self.customHeaders[@"x-cos-copy-source-server-side-encryption-customer-algorithm"];
53+
}
54+
if ([self.customHeaders objectForKey:@"x-cos-copy-source-server-side-encryption-customer-key"]) {
55+
customHeaders[@"x-cos-server-side-encryption-customer-key"] =self.customHeaders[@"x-cos-copy-source-server-side-encryption-customer-key"];
56+
}
57+
if ([self.customHeaders objectForKey:@"x-cos-copy-source-server-side-encryption-customer-key-MD5"]) {
58+
customHeaders[@"x-cos-server-side-encryption-customer-key-MD5"] =self.customHeaders[@"x-cos-copy-source-server-side-encryption-customer-key-MD5"];
59+
}
60+
}
61+
headObjectRequest.customHeaders = [customHeaders mutableCopy];
4862
headObjectRequest.bucket = self.sourceBucket;
4963
headObjectRequest.object = self.sourceObject;
5064
headObjectRequest.ifModifiedSince = self.objectCopyIfModifiedSince;
@@ -76,6 +90,7 @@ - (void)fackStart {
7690

7791
- (void)simpleCopy {
7892
QCloudPutObjectCopyRequest* request = [[QCloudPutObjectCopyRequest alloc] init];
93+
request.customHeaders =[self.customHeaders mutableCopy];
7994
request.bucket = self.bucket;
8095
request.object = self.object;
8196
request.objectCopyIfMatch = self.objectCopyIfMatch;
@@ -94,14 +109,14 @@ - (void)simpleCopy {
94109
[objectCopySource appendFormat:@"/%@",QCloudPercentEscapedStringFromString(self.sourceObject)];
95110
request.objectCopySource = objectCopySource;
96111
QCloudLogDebug(@"Object copy source url %@", objectCopySource);
97-
[[QCloudCOSXMLService defaultCOSXML] PutObjectCopy:request];
112+
[self.transferManager.cosService PutObjectCopy:request];
98113
}
99114

100115
- (void)multipleCopy {
101116
QCloudInitiateMultipartUploadRequest* initMultipartUploadRequest = [[QCloudInitiateMultipartUploadRequest alloc] init];
102117
initMultipartUploadRequest.bucket = self.bucket;
103118
initMultipartUploadRequest.object = self.object;
104-
initMultipartUploadRequest.customHeaders = self.customHeaders;
119+
initMultipartUploadRequest.customHeaders = [self.customHeaders mutableCopy];
105120
__weak typeof(self) weakSelf = self;
106121
[initMultipartUploadRequest setFinishBlock:^(QCloudInitiateMultipartUploadResult* result, NSError* error) {
107122
if (nil == error) {
@@ -114,7 +129,7 @@ - (void)multipleCopy {
114129
}
115130
}];
116131

117-
[[QCloudCOSXMLService defaultCOSXML] InitiateMultipartUpload:initMultipartUploadRequest];
132+
[self.transferManager.cosService InitiateMultipartUpload:initMultipartUploadRequest];
118133

119134
}
120135

@@ -142,6 +157,7 @@ - (void)uploadCopyParts {
142157
@autoreleasepool {
143158
QCloudUploadPartCopyRequest* request = [[QCloudUploadPartCopyRequest alloc] init];
144159
request.bucket = self.bucket;
160+
request.customHeaders = [self.customHeaders mutableCopy];
145161
request.object = self.object;
146162
NSMutableString* objectCopySource = [NSMutableString string];
147163
NSString* serviceURL =[service.configuration.endpoint serverURLWithBucket:self.sourceBucket appID:self.sourceAPPID].absoluteString;
@@ -210,7 +226,7 @@ - (void)finishUploadParts {
210226
}
211227
}
212228
}];
213-
[[QCloudCOSXMLService defaultCOSXML] CompleteMultipartUpload:request];
229+
[self.transferManager.cosService CompleteMultipartUpload:request];
214230
}
215231

216232
- (QCloudCOSXMLService*)tempService {
@@ -220,6 +236,7 @@ - (QCloudCOSXMLService*)tempService {
220236
QCloudServiceConfiguration* configuration = [QCloudServiceConfiguration new];
221237
configuration.signatureProvider = self.transferManager.configuration.signatureProvider;
222238
configuration.appID = self.sourceAPPID;
239+
configuration.endpoint.useHTTPS = self.transferManager.configuration.endpoint.useHTTPS;
223240
QCloudCOSXMLEndPoint* endpoint = [[QCloudCOSXMLEndPoint alloc] init];
224241
endpoint.regionName = self.sourceRegion;
225242
endpoint.serviceName = self.transferManager.configuration.endpoint.serviceName;
@@ -256,5 +273,13 @@ - (NSMutableArray*)uploadParts {
256273
- (void)setCopyProgressBlock:(void (^)(int64_t, int64_t))copyProgressBlock {
257274
self.copyProgressBlock = copyProgressBlock;
258275
}
276+
-(void)setCOSServerSideEncyptionWithCustomerKey:(NSString *)customerKey{
277+
NSData *data = [customerKey dataUsingEncoding:NSUTF8StringEncoding];
278+
NSString* excryptAES256Key = [data base64EncodedStringWithOptions:0]; // base64格式的字符串
279+
NSString *base64md5key = QCloudEncrytNSDataMD5Base64(data);
280+
self.customHeaders[@"x-cos-copy-source-server-side-encryption-customer-algorithm"] = @"AES256";
281+
self.customHeaders[@"x-cos-copy-source-server-side-encryption-customer-key"] = excryptAES256Key;
282+
self.customHeaders[@"x-cos-copy-source-server-side-encryption-customer-key-MD5"] = base64md5key;
283+
}
259284

260285
@end

QCloudCOSXML/Classes/Transfer/request/QCloudCOSXMLUploadObjectRequest.h

Lines changed: 9 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -33,11 +33,7 @@ typedef void(^InitMultipleUploadFinishBlock)(QCloudInitiateMultipartUploadResult
3333
@property (strong, nonatomic) NSString *bucket;
3434

3535

36-
/**
37-
在进行HTTP请求的时候,您可以通过设置该参数来设置自定义的一些头部信息。
38-
39-
*/
40-
@property (strong, nonatomic) NSDictionary* customHeaders;
36+
4137
/**
4238
需要上传的对象内容。可以传入NSData*或者NSURL*类型的变量
4339
*/
@@ -118,6 +114,11 @@ typedef void(^InitMultipleUploadFinishBlock)(QCloudInitiateMultipartUploadResult
118114
*/
119115
@property (nonatomic, assign) BOOL enableMD5Verification;
120116

117+
/*
118+
在进行HTTP请求的时候,可以通过设置该参数来设置自定义的一些头部信息。
119+
通常情况下,携带特定的额外HTTP头部可以使用某项功能,如果是这类需求,可以通过设置该属性来实现。
120+
*/
121+
@property (strong, nonatomic) NSMutableDictionary* customHeaders;
121122
/**
122123
上传完成后会通过该block回调。若error为空,可视为成功。
123124
@@ -130,4 +131,7 @@ typedef void(^InitMultipleUploadFinishBlock)(QCloudInitiateMultipartUploadResult
130131

131132

132133
- (void) abort:(QCloudRequestFinishBlock)finishBlock;
134+
-(void)setCOSServerSideEncyption;
135+
-(void)setCOSServerSideEncyptionWithCustomerKey:(NSString *)customerKey;
136+
-(void)setCOSServerSideEncyptionWithKMSCustomKey:(NSString *)customerKey jsonStr:(NSString *)jsonStr;
133137
@end

QCloudCOSXML/Classes/Transfer/request/QCloudCOSXMLUploadObjectRequest.m

Lines changed: 35 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,7 @@
2626
#import <QCloudCore/QCloudNetworkingAPI.h>
2727
#import <QCloudCore/QCloudUniversalPathFactory.h>
2828
#import "QCloudCOSTransferMangerService.h"
29+
#import "QCloudPutObjectRequest+Custom.h"
2930
static NSUInteger kQCloudCOSXMLUploadLengthLimit = 1*1024*1024;
3031
static NSUInteger kQCloudCOSXMLUploadSliceLength = 1*1024*1024;
3132

@@ -78,10 +79,11 @@ - (instancetype) init
7879
return self;
7980
}
8081
_requestCacheArray = [NSPointerArray weakObjectsPointerArray];
82+
_customHeaders = [NSMutableDictionary dictionary];
8183
_aborted = NO;
82-
_enableMD5Verification = YES;
8384
_recursiveLock = [NSRecursiveLock new];
8485
_progressLock = [NSRecursiveLock new];
86+
_enableMD5Verification = YES;
8587
return self;
8688
}
8789
- (NSDictionary *)modelCustomWillTransformFromDictionary:(NSDictionary *)dictionary {
@@ -189,6 +191,7 @@ - (void) fackStart {
189191
- (void) startSimpleUpload
190192
{
191193
QCloudPutObjectRequest* request = [QCloudPutObjectRequest new];
194+
request.enableMD5Verification = self.enableMD5Verification;
192195
__weak typeof(self) weakSelf = self;
193196
request.finishBlock = ^(id outputObject, NSError *error) {
194197
if (error) {
@@ -200,27 +203,7 @@ - (void) startSimpleUpload
200203
result.versionID = outputObject[@"x-cos-version-id"];
201204
}
202205

203-
if(self.enableMD5Verification) {
204-
result.eTag = [outputObject valueForKey:@"Etag"];
205-
NSString* localMD5 ;
206-
if ([weakSelf.body isKindOfClass:[NSData class]]) {
207-
localMD5 = QCloudEncrytNSDataMD5(weakSelf.body);
208-
} else if ([weakSelf.body isKindOfClass:[NSURL class]]) {
209-
localMD5 = QCloudEncrytFileMD5(((NSURL*)weakSelf.body).path);
210-
}
211-
NSString* MD5FromCOS = [result.eTag substringWithRange:NSMakeRange(1, result.eTag.length - 2)];
212-
if ( (localMD5 != nil) && (![localMD5.lowercaseString isEqualToString:MD5FromCOS]) ) {
213-
NSMutableString* errorMessageString = [[NSMutableString alloc] init];
214-
[errorMessageString appendFormat:@"简单上传过程中MD5校验与本地不一致,请检查本地文件在上传过程中是否发生了变化,建议调用删除接口将COS上的文件删除并重新上传"];
215-
if ( outputObject[@"x-cos-request-id"]!= nil) {
216-
NSString* requestID = outputObject[@"x-cos-request-id"];
217-
[errorMessageString appendFormat:@", Request id:%@",requestID];
218-
}
219-
NSError* error = [NSError qcloud_errorWithCode:QCloudNetworkErrorCodeMD5NotMatch message:errorMessageString];
220-
[weakSelf onError:error];
221-
return ;
222-
}
223-
}
206+
224207
result.key = weakSelf.object;
225208
result.bucket = weakSelf.bucket;
226209
result.location = QCloudCOSXMLObjectLocation(weakSelf.transferManager.configuration.endpoint,
@@ -246,7 +229,7 @@ - (void) startSimpleUpload
246229
request.grantFullControl = self.grantFullControl;
247230
request.sendProcessBlock = self.sendProcessBlock;
248231
request.delegate = self.delegate;
249-
request.customHeaders = self.customHeaders;
232+
request.customHeaders = [self.customHeaders mutableCopy];
250233
[self.requestCacheArray addPointer:(__bridge void * _Nullable)(request)];
251234
[self.transferManager.cosService PutObject:request];
252235
}
@@ -266,7 +249,7 @@ - (void) startMultiUpload {
266249
uploadRequet.grantRead = self.grantRead;
267250
uploadRequet.grantWrite = self.grantWrite;
268251
uploadRequet.grantFullControl = self.grantFullControl;
269-
uploadRequet.customHeaders = self.customHeaders;
252+
uploadRequet.customHeaders = [self.customHeaders mutableCopy];
270253
__weak typeof(self) weakSelf = self;
271254

272255
[uploadRequet setFinishBlock:^(QCloudInitiateMultipartUploadResult * _Nonnull result,
@@ -364,7 +347,7 @@ - (void) uploadOffsetBodys:(NSArray<QCloudFileOffsetBody*>*)allParts
364347
request.priority = QCloudAbstractRequestPriorityLow;
365348
request.partNumber = (int)body.index + 1;
366349
request.uploadId = self.uploadId;
367-
request.customHeaders = self.customHeaders;
350+
request.customHeaders = [self.customHeaders mutableCopy];
368351
request.body = body;
369352

370353
__block int64_t partBytesSent = 0;
@@ -401,7 +384,7 @@ - (void) uploadOffsetBodys:(NSArray<QCloudFileOffsetBody*>*)allParts
401384
NSString* localMD5String = [QCloudEncrytFileOffsetMD5(body.fileURL.path, body.offset, body.sliceLength) lowercaseString];
402385
if (![MD5FromeETag isEqualToString:localMD5String]) {
403386
NSMutableString* errorMessageString = [[NSMutableString alloc] init];
404-
[errorMessageString appendFormat:@"分片上传过程中MD5校验与本地不一致,请检查本地文件在上传过程中是否发生了变化,建议调用删除接口将COS上的文件删除并重新上传"];
387+
[errorMessageString appendFormat:@"分片上传过程中MD5校验与本地不一致,请检查本地文件在上传过程中是否发生了变化,建议调用删除接口将COS上的文件删除并重新上传,本地计算的 MD5 值:%@, 返回的 ETag值:%@",localMD5String,MD5FromeETag];
405388
if ( [outputObject __originHTTPURLResponse__]&& [[outputObject __originHTTPURLResponse__].allHeaderFields valueForKey:@"x-cos-request-id"]!= nil) {
406389
NSString* requestID = [[outputObject __originHTTPURLResponse__].allHeaderFields valueForKey:@"x-cos-request-id"];
407390
[errorMessageString appendFormat:@", Request id:%@",requestID];
@@ -616,6 +599,31 @@ - (void) abort:(QCloudRequestFinishBlock)finishBlock
616599
_aborted = YES;
617600
[self cancel];
618601
}
602+
-(void)setCOSServerSideEncyption{
603+
self.enableMD5Verification = NO;
604+
self.customHeaders[@"x-cos-server-side-encryption"] = @"AES256";
605+
}
606+
-(void)setCOSServerSideEncyptionWithCustomerKey:(NSString *)customerKey{
607+
self.enableMD5Verification = NO;
608+
NSData *data = [customerKey dataUsingEncoding:NSUTF8StringEncoding];
609+
NSString* excryptAES256Key = [data base64EncodedStringWithOptions:0]; // base64格式的字符串
610+
NSString *base64md5key = QCloudEncrytNSDataMD5Base64(data);
611+
self.customHeaders[@"x-cos-server-side-encryption-customer-algorithm"] = @"AES256";
612+
self.customHeaders[@"x-cos-server-side-encryption-customer-key"] = excryptAES256Key;
613+
self.customHeaders[@"x-cos-server-side-encryption-customer-key-MD5"] = base64md5key;
614+
615+
}
619616

620-
617+
-(void)setCOSServerSideEncyptionWithKMSCustomKey:(NSString *)customerKey jsonStr:(NSString *)jsonStr{
618+
self.enableMD5Verification = NO;
619+
self.customHeaders[@"x-cos-server-side-encryption"] = @"cos/kms";
620+
if(customerKey){
621+
self.customHeaders[@"x-cos-server-side-encryption-cos-kms-key-id"] = customerKey;
622+
}
623+
if(jsonStr){
624+
//先将string转换成data
625+
NSData *data = [jsonStr dataUsingEncoding:NSUTF8StringEncoding];
626+
self.customHeaders[@"x-cos-server-side-encryption-context"] = [data base64EncodedStringWithOptions:0];
627+
}
628+
}
621629
@end

QCloudCOSXML/Classes/Transfer/request/QCloudCompleteMultipartUploadRequest.h

Lines changed: 1 addition & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -80,11 +80,7 @@ completeRequst.uploadId = @"uploadId"; //本次分片上传的UploadID
8080
*/
8181
@property (strong, nonatomic) QCloudCompleteMultipartUploadInfo *parts;
8282

83-
/*
84-
在进行HTTP请求的时候,可以通过设置该参数来设置自定义的一些头部信息。
85-
通常情况下,携带特定的额外HTTP头部可以使用某项功能,如果是这类需求,可以通过设置该属性来实现。
86-
*/
87-
@property (strong, nonatomic) NSDictionary* customHeaders;
83+
8884

8985
- (void) setFinishBlock:(void (^)(QCloudUploadObjectResult* result, NSError * error))QCloudRequestFinishBlock;
9086
@end

0 commit comments

Comments
 (0)