提交
This commit is contained in:
20
Pods/AliyunOSSiOS/AliyunOSSSDK/NSData+OSS.h
generated
Normal file
20
Pods/AliyunOSSiOS/AliyunOSSSDK/NSData+OSS.h
generated
Normal file
@@ -0,0 +1,20 @@
|
||||
//
|
||||
// NSData+OSS.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by ws on 2023/12/28.
|
||||
// Copyright © 2023 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
@interface NSData (OSS)
|
||||
|
||||
- (NSString *)hexString;
|
||||
- (NSData *)calculateSha256;
|
||||
|
||||
@end
|
||||
|
||||
NS_ASSUME_NONNULL_END
|
||||
41
Pods/AliyunOSSiOS/AliyunOSSSDK/NSData+OSS.m
generated
Normal file
41
Pods/AliyunOSSiOS/AliyunOSSSDK/NSData+OSS.m
generated
Normal file
@@ -0,0 +1,41 @@
|
||||
//
|
||||
// NSData+OSS.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by ws on 2023/12/28.
|
||||
// Copyright © 2023 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "NSData+OSS.h"
|
||||
#import <CommonCrypto/CommonDigest.h>
|
||||
|
||||
@implementation NSData (OSS)
|
||||
|
||||
- (NSString *)hexString {
|
||||
NSMutableString *hexString = [NSMutableString string];
|
||||
Byte *byte = (Byte *)[self bytes];
|
||||
for (int i = 0; i<[self length]; i++) {
|
||||
[hexString appendFormat:@"%x", (*(byte + i) >> 4) & 0xf];
|
||||
[hexString appendFormat:@"%x", *(byte + i) & 0xf];
|
||||
}
|
||||
return hexString;
|
||||
}
|
||||
|
||||
- (NSData *)calculateSha256 {
|
||||
unsigned char *digest = NULL;
|
||||
|
||||
digest = malloc(CC_SHA256_DIGEST_LENGTH * sizeof(unsigned char));
|
||||
memset(digest, 0x0, CC_SHA256_DIGEST_LENGTH);
|
||||
CC_SHA256(self.bytes, (CC_LONG)self.length, digest);
|
||||
|
||||
if (digest) {
|
||||
NSData *data = [NSData dataWithBytes:digest length:CC_SHA256_DIGEST_LENGTH];
|
||||
free(digest);
|
||||
return data;
|
||||
}
|
||||
free(digest);
|
||||
|
||||
return nil;
|
||||
}
|
||||
|
||||
@end
|
||||
22
Pods/AliyunOSSiOS/AliyunOSSSDK/NSDate+OSS.h
generated
Normal file
22
Pods/AliyunOSSiOS/AliyunOSSSDK/NSDate+OSS.h
generated
Normal file
@@ -0,0 +1,22 @@
|
||||
//
|
||||
// NSDate+OSS.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/7/31.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
|
||||
/**
|
||||
Categories NSDate
|
||||
*/
|
||||
@interface NSDate (OSS)
|
||||
+ (void)oss_setClockSkew:(NSTimeInterval)clockSkew;
|
||||
+ (NSDate *)oss_dateFromString:(NSString *)string;
|
||||
+ (NSDate *)oss_clockSkewFixedDate;
|
||||
- (NSString *)oss_asStringValue;
|
||||
+ (NSDate *)oss_dateFromString:(NSString *)string
|
||||
dateFormat:(NSString *)dateFormat;
|
||||
- (NSString *)oss_asStringValueWithDateFormat:(NSString *)dateFormat;
|
||||
@end
|
||||
68
Pods/AliyunOSSiOS/AliyunOSSSDK/NSDate+OSS.m
generated
Normal file
68
Pods/AliyunOSSiOS/AliyunOSSSDK/NSDate+OSS.m
generated
Normal file
@@ -0,0 +1,68 @@
|
||||
//
|
||||
// NSDate+OSS.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/7/31.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "NSDate+OSS.h"
|
||||
|
||||
@implementation NSDate (OSS)
|
||||
|
||||
NSString * const serverReturnDateFormat = @"EEE, dd MMM yyyy HH:mm:ss z";
|
||||
|
||||
static NSTimeInterval _clockSkew = 0.0;
|
||||
|
||||
+ (void)oss_setClockSkew:(NSTimeInterval)clockSkew {
|
||||
@synchronized(self) {
|
||||
_clockSkew = clockSkew;
|
||||
}
|
||||
}
|
||||
|
||||
+ (NSDate *)oss_clockSkewFixedDate {
|
||||
NSTimeInterval skew = 0.0;
|
||||
@synchronized(self) {
|
||||
skew = _clockSkew;
|
||||
}
|
||||
return [[NSDate date] dateByAddingTimeInterval:(-1 * skew)];
|
||||
}
|
||||
|
||||
+ (NSDate *)oss_dateFromString:(NSString *)string {
|
||||
NSDateFormatter *dateFormatter = [NSDateFormatter new];
|
||||
dateFormatter.timeZone = [NSTimeZone timeZoneWithName:@"GMT"];
|
||||
dateFormatter.locale = [NSLocale localeWithLocaleIdentifier:@"en_US"];
|
||||
dateFormatter.dateFormat = serverReturnDateFormat;
|
||||
|
||||
return [dateFormatter dateFromString:string];
|
||||
}
|
||||
|
||||
- (NSString *)oss_asStringValue {
|
||||
NSDateFormatter *dateFormatter = [NSDateFormatter new];
|
||||
dateFormatter.timeZone = [NSTimeZone timeZoneWithName:@"GMT"];
|
||||
dateFormatter.locale = [NSLocale localeWithLocaleIdentifier:@"en_US"];
|
||||
dateFormatter.dateFormat = serverReturnDateFormat;
|
||||
|
||||
return [dateFormatter stringFromDate:self];
|
||||
}
|
||||
|
||||
+ (NSDate *)oss_dateFromString:(NSString *)string
|
||||
dateFormat:(NSString *)dateFormat {
|
||||
NSDateFormatter *dateFormatter = [NSDateFormatter new];
|
||||
dateFormatter.timeZone = [NSTimeZone timeZoneWithName:@"GMT"];
|
||||
dateFormatter.locale = [NSLocale localeWithLocaleIdentifier:@"en_US"];
|
||||
dateFormatter.dateFormat = dateFormat;
|
||||
|
||||
return [dateFormatter dateFromString:string];
|
||||
}
|
||||
|
||||
- (NSString *)oss_asStringValueWithDateFormat:(NSString *)dateFormat {
|
||||
NSDateFormatter *dateFormatter = [NSDateFormatter new];
|
||||
dateFormatter.timeZone = [NSTimeZone timeZoneWithName:@"GMT"];
|
||||
dateFormatter.locale = [NSLocale localeWithLocaleIdentifier:@"en_US"];
|
||||
dateFormatter.dateFormat = dateFormat;
|
||||
|
||||
return [dateFormatter stringFromDate:self];
|
||||
}
|
||||
|
||||
@end
|
||||
15
Pods/AliyunOSSiOS/AliyunOSSSDK/NSMutableData+OSS_CRC.h
generated
Normal file
15
Pods/AliyunOSSiOS/AliyunOSSSDK/NSMutableData+OSS_CRC.h
generated
Normal file
@@ -0,0 +1,15 @@
|
||||
//
|
||||
// NSMutableData+OSS_CRC.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by 怀叙 on 2017/11/29.
|
||||
// Copyright © 2017年 阿里云. All rights reserved.
|
||||
//
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
|
||||
@interface NSMutableData (OSS_CRC)
|
||||
|
||||
- (uint64_t)oss_crc64;
|
||||
|
||||
@end
|
||||
19
Pods/AliyunOSSiOS/AliyunOSSSDK/NSMutableData+OSS_CRC.m
generated
Normal file
19
Pods/AliyunOSSiOS/AliyunOSSSDK/NSMutableData+OSS_CRC.m
generated
Normal file
@@ -0,0 +1,19 @@
|
||||
//
|
||||
// NSMutableData+OSS_CRC.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by 怀叙 on 2017/11/29.
|
||||
// Copyright © 2017年 阿里云. All rights reserved.
|
||||
//
|
||||
|
||||
#import "NSMutableData+OSS_CRC.h"
|
||||
#include "aos_crc64.h"
|
||||
|
||||
@implementation NSMutableData (OSS_CRC)
|
||||
|
||||
- (uint64_t)oss_crc64
|
||||
{
|
||||
return aos_crc64(0, self.mutableBytes, self.length);
|
||||
}
|
||||
|
||||
@end
|
||||
15
Pods/AliyunOSSiOS/AliyunOSSSDK/NSMutableDictionary+OSS.h
generated
Normal file
15
Pods/AliyunOSSiOS/AliyunOSSSDK/NSMutableDictionary+OSS.h
generated
Normal file
@@ -0,0 +1,15 @@
|
||||
//
|
||||
// NSMutableDictionary+OSS.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/8/1.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
|
||||
@interface NSMutableDictionary (OSS)
|
||||
|
||||
- (void)oss_setObject:(id)anObject forKey:(id <NSCopying>)aKey;
|
||||
|
||||
@end
|
||||
19
Pods/AliyunOSSiOS/AliyunOSSSDK/NSMutableDictionary+OSS.m
generated
Normal file
19
Pods/AliyunOSSiOS/AliyunOSSSDK/NSMutableDictionary+OSS.m
generated
Normal file
@@ -0,0 +1,19 @@
|
||||
//
|
||||
// NSMutableDictionary+OSS.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/8/1.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "NSMutableDictionary+OSS.h"
|
||||
|
||||
@implementation NSMutableDictionary (OSS)
|
||||
|
||||
- (void)oss_setObject:(id)anObject forKey:(id <NSCopying>)aKey {
|
||||
if (anObject && aKey) {
|
||||
[self setObject:anObject forKey:aKey];
|
||||
}
|
||||
}
|
||||
|
||||
@end
|
||||
19
Pods/AliyunOSSiOS/AliyunOSSSDK/NSSet+OSS.h
generated
Normal file
19
Pods/AliyunOSSiOS/AliyunOSSSDK/NSSet+OSS.h
generated
Normal file
@@ -0,0 +1,19 @@
|
||||
//
|
||||
// NSSet+OSS.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by ws on 2023/12/28.
|
||||
// Copyright © 2023 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
@interface NSSet (OSS)
|
||||
|
||||
- (NSString *)componentsJoinedByString:(NSString *)separator;
|
||||
|
||||
@end
|
||||
|
||||
NS_ASSUME_NONNULL_END
|
||||
30
Pods/AliyunOSSiOS/AliyunOSSSDK/NSSet+OSS.m
generated
Normal file
30
Pods/AliyunOSSiOS/AliyunOSSSDK/NSSet+OSS.m
generated
Normal file
@@ -0,0 +1,30 @@
|
||||
//
|
||||
// NSSet+OSS.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by ws on 2023/12/28.
|
||||
// Copyright © 2023 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "NSSet+OSS.h"
|
||||
|
||||
@implementation NSSet (OSS)
|
||||
|
||||
- (NSString *)componentsJoinedByString:(NSString *)separator {
|
||||
NSMutableString *builder = [NSMutableString new];
|
||||
int i = 0;
|
||||
|
||||
for (NSObject *part in self) {
|
||||
if ([part isKindOfClass:[NSString class]]) {
|
||||
[builder appendString:(NSString *)part];
|
||||
if (i < [self count] - 1) {
|
||||
[builder appendString:separator];
|
||||
}
|
||||
}
|
||||
i++;
|
||||
}
|
||||
|
||||
return builder;
|
||||
}
|
||||
|
||||
@end
|
||||
34
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSAllRequestNeededMessage.h
generated
Normal file
34
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSAllRequestNeededMessage.h
generated
Normal file
@@ -0,0 +1,34 @@
|
||||
//
|
||||
// OSSAllRequestNeededMessage.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/1/22.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
#import "OSSConstants.h"
|
||||
#import "OSSTask.h"
|
||||
|
||||
/**
|
||||
All necessary information in one OSS request.
|
||||
*/
|
||||
@interface OSSAllRequestNeededMessage : NSObject
|
||||
@property (nonatomic, strong) NSString *endpoint;
|
||||
@property (nonatomic, strong) NSString *httpMethod;
|
||||
@property (nonatomic, strong) NSString *bucketName;
|
||||
@property (nonatomic, strong) NSString *objectKey;
|
||||
@property (nonatomic, strong) NSString *contentType;
|
||||
@property (nonatomic, strong) NSString *contentMd5;
|
||||
@property (nonatomic, strong) NSString *range;
|
||||
@property (nonatomic, strong) NSString *date;
|
||||
@property (nonatomic, strong) NSMutableDictionary *headerParams;
|
||||
@property (nonatomic, copy) NSDictionary *params;
|
||||
@property (nonatomic, copy) NSString *contentSHA1;
|
||||
@property (nonatomic, assign) BOOL isHostInCnameExcludeList;
|
||||
@property (nonatomic, assign) BOOL isUseUrlSignature;
|
||||
@property (nonatomic, copy) NSSet<NSString *> *additionalHeaderNames;
|
||||
|
||||
- (OSSTask *)validateRequestParamsInOperationType:(OSSOperationType)operType;
|
||||
|
||||
@end
|
||||
72
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSAllRequestNeededMessage.m
generated
Normal file
72
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSAllRequestNeededMessage.m
generated
Normal file
@@ -0,0 +1,72 @@
|
||||
//
|
||||
// OSSAllRequestNeededMessage.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/1/22.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSAllRequestNeededMessage.h"
|
||||
|
||||
#import "OSSDefine.h"
|
||||
#import "OSSUtil.h"
|
||||
|
||||
@implementation OSSAllRequestNeededMessage
|
||||
|
||||
- (instancetype)init
|
||||
{
|
||||
self = [super init];
|
||||
if (self) {
|
||||
_date = [[NSDate oss_clockSkewFixedDate] oss_asStringValue];
|
||||
_headerParams = [NSMutableDictionary dictionary];
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
- (void)setHeaderParams:(NSMutableDictionary *)headerParams {
|
||||
if (!headerParams || [headerParams isEqualToDictionary:_headerParams]) {
|
||||
return;
|
||||
}
|
||||
_headerParams = [headerParams mutableCopy];
|
||||
}
|
||||
|
||||
- (OSSTask *)validateRequestParamsInOperationType:(OSSOperationType)operType {
|
||||
NSString * errorMessage = nil;
|
||||
|
||||
if (!self.endpoint) {
|
||||
errorMessage = @"Endpoint should not be nil";
|
||||
}
|
||||
|
||||
if (!self.bucketName && operType != OSSOperationTypeGetService) {
|
||||
errorMessage = @"Bucket name should not be nil";
|
||||
}
|
||||
|
||||
if (self.bucketName && ![OSSUtil validateBucketName:self.bucketName]) {
|
||||
errorMessage = @"Bucket name invalid";
|
||||
}
|
||||
|
||||
if (!self.objectKey &&
|
||||
(operType != OSSOperationTypeGetBucket && operType != OSSOperationTypeCreateBucket
|
||||
&& operType != OSSOperationTypeDeleteBucket && operType != OSSOperationTypeGetService
|
||||
&& operType != OSSOperationTypeGetBucketACL&& operType != OSSOperationTypeDeleteMultipleObjects
|
||||
&& operType != OSSOperationTypeListMultipartUploads
|
||||
&& operType != OSSOperationTypeGetBucketInfo)) {
|
||||
errorMessage = @"Object key should not be nil";
|
||||
}
|
||||
|
||||
|
||||
|
||||
if (self.objectKey && ![OSSUtil validateObjectKey:self.objectKey]) {
|
||||
errorMessage = @"Object key invalid";
|
||||
}
|
||||
|
||||
if (errorMessage) {
|
||||
return [OSSTask taskWithError:[NSError errorWithDomain:OSSClientErrorDomain
|
||||
code:OSSClientErrorCodeInvalidArgument
|
||||
userInfo:@{OSSErrorMessageTOKEN: errorMessage}]];
|
||||
} else {
|
||||
return [OSSTask taskWithResult:nil];
|
||||
}
|
||||
}
|
||||
|
||||
@end
|
||||
533
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSClient.h
generated
Normal file
533
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSClient.h
generated
Normal file
@@ -0,0 +1,533 @@
|
||||
//
|
||||
// OSSClient.h
|
||||
// oss_ios_sdk
|
||||
//
|
||||
// Created by zhouzhuo on 8/16/15.
|
||||
// Copyright (c) 2015 aliyun.com. All rights reserved.
|
||||
//
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
@class OSSGetServiceRequest;
|
||||
@class OSSCreateBucketRequest;
|
||||
@class OSSDeleteBucketRequest;
|
||||
@class OSSHeadObjectRequest;
|
||||
@class OSSGetBucketRequest;
|
||||
@class OSSGetBucketACLRequest;
|
||||
@class OSSGetObjectRequest;
|
||||
@class OSSGetObjectACLRequest;
|
||||
@class OSSPutObjectRequest;
|
||||
@class OSSPutObjectACLRequest;
|
||||
@class OSSDeleteObjectRequest;
|
||||
@class OSSDeleteMultipleObjectsRequest;
|
||||
@class OSSCopyObjectRequest;
|
||||
@class OSSInitMultipartUploadRequest;
|
||||
@class OSSUploadPartRequest;
|
||||
@class OSSCompleteMultipartUploadRequest;
|
||||
@class OSSListPartsRequest;
|
||||
@class OSSListMultipartUploadsRequest;
|
||||
@class OSSAbortMultipartUploadRequest;
|
||||
@class OSSAppendObjectRequest;
|
||||
@class OSSResumableUploadRequest;
|
||||
@class OSSMultipartUploadRequest;
|
||||
@class OSSCallBackRequest;
|
||||
@class OSSImagePersistRequest;
|
||||
@class OSSGetBucketInfoRequest;
|
||||
@class OSSPutSymlinkRequest;
|
||||
@class OSSGetSymlinkRequest;
|
||||
@class OSSRestoreObjectRequest;
|
||||
@class OSSGetObjectTaggingRequest;
|
||||
@class OSSDeleteObjectTaggingRequest;
|
||||
@class OSSPutObjectTaggingRequest;
|
||||
|
||||
@class OSSTask;
|
||||
@class OSSExecutor;
|
||||
@class OSSNetworking;
|
||||
@class OSSClientConfiguration;
|
||||
@protocol OSSCredentialProvider;
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
/**
|
||||
OSSClient is the entry class to access OSS in an iOS client. It provides all the methods to communicate with OSS.
|
||||
Generally speaking, only one instance of OSSClient is needed in the whole app.
|
||||
*/
|
||||
@interface OSSClient : NSObject
|
||||
|
||||
/**
|
||||
OSS endpoint. It varies in different regions. Please check out OSS official website for the exact endpoints for your data.
|
||||
*/
|
||||
@property (nonatomic, strong) NSString * endpoint;
|
||||
|
||||
/**
|
||||
The networking instance for sending and receiving data
|
||||
*/
|
||||
@property (nonatomic, strong) OSSNetworking * networking;
|
||||
|
||||
/**
|
||||
The credential provider instance
|
||||
*/
|
||||
@property (nonatomic, strong) id<OSSCredentialProvider> credentialProvider;
|
||||
|
||||
/**
|
||||
Client configuration instance
|
||||
*/
|
||||
@property (nonatomic, strong) OSSClientConfiguration * clientConfiguration;
|
||||
|
||||
/// OSS services Region
|
||||
@property (nonatomic, copy) NSString *region;
|
||||
|
||||
/// cloudBoxId OSS cloud box id
|
||||
@property (nonatomic, copy) NSString *cloudBoxId;
|
||||
|
||||
/**
|
||||
oss operation task queue
|
||||
*/
|
||||
@property (nonatomic, strong, readonly) OSSExecutor * ossOperationExecutor;
|
||||
|
||||
/**
|
||||
Initializes an OSSClient instance with the default client configuration.
|
||||
@endpoint it specifies domain of the bucket's region. Starting 2017, the domain must be prefixed with "https://" to follow Apple's ATS policy.
|
||||
For example: "https://oss-cn-hangzhou.aliyuncs.com"
|
||||
@credentialProvider The credential provider
|
||||
*/
|
||||
- (instancetype)initWithEndpoint:(NSString *)endpoint
|
||||
credentialProvider:(id<OSSCredentialProvider>) credentialProvider;
|
||||
|
||||
/**
|
||||
Initializes an OSSClient with the custom client configuration.
|
||||
@endpoint it specifies domain of the bucket's region. Starting 2017, the domain must be prefixed with "https://" to follow Apple's ATS policy.
|
||||
For example: "https://oss-cn-hangzhou.aliyuncs.com"
|
||||
@credentialProvider The credential provider
|
||||
@conf The custom client configuration such as retry time, timeout values, etc.
|
||||
*/
|
||||
- (instancetype)initWithEndpoint:(NSString *)endpoint
|
||||
credentialProvider:(id<OSSCredentialProvider>)credentialProvider
|
||||
clientConfiguration:(OSSClientConfiguration *)conf;
|
||||
|
||||
#pragma mark restful-api
|
||||
|
||||
/**
|
||||
The corresponding RESTFul API: GetService
|
||||
Gets all the buckets of the current user
|
||||
Notes:
|
||||
1. STS is not supported yet in this call.
|
||||
2. When all buckets are returned, the xml in response body does not have nodes of Prefix, Marker, MaxKeys, IsTruncated and NextMarker.
|
||||
If there're remaining buckets to return, the xml will have these nodes. The nextMarker is the value of marker in the next call.
|
||||
*/
|
||||
- (OSSTask *)getService:(OSSGetServiceRequest *)request;
|
||||
|
||||
@end
|
||||
|
||||
|
||||
@interface OSSClient (Bucket)
|
||||
|
||||
/**
|
||||
The corresponding RESTFul API: PutBucket
|
||||
Creates a bucket--it does not support anonymous access. By default, the datacenter used is oss-cn-hangzhou.
|
||||
Callers could explicitly specify the datacenter for the bucket to optimize the performance and cost or meet the regulation requirement.
|
||||
Notes:
|
||||
1. STS is not supported yet.
|
||||
*/
|
||||
- (OSSTask *)createBucket:(OSSCreateBucketRequest *)request;
|
||||
|
||||
/**
|
||||
The corresponding RESTFul API: DeleteBucket
|
||||
Deletes a bucket.
|
||||
*/
|
||||
- (OSSTask *)deleteBucket:(OSSDeleteBucketRequest *)request;
|
||||
|
||||
/**
|
||||
The corresponding RESTFul API: GetBucket
|
||||
Lists all objects in a bucket. It could be specified with filters such as prefix, marker, delimeter and max-keys.
|
||||
*/
|
||||
- (OSSTask *)getBucket:(OSSGetBucketRequest *)request;
|
||||
|
||||
/**
|
||||
The corresponding RESTFul API: GetBucketInfo
|
||||
Gets the {@link Bucket}'s basic information as well as its ACL.
|
||||
*/
|
||||
- (OSSTask *)getBucketInfo:(OSSGetBucketInfoRequest *)request;
|
||||
|
||||
/**
|
||||
The corresponding RESTFul API: GetBucketACL
|
||||
Gets the bucket ACL.
|
||||
*/
|
||||
- (OSSTask *)getBucketACL:(OSSGetBucketACLRequest *)request;
|
||||
|
||||
@end
|
||||
|
||||
|
||||
@interface OSSClient (Object)
|
||||
|
||||
/**
|
||||
The corresponding RESTFul API: HeadObject
|
||||
Gets the object's metadata information. The object's content is not returned.
|
||||
*/
|
||||
- (OSSTask *)headObject:(OSSHeadObjectRequest *)request;
|
||||
|
||||
/**
|
||||
The corresponding RESTFul API: GetObject
|
||||
Gets the whole object (includes content). It requires caller have read permission on the object.
|
||||
*/
|
||||
- (OSSTask *)getObject:(OSSGetObjectRequest *)request;
|
||||
|
||||
/**
|
||||
The corresponding RESTFul API: GetObjectACL
|
||||
get the acl of an object.
|
||||
*/
|
||||
- (OSSTask *)getObjectACL:(OSSGetObjectACLRequest *)request;
|
||||
|
||||
/**
|
||||
The corresponding RESTFul API: PutObject
|
||||
Uploads a file.
|
||||
*/
|
||||
- (OSSTask *)putObject:(OSSPutObjectRequest *)request;
|
||||
|
||||
/**
|
||||
Sets the object's ACL. Right now an object has three access permissions: private, public-ready, public-read-write.
|
||||
The operation specifies the x-oss-object-acl header in the put request. The caller must be the owner of the object.
|
||||
If succeeds, it returns HTTP status 200; otherwise it returns related error code and error messages.
|
||||
*/
|
||||
- (OSSTask *)putObjectACL:(OSSPutObjectACLRequest *)request;
|
||||
|
||||
/**
|
||||
The corresponding RESTFul API: AppendObject
|
||||
Appends data to an existing or non-existing object. The object created by this operation is appendable.
|
||||
As a comparison, the object created by Put Object is normal (non-appendable).
|
||||
*/
|
||||
- (OSSTask *)appendObject:(OSSAppendObjectRequest *)request;
|
||||
|
||||
/**
|
||||
* @brief Appends data to an existing or non-existing object on the OSS server.
|
||||
* The object created by this operation is appendable.
|
||||
* @request request
|
||||
* @crc64ecma crc64ecma
|
||||
* if object has been stored on OSS server, you need to invoke headObject
|
||||
* api get object's crc64ecma,then use this api to append data to the
|
||||
* object.
|
||||
*/
|
||||
- (OSSTask *)appendObject:(OSSAppendObjectRequest *)request withCrc64ecma:(nullable NSString *)crc64ecma;
|
||||
|
||||
/**
|
||||
The corresponding RESTFul API: copyObject
|
||||
Copies an existing object to another one.The operation sends a PUT request with x-oss-copy-source header to specify the source object.
|
||||
OSS server side will detect and copy the object. If it succeeds, the new object's metadata information will be returned.
|
||||
The operation applies for files less than 1GB. For big files, use UploadPartCopy RESTFul API.
|
||||
*/
|
||||
- (OSSTask *)copyObject:(OSSCopyObjectRequest *)request;
|
||||
|
||||
/**
|
||||
* Batch deletes the specified files under a specific bucket. If the files
|
||||
* are non-exist, the operation will still return successful.
|
||||
*
|
||||
* @param request
|
||||
* A OSSDeleteMultipleObjectsRequest instance which specifies the
|
||||
* bucket and file keys to delete.
|
||||
* @return A OSSTask with result of OSSDeleteMultipleObjectsResult instance which specifies each
|
||||
* file's result in normal mode or only failed deletions in quite
|
||||
* mode. By default it's quite mode.
|
||||
*/
|
||||
- (OSSTask *)deleteMultipleObjects:(OSSDeleteMultipleObjectsRequest *)request;
|
||||
|
||||
/**
|
||||
The corresponding RESTFul API: DeleteObject
|
||||
Deletes an object
|
||||
*/
|
||||
- (OSSTask *)deleteObject:(OSSDeleteObjectRequest *)request;
|
||||
|
||||
/**
|
||||
* Creates a symbol link to a target file under the bucket---this is not
|
||||
* supported for archive class bucket.
|
||||
*
|
||||
* @param request
|
||||
* A OSSPutSymlinkRequest instance that specifies the
|
||||
* bucket name, symlink name.
|
||||
* @return An instance of OSSTask. On successful execution, `task.result` will
|
||||
* contain an instance of `OSSPutSymlinkResult`,otherwise will contain
|
||||
* an instance of NSError.
|
||||
*
|
||||
* for more information,please refer to https://help.aliyun.com/document_detail/45126.html
|
||||
*/
|
||||
- (OSSTask *)putSymlink:(OSSPutSymlinkRequest *)request;
|
||||
|
||||
/**
|
||||
* Gets the symlink information for the given symlink name.
|
||||
*
|
||||
* @param request
|
||||
* A OSSGetSymlinkRequest instance which specifies the bucket
|
||||
* name and symlink name.
|
||||
* @return An instance of OSSTask. On successful execution, `task.result` will
|
||||
* contain an instance of `OSSGetSymlinkResult`,otherwise will contain
|
||||
* an instance of NSError.
|
||||
*
|
||||
* for more information,please refer to https://help.aliyun.com/document_detail/45146.html
|
||||
*/
|
||||
- (OSSTask *)getSymlink:(OSSGetSymlinkRequest *)request;
|
||||
|
||||
/**
|
||||
* Restores the object of archive storage. The function is not applicable to
|
||||
* Normal or IA storage. The restoreObject() needs to be called prior to
|
||||
* calling getObject() on an archive object.
|
||||
*
|
||||
* @param request
|
||||
* A container for the necessary parameters to execute the RestoreObject
|
||||
* service method.
|
||||
*
|
||||
* @return An instance of OSSTask. On successful execution, `task.result` will
|
||||
* contain an instance of `OSSRestoreObjectResult`,otherwise will contain
|
||||
* an instance of NSError.
|
||||
*
|
||||
* for more information,please refer to https://help.aliyun.com/document_detail/52930.html
|
||||
*/
|
||||
- (OSSTask *)restoreObject:(OSSRestoreObjectRequest *)request;
|
||||
|
||||
/**
|
||||
* You can call this operation to query the tags of an object.
|
||||
*
|
||||
* @param request
|
||||
* A OSSGetObjectTaggingRequest instance which specifies the bucket
|
||||
* name and object key.
|
||||
*
|
||||
* @return An instance of OSSTask. On successful execution, `task.result` will
|
||||
* contain an instance of `OSSGetObjectTaggingResult`,otherwise will contain
|
||||
* an instance of NSError.
|
||||
*
|
||||
* for more information,please refer to https://help.aliyun.com/document_detail/114878.html
|
||||
*/
|
||||
- (OSSTask *)getObjectTagging:(OSSGetObjectTaggingRequest *)request;
|
||||
|
||||
/**
|
||||
* You can call this operation to add tags to an object or update the tags added to
|
||||
* the bucket. The object tagging feature uses a key-value pair to tag an object.
|
||||
*
|
||||
* @param request
|
||||
* A OSSPutObjectTaggingRequest instance which specifies the bucket
|
||||
* name、object key and tags.
|
||||
*
|
||||
* @return An instance of OSSTask. On successful execution, `task.result` will
|
||||
* contain an instance of `OSSPutObjectTaggingResult`,otherwise will contain
|
||||
* an instance of NSError.
|
||||
*
|
||||
* for more information,please refer to https://help.aliyun.com/document_detail/114855.html
|
||||
*/
|
||||
- (OSSTask *)putObjectTagging:(OSSPutObjectTaggingRequest *)request;
|
||||
|
||||
/**
|
||||
* You can call this operation to delete the tags of a specified object.
|
||||
*
|
||||
* @param request
|
||||
* A OSSDeleteObjectTaggingRequest instance which specifies the bucket
|
||||
* name and object key.
|
||||
*
|
||||
* @return An instance of OSSTask. On successful execution, `task.result` will
|
||||
* contain an instance of `OSSDeleteObjectTaggingResult`,otherwise will contain
|
||||
* an instance of NSError.
|
||||
*
|
||||
* for more information,please refer to https://help.aliyun.com/document_detail/114879.html
|
||||
*/
|
||||
- (OSSTask *)deleteObjectTagging:(OSSDeleteObjectTaggingRequest *)request;
|
||||
|
||||
|
||||
|
||||
@end
|
||||
|
||||
@interface OSSClient (MultipartUpload)
|
||||
|
||||
/**
|
||||
The corresponding RESTFul API: InitiateMultipartUpload
|
||||
Initiates a multipart upload to get a upload Id. It's needed before starting uploading parts data.
|
||||
The upload Id is used for subsequential operations such as aborting the upload, querying the uploaded parts, etc.
|
||||
*/
|
||||
- (OSSTask *)multipartUploadInit:(OSSInitMultipartUploadRequest *)request;
|
||||
|
||||
/**
|
||||
The corresponding RESTFul API: UploadPart
|
||||
After the multipart upload is initiated, this API could be called to upload the data to the target file with the upload Id.
|
||||
Every uploaded part has a unique id called part number, which ranges from 1 to 10,000.
|
||||
For a given upload Id, the part number identifies the specific range of the data in the whole file.
|
||||
If the same part number is used for another upload, the existing data will be overwritten by the new upload.
|
||||
Except the last part, all other part's minimal size is 100KB.
|
||||
But no minimal size requirement on the last part.
|
||||
*/
|
||||
- (OSSTask *)uploadPart:(OSSUploadPartRequest *)request;
|
||||
|
||||
/**
|
||||
The corresponding RESTFul API: CompleteMultipartUpload
|
||||
This API is to complete the multipart upload after all parts data have been uploaded.
|
||||
It must be provided with a valid part list (each part has the part number and ETag).
|
||||
OSS will validate every part and then complete the multipart upload.
|
||||
If any part is invalid (e.g. the part is updated by another part upload), this API will fail.
|
||||
*/
|
||||
- (OSSTask *)completeMultipartUpload:(OSSCompleteMultipartUploadRequest *)request;
|
||||
|
||||
/**
|
||||
The corresponding RESTFul API: ListParts
|
||||
Lists all uploaded parts of the specified upload id.
|
||||
*/
|
||||
- (OSSTask *)listParts:(OSSListPartsRequest *)request;
|
||||
|
||||
/**
|
||||
The corresponding RESTFul API: ListMultipartUploads
|
||||
Lists all multipart uploads with the specified bucket.
|
||||
*/
|
||||
- (OSSTask *)listMultipartUploads:(OSSListMultipartUploadsRequest *)request;
|
||||
|
||||
/**
|
||||
The corresponding RESTFul API: AbortMultipartUpload
|
||||
Aborts the multipart upload by the specified upload Id.
|
||||
Once the multipart upload is aborted by this API, all parts data will be deleted and the upload Id is invalid anymore.
|
||||
*/
|
||||
- (OSSTask *)abortMultipartUpload:(OSSAbortMultipartUploadRequest *)request;
|
||||
|
||||
- (OSSTask *)abortResumableMultipartUpload:(OSSResumableUploadRequest *)request;
|
||||
|
||||
/**
|
||||
Multipart upload API
|
||||
*/
|
||||
- (OSSTask *)multipartUpload:(OSSMultipartUploadRequest *)request;
|
||||
/**
|
||||
TODOTODO
|
||||
Resumable upload API
|
||||
This API wraps the multipart upload and also enables resuming upload by reading/writing the checkpoint data.
|
||||
For a new file, multipartUploadInit() needs to be called first to get the upload Id. Then use this upload id to call this API to upload the data.
|
||||
If the upload fails, checks the error messages:
|
||||
If it's a recoverable error, then call this API again with the same upload Id to retry. The uploaded data will not be uploaded again.
|
||||
Otherwise then you may need to recreates a new upload Id and call this method again.
|
||||
Check out demo for the detail.
|
||||
*/
|
||||
- (OSSTask *)resumableUpload:(OSSResumableUploadRequest *)request;
|
||||
|
||||
/**
|
||||
* multipart upload sequentially in order,support resume upload
|
||||
*/
|
||||
- (OSSTask *)sequentialMultipartUpload:(OSSResumableUploadRequest *)request;
|
||||
|
||||
@end
|
||||
|
||||
|
||||
@interface OSSClient (PresignURL)
|
||||
|
||||
/**
|
||||
Generates a signed URL for the object and anyone has this URL will get the GET permission on the object.
|
||||
@bucketName object's bucket name
|
||||
@objectKey Object name
|
||||
@interval Expiration time in seconds. The URL could be specified with the expiration time to limit the access window on the object.
|
||||
*/
|
||||
- (OSSTask *)presignConstrainURLWithBucketName:(NSString *)bucketName
|
||||
withObjectKey:(NSString *)objectKey
|
||||
withExpirationInterval:(NSTimeInterval)interval;
|
||||
|
||||
/**
|
||||
Generates a signed URL for the object and anyone has this URL will get the specified permission on the object.
|
||||
@bucketName object's bucket name
|
||||
@objectKey Object name
|
||||
@interval Expiration time in seconds. The URL could be specified with the expiration time to limit the access window on the object.
|
||||
@parameter it could specify allowed HTTP methods
|
||||
*/
|
||||
- (OSSTask *)presignConstrainURLWithBucketName:(NSString *)bucketName
|
||||
withObjectKey:(NSString *)objectKey
|
||||
withExpirationInterval:(NSTimeInterval)interval
|
||||
withParameters:(NSDictionary *)parameters;
|
||||
|
||||
/**
|
||||
Generates a signed URL for the object and anyone has this URL will get the specified permission on the object. currently only support get and head method.
|
||||
@bucketName object's bucket name
|
||||
@objectKey Object name
|
||||
@httpMethod http method.currently only support get and head.
|
||||
@interval Expiration time in seconds. The URL could be specified with the expiration time to limit the access window on the object.
|
||||
@parameter it could specify allowed HTTP methods
|
||||
*/
|
||||
- (OSSTask *)presignConstrainURLWithBucketName:(NSString *)bucketName
|
||||
withObjectKey:(NSString *)objectKey
|
||||
httpMethod:(NSString *)method
|
||||
withExpirationInterval:(NSTimeInterval)interval
|
||||
withParameters:(NSDictionary *)parameters;
|
||||
|
||||
|
||||
/// Generates a signed URL for the object and anyone has this URL will get the specified permission on the object.
|
||||
/// @param bucketName object's bucket name
|
||||
/// @param objectKey Object name
|
||||
/// @param method http method.currently only support get and head.
|
||||
/// @param interval Expiration time in seconds. The URL could be specified with the expiration time to limit the access window on the object.
|
||||
/// @param parameters it could specify allowed HTTP methods
|
||||
/// @param contentType Content-Type to url sign
|
||||
/// @param contentMd5 Content-MD5 to url sign
|
||||
- (OSSTask *)presignConstrainURLWithBucketName:(NSString *)bucketName
|
||||
withObjectKey:(NSString *)objectKey
|
||||
httpMethod:(NSString *)method
|
||||
withExpirationInterval:(NSTimeInterval)interval
|
||||
withParameters:(NSDictionary *)parameters
|
||||
contentType:(nullable NSString *)contentType
|
||||
contentMd5:(nullable NSString *)contentMd5;
|
||||
|
||||
/// Generates a signed URL for the object and anyone has this URL will get the specified permission on the object.
|
||||
/// @param bucketName object's bucket name
|
||||
/// @param objectKey Object name
|
||||
/// @param method http method.currently only support get and head.
|
||||
/// @param interval Expiration time in seconds. The URL could be specified with the expiration time to limit the access window on the object.
|
||||
/// @param parameters it could specify allowed HTTP methods
|
||||
/// @param headers Content Type, Content-MD5, and all HTTP headers prefixed with 'x-oss-*'
|
||||
- (OSSTask *)presignConstrainURLWithBucketName:(NSString *)bucketName
|
||||
withObjectKey:(NSString *)objectKey
|
||||
httpMethod:(NSString *)method
|
||||
withExpirationInterval:(NSTimeInterval)interval
|
||||
withParameters:(NSDictionary *)parameters
|
||||
withHeaders:(nullable NSDictionary *)headers;
|
||||
|
||||
/**
|
||||
If the object's ACL is public read or public read-write, use this API to generate a signed url for sharing.
|
||||
@bucketName Object's bucket name
|
||||
@objectKey Object name
|
||||
*/
|
||||
- (OSSTask *)presignPublicURLWithBucketName:(NSString *)bucketName
|
||||
withObjectKey:(NSString *)objectKey;
|
||||
|
||||
/** TODOTODO
|
||||
If the object's ACL is public read or public read-write, use this API to generate a signed url for sharing.
|
||||
@bucketName Object's bucket name
|
||||
@objectKey Object name
|
||||
@parameter the request parameters.
|
||||
*/
|
||||
- (OSSTask *)presignPublicURLWithBucketName:(NSString *)bucketName
|
||||
withObjectKey:(NSString *)objectKey
|
||||
withParameters:(NSDictionary *)parameters;
|
||||
|
||||
@end
|
||||
|
||||
|
||||
@interface OSSClient (ImageService)
|
||||
|
||||
/*
|
||||
* image persist action
|
||||
* https://help.aliyun.com/document_detail/55811.html
|
||||
*/
|
||||
- (OSSTask *)imageActionPersist:(OSSImagePersistRequest *)request;
|
||||
|
||||
@end
|
||||
|
||||
|
||||
@interface OSSClient (Utilities)
|
||||
|
||||
/**
|
||||
Checks if the object exists
|
||||
@bucketName Object's bucket name
|
||||
@objectKey Object name
|
||||
|
||||
return YES Object exists
|
||||
return NO && *error = nil Object does not exist
|
||||
return NO && *error != nil Error occured.
|
||||
*/
|
||||
- (BOOL)doesObjectExistInBucket:(NSString *)bucketName
|
||||
objectKey:(NSString *)objectKey
|
||||
error:(const NSError **)error;
|
||||
|
||||
@end
|
||||
|
||||
|
||||
@interface OSSClient (Callback)
|
||||
|
||||
- (OSSTask *)triggerCallBack:(OSSCallBackRequest *)request;
|
||||
|
||||
@end
|
||||
|
||||
NS_ASSUME_NONNULL_END
|
||||
2269
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSClient.m
generated
Normal file
2269
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSClient.m
generated
Normal file
File diff suppressed because it is too large
Load Diff
85
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSCompat.h
generated
Normal file
85
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSCompat.h
generated
Normal file
@@ -0,0 +1,85 @@
|
||||
//
|
||||
// OSSCompat.h
|
||||
// oss_ios_sdk_new
|
||||
//
|
||||
// Created by zhouzhuo on 9/10/15.
|
||||
// Copyright (c) 2015 aliyun.com. All rights reserved.
|
||||
//
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
#import "OSSService.h"
|
||||
|
||||
@class OSSCancellationTokenSource;
|
||||
|
||||
typedef OSSCancellationTokenSource OSSTaskHandler;
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
@interface OSSClient (Compat)
|
||||
|
||||
/**
|
||||
The old version's upload API.
|
||||
Please use putObject instead.
|
||||
*/
|
||||
- (OSSTaskHandler *)uploadData:(NSData *)data
|
||||
withContentType:(NSString *)contentType
|
||||
withObjectMeta:(NSDictionary *)meta
|
||||
toBucketName:(NSString *)bucketName
|
||||
toObjectKey:(NSString *)objectKey
|
||||
onCompleted:(void(^)(BOOL, NSError *))onCompleted
|
||||
onProgress:(void(^)(float progress))onProgress;
|
||||
|
||||
/**
|
||||
The old version's download API.
|
||||
Please use getObject instead.
|
||||
*/
|
||||
- (OSSTaskHandler *)downloadToDataFromBucket:(NSString *)bucketName
|
||||
objectKey:(NSString *)objectKey
|
||||
onCompleted:(void(^)(NSData *, NSError *))onCompleted
|
||||
onProgress:(void(^)(float progress))onProgress;
|
||||
|
||||
/**
|
||||
The old version's upload API.
|
||||
Please use putObject instead.
|
||||
*/
|
||||
- (OSSTaskHandler *)uploadFile:(NSString *)filePath
|
||||
withContentType:(NSString *)contentType
|
||||
withObjectMeta:(NSDictionary *)meta
|
||||
toBucketName:(NSString *)bucketName
|
||||
toObjectKey:(NSString *)objectKey
|
||||
onCompleted:(void(^)(BOOL, NSError *))onCompleted
|
||||
onProgress:(void(^)(float progress))onProgress;
|
||||
|
||||
/**
|
||||
The old version's download API.
|
||||
Please use getObject instead.
|
||||
*/
|
||||
- (OSSTaskHandler *)downloadToFileFromBucket:(NSString *)bucketName
|
||||
objectKey:(NSString *)objectKey
|
||||
toFile:(NSString *)filePath
|
||||
onCompleted:(void(^)(BOOL, NSError *))onCompleted
|
||||
onProgress:(void(^)(float progress))onProgress;
|
||||
|
||||
|
||||
/**
|
||||
The old version's upload API with resumable upload support.
|
||||
Please use resumableUpload instead.
|
||||
*/
|
||||
- (OSSTaskHandler *)resumableUploadFile:(NSString *)filePath
|
||||
withContentType:(NSString *)contentType
|
||||
withObjectMeta:(NSDictionary *)meta
|
||||
toBucketName:(NSString *)bucketName
|
||||
toObjectKey:(NSString *)objectKey
|
||||
onCompleted:(void(^)(BOOL, NSError *))onCompleted
|
||||
onProgress:(void(^)(float progress))onProgress;
|
||||
|
||||
/**
|
||||
The old version's delete API.
|
||||
Please use deleteObject instead.
|
||||
*/
|
||||
- (void)deleteObjectInBucket:(NSString *)bucketName
|
||||
objectKey:(NSString *)objectKey
|
||||
onCompleted:(void(^)(BOOL, NSError *))onCompleted;
|
||||
@end
|
||||
|
||||
NS_ASSUME_NONNULL_END
|
||||
260
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSCompat.m
generated
Normal file
260
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSCompat.m
generated
Normal file
@@ -0,0 +1,260 @@
|
||||
//
|
||||
// OSSCompat.m
|
||||
// oss_ios_sdk_new
|
||||
//
|
||||
// Created by zhouzhuo on 9/10/15.
|
||||
// Copyright (c) 2015 aliyun.com. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSDefine.h"
|
||||
#import "OSSCompat.h"
|
||||
#import "OSSBolts.h"
|
||||
#import "OSSModel.h"
|
||||
|
||||
@implementation OSSClient (Compat)
|
||||
|
||||
- (OSSTaskHandler *)uploadData:(NSData *)data
|
||||
withContentType:(NSString *)contentType
|
||||
withObjectMeta:(NSDictionary *)meta
|
||||
toBucketName:(NSString *)bucketName
|
||||
toObjectKey:(NSString *)objectKey
|
||||
onCompleted:(void(^)(BOOL, NSError *))onCompleted
|
||||
onProgress:(void(^)(float progress))onProgress {
|
||||
|
||||
OSSTaskHandler * bcts = [OSSCancellationTokenSource cancellationTokenSource];
|
||||
|
||||
[[[OSSTask taskWithResult:nil] continueWithExecutor:self.ossOperationExecutor withSuccessBlock:^id(OSSTask *task) {
|
||||
OSSPutObjectRequest * put = [OSSPutObjectRequest new];
|
||||
put.bucketName = bucketName;
|
||||
put.objectKey = objectKey;
|
||||
put.objectMeta = meta;
|
||||
put.uploadingData = data;
|
||||
put.contentType = contentType;
|
||||
|
||||
put.uploadProgress = ^(int64_t bytesSent, int64_t totalBytesSent, int64_t totalBytesExpectedToSend) {
|
||||
if (totalBytesExpectedToSend) {
|
||||
onProgress((float)totalBytesSent / totalBytesExpectedToSend);
|
||||
}
|
||||
};
|
||||
|
||||
[bcts.token registerCancellationObserverWithBlock:^{
|
||||
[put cancel];
|
||||
}];
|
||||
|
||||
OSSTask * putTask = [self putObject:put];
|
||||
[putTask waitUntilFinished];
|
||||
onProgress(1.0f);
|
||||
return putTask;
|
||||
}] continueWithBlock:^id(OSSTask *task) {
|
||||
if (task.error) {
|
||||
onCompleted(NO, task.error);
|
||||
} else {
|
||||
onCompleted(YES, nil);
|
||||
}
|
||||
return nil;
|
||||
}];
|
||||
return bcts;
|
||||
}
|
||||
|
||||
- (OSSTaskHandler *)downloadToDataFromBucket:(NSString *)bucketName
|
||||
objectKey:(NSString *)objectKey
|
||||
onCompleted:(void (^)(NSData *, NSError *))onCompleted
|
||||
onProgress:(void (^)(float))onProgress {
|
||||
|
||||
OSSTaskHandler * bcts = [OSSCancellationTokenSource cancellationTokenSource];
|
||||
|
||||
[[[OSSTask taskWithResult:nil] continueWithExecutor:self.ossOperationExecutor withBlock:^id(OSSTask *task) {
|
||||
OSSGetObjectRequest * get = [OSSGetObjectRequest new];
|
||||
get.bucketName = bucketName;
|
||||
get.objectKey = objectKey;
|
||||
|
||||
get.downloadProgress = ^(int64_t bytesWritten, int64_t totalBytesWritten, int64_t totalBytesExpectedToWrite) {
|
||||
if (totalBytesExpectedToWrite) {
|
||||
onProgress((float)totalBytesWritten / totalBytesExpectedToWrite);
|
||||
}
|
||||
};
|
||||
|
||||
[bcts.token registerCancellationObserverWithBlock:^{
|
||||
[get cancel];
|
||||
}];
|
||||
|
||||
OSSTask * getTask = [self getObject:get];
|
||||
[getTask waitUntilFinished];
|
||||
onProgress(1.0f);
|
||||
return getTask;
|
||||
}] continueWithBlock:^id(OSSTask *task) {
|
||||
if (task.error) {
|
||||
onCompleted(nil, task.error);
|
||||
} else {
|
||||
OSSGetObjectResult * result = task.result;
|
||||
onCompleted(result.downloadedData, nil);
|
||||
}
|
||||
return nil;
|
||||
}];
|
||||
|
||||
return bcts;
|
||||
}
|
||||
|
||||
- (OSSTaskHandler *)downloadToFileFromBucket:(NSString *)bucketName
|
||||
objectKey:(NSString *)objectKey
|
||||
toFile:(NSString *)filePath
|
||||
onCompleted:(void (^)(BOOL, NSError *))onCompleted
|
||||
onProgress:(void (^)(float))onProgress {
|
||||
|
||||
OSSTaskHandler * bcts = [OSSCancellationTokenSource cancellationTokenSource];
|
||||
|
||||
[[[OSSTask taskWithResult:nil] continueWithExecutor:self.ossOperationExecutor withBlock:^id(OSSTask *task) {
|
||||
OSSGetObjectRequest * get = [OSSGetObjectRequest new];
|
||||
get.bucketName = bucketName;
|
||||
get.objectKey = objectKey;
|
||||
get.downloadToFileURL = [NSURL fileURLWithPath:filePath];
|
||||
|
||||
get.downloadProgress = ^(int64_t bytesWritten, int64_t totalBytesWritten, int64_t totalBytesExpectedToWrite) {
|
||||
if (totalBytesExpectedToWrite) {
|
||||
onProgress((float)totalBytesWritten / totalBytesExpectedToWrite);
|
||||
}
|
||||
};
|
||||
|
||||
[bcts.token registerCancellationObserverWithBlock:^{
|
||||
[get cancel];
|
||||
}];
|
||||
|
||||
OSSTask * getTask = [self getObject:get];
|
||||
[getTask waitUntilFinished];
|
||||
onProgress(1.0f);
|
||||
return getTask;
|
||||
}] continueWithBlock:^id(OSSTask *task) {
|
||||
if (task.error) {
|
||||
onCompleted(NO, task.error);
|
||||
} else {
|
||||
onCompleted(YES, nil);
|
||||
}
|
||||
return nil;
|
||||
}];
|
||||
|
||||
return bcts;
|
||||
}
|
||||
|
||||
- (void)deleteObjectInBucket:(NSString *)bucketName
|
||||
objectKey:(NSString *)objectKey
|
||||
onCompleted:(void (^)(BOOL, NSError *))onCompleted {
|
||||
|
||||
[[[OSSTask taskWithResult:nil] continueWithExecutor:self.ossOperationExecutor withBlock:^id(OSSTask *task) {
|
||||
OSSDeleteObjectRequest * delete = [OSSDeleteObjectRequest new];
|
||||
delete.bucketName = bucketName;
|
||||
delete.objectKey = objectKey;
|
||||
|
||||
OSSTask * deleteTask = [self deleteObject:delete];
|
||||
[deleteTask waitUntilFinished];
|
||||
return deleteTask;
|
||||
}] continueWithBlock:^id(OSSTask *task) {
|
||||
if (task.error) {
|
||||
onCompleted(NO, task.error);
|
||||
} else {
|
||||
onCompleted(YES, nil);
|
||||
}
|
||||
return nil;
|
||||
}];
|
||||
}
|
||||
|
||||
- (OSSTaskHandler *)uploadFile:(NSString *)filePath
|
||||
withContentType:(NSString *)contentType
|
||||
withObjectMeta:(NSDictionary *)meta
|
||||
toBucketName:(NSString *)bucketName
|
||||
toObjectKey:(NSString *)objectKey
|
||||
onCompleted:(void (^)(BOOL, NSError *))onCompleted
|
||||
onProgress:(void (^)(float))onProgress {
|
||||
|
||||
OSSTaskHandler * bcts = [OSSCancellationTokenSource cancellationTokenSource];
|
||||
|
||||
[[[OSSTask taskWithResult:nil] continueWithExecutor:self.ossOperationExecutor withSuccessBlock:^id(OSSTask *task) {
|
||||
OSSPutObjectRequest * put = [OSSPutObjectRequest new];
|
||||
put.bucketName = bucketName;
|
||||
put.objectKey = objectKey;
|
||||
put.objectMeta = meta;
|
||||
put.uploadingFileURL = [NSURL fileURLWithPath:filePath];
|
||||
put.contentType = contentType;
|
||||
|
||||
put.uploadProgress = ^(int64_t bytesSent, int64_t totalBytesSent, int64_t totalBytesExpectedToSend) {
|
||||
if (totalBytesExpectedToSend) {
|
||||
onProgress((float)totalBytesSent / totalBytesExpectedToSend);
|
||||
}
|
||||
};
|
||||
|
||||
[bcts.token registerCancellationObserverWithBlock:^{
|
||||
[put cancel];
|
||||
}];
|
||||
|
||||
OSSTask * putTask = [self putObject:put];
|
||||
[putTask waitUntilFinished];
|
||||
onProgress(1.0f);
|
||||
return putTask;
|
||||
}] continueWithBlock:^id(OSSTask *task) {
|
||||
if (task.error) {
|
||||
onCompleted(NO, task.error);
|
||||
} else {
|
||||
onCompleted(YES, nil);
|
||||
}
|
||||
return nil;
|
||||
}];
|
||||
return bcts;
|
||||
}
|
||||
|
||||
- (OSSTaskHandler *)resumableUploadFile:(NSString *)filePath
|
||||
withContentType:(NSString *)contentType
|
||||
withObjectMeta:(NSDictionary *)meta
|
||||
toBucketName:(NSString *)bucketName
|
||||
toObjectKey:(NSString *)objectKey
|
||||
onCompleted:(void(^)(BOOL, NSError *))onComplete
|
||||
onProgress:(void(^)(float progress))onProgress {
|
||||
|
||||
OSSTaskHandler * bcts = [OSSCancellationTokenSource cancellationTokenSource];
|
||||
|
||||
[[[OSSTask taskWithResult:nil] continueWithBlock:^id(OSSTask *task) {
|
||||
NSURL * fileURL = [NSURL fileURLWithPath:filePath];
|
||||
NSDate * lastModified;
|
||||
NSError * error;
|
||||
[fileURL getResourceValue:&lastModified forKey:NSURLContentModificationDateKey error:&error];
|
||||
if (error) {
|
||||
return [OSSTask taskWithError:error];
|
||||
}
|
||||
OSSResumableUploadRequest * resumableUpload = [OSSResumableUploadRequest new];
|
||||
resumableUpload.bucketName = bucketName;
|
||||
resumableUpload.deleteUploadIdOnCancelling = NO;//cancel not delete record file
|
||||
resumableUpload.contentType = contentType;
|
||||
resumableUpload.completeMetaHeader = meta;
|
||||
NSString *cachesDir = [NSSearchPathForDirectoriesInDomains(NSCachesDirectory, NSUserDomainMask, YES) firstObject];
|
||||
resumableUpload.recordDirectoryPath = cachesDir; //default record file path
|
||||
resumableUpload.uploadingFileURL = fileURL;
|
||||
resumableUpload.objectKey = objectKey;
|
||||
resumableUpload.uploadId = task.result;
|
||||
resumableUpload.uploadingFileURL = [NSURL fileURLWithPath:filePath];
|
||||
__weak OSSResumableUploadRequest * weakRef = resumableUpload;
|
||||
resumableUpload.uploadProgress = ^(int64_t bytesSent, int64_t totalBytesSent, int64_t totalBytesExpectedToSend) {
|
||||
onProgress((float)totalBytesSent/totalBytesExpectedToSend);
|
||||
if (bcts.token.isCancellationRequested || bcts.isCancellationRequested) {
|
||||
[weakRef cancel];
|
||||
}
|
||||
OSSLogDebugNoFile(@"%lld %lld %lld", bytesSent, totalBytesSent, totalBytesExpectedToSend);
|
||||
};
|
||||
return [self resumableUpload:resumableUpload];
|
||||
}] continueWithBlock:^id(OSSTask *task) {
|
||||
if (task.cancelled) {
|
||||
onComplete(NO, [NSError errorWithDomain:OSSClientErrorDomain
|
||||
code:OSSClientErrorCodeTaskCancelled
|
||||
userInfo:@{OSSErrorMessageTOKEN: @"This task is cancelled"}]);
|
||||
} else if (task.error) {
|
||||
onComplete(NO, task.error);
|
||||
} else if (task.faulted) {
|
||||
onComplete(NO, [NSError errorWithDomain:OSSClientErrorDomain
|
||||
code:OSSClientErrorCodeExcpetionCatched
|
||||
userInfo:@{OSSErrorMessageTOKEN: [NSString stringWithFormat:@"Catch exception - %@", task.exception]}]);
|
||||
} else {
|
||||
onComplete(YES, nil);
|
||||
}
|
||||
return nil;
|
||||
}];
|
||||
return bcts;
|
||||
}
|
||||
|
||||
@end
|
||||
144
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSConstants.h
generated
Normal file
144
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSConstants.h
generated
Normal file
@@ -0,0 +1,144 @@
|
||||
//
|
||||
// OSSConstants.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/1/22.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
typedef NSString* _Nullable (^OSSCustomSignContentBlock) (NSString * contentToSign, NSError **error);
|
||||
typedef NSData * _Nullable (^OSSResponseDecoderBlock) (NSData * data);
|
||||
|
||||
typedef void (^OSSNetworkingUploadProgressBlock) (int64_t bytesSent, int64_t totalBytesSent, int64_t totalBytesExpectedToSend);
|
||||
typedef void (^OSSNetworkingDownloadProgressBlock) (int64_t bytesWritten, int64_t totalBytesWritten, int64_t totalBytesExpectedToWrite);
|
||||
typedef void (^OSSNetworkingRetryBlock) (void);
|
||||
typedef void (^OSSNetworkingCompletionHandlerBlock) (id _Nullable responseObject, NSError * _Nullable error);
|
||||
typedef void (^OSSNetworkingOnRecieveDataBlock) (NSData * data);
|
||||
|
||||
/**
|
||||
The flag of verification about crc64
|
||||
*/
|
||||
typedef NS_ENUM(NSUInteger, OSSRequestCRCFlag) {
|
||||
OSSRequestCRCUninitialized,
|
||||
OSSRequestCRCOpen,
|
||||
OSSRequestCRCClosed
|
||||
};
|
||||
|
||||
/**
|
||||
Retry type definition
|
||||
*/
|
||||
typedef NS_ENUM(NSInteger, OSSNetworkingRetryType) {
|
||||
OSSNetworkingRetryTypeUnknown,
|
||||
OSSNetworkingRetryTypeShouldRetry,
|
||||
OSSNetworkingRetryTypeShouldNotRetry,
|
||||
OSSNetworkingRetryTypeShouldRefreshCredentialsAndRetry,
|
||||
OSSNetworkingRetryTypeShouldCorrectClockSkewAndRetry
|
||||
};
|
||||
|
||||
/**
|
||||
* @brief: The following constants are provided by OSSNetworking as possible operation types.
|
||||
*/
|
||||
typedef NS_ENUM(NSInteger, OSSOperationType) {
|
||||
OSSOperationTypeGetService,
|
||||
OSSOperationTypeCreateBucket,
|
||||
OSSOperationTypeDeleteBucket,
|
||||
OSSOperationTypeGetBucket,
|
||||
OSSOperationTypeGetBucketInfo,
|
||||
OSSOperationTypeGetBucketACL,
|
||||
OSSOperationTypeHeadObject,
|
||||
OSSOperationTypeGetObject,
|
||||
OSSOperationTypeGetObjectACL,
|
||||
OSSOperationTypePutObject,
|
||||
OSSOperationTypePutObjectACL,
|
||||
OSSOperationTypeAppendObject,
|
||||
OSSOperationTypeDeleteObject,
|
||||
OSSOperationTypeDeleteMultipleObjects,
|
||||
OSSOperationTypeCopyObject,
|
||||
OSSOperationTypeInitMultipartUpload,
|
||||
OSSOperationTypeUploadPart,
|
||||
OSSOperationTypeCompleteMultipartUpload,
|
||||
OSSOperationTypeAbortMultipartUpload,
|
||||
OSSOperationTypeListMultipart,
|
||||
OSSOperationTypeListMultipartUploads,
|
||||
OSSOperationTypeTriggerCallBack,
|
||||
OSSOperationTypeImagePersist,
|
||||
OSSOperationTypeRestoreObject,
|
||||
OSSOperationTypePutSymlink,
|
||||
OSSOperationTypeGetSymlink,
|
||||
OSSOperationTypeGetObjectTagging,
|
||||
OSSOperationTypePutObjectTagging,
|
||||
OSSOperationTypeDeleteObjectTagging,
|
||||
};
|
||||
|
||||
/**
|
||||
* @brief: The following constants are provided by OSSClient as possible error codes.
|
||||
*/
|
||||
typedef NS_ENUM(NSInteger, OSSClientErrorCODE) {
|
||||
OSSClientErrorCodeNetworkingFailWithResponseCode0,
|
||||
OSSClientErrorCodeSignFailed,
|
||||
OSSClientErrorCodeFileCantWrite,
|
||||
OSSClientErrorCodeInvalidArgument,
|
||||
OSSClientErrorCodeNilUploadid,
|
||||
OSSClientErrorCodeTaskCancelled,
|
||||
OSSClientErrorCodeNetworkError,
|
||||
OSSClientErrorCodeInvalidCRC,
|
||||
OSSClientErrorCodeCannotResumeUpload,
|
||||
OSSClientErrorCodeExcpetionCatched,
|
||||
OSSClientErrorCodeNotKnown,
|
||||
OSSClientErrorCodeFileCantRead
|
||||
};
|
||||
|
||||
typedef NS_ENUM(NSInteger, OSSXMLDictionaryAttributesMode)
|
||||
{
|
||||
OSSXMLDictionaryAttributesModePrefixed = 0, //default
|
||||
OSSXMLDictionaryAttributesModeDictionary,
|
||||
OSSXMLDictionaryAttributesModeUnprefixed,
|
||||
OSSXMLDictionaryAttributesModeDiscard
|
||||
};
|
||||
|
||||
|
||||
typedef NS_ENUM(NSInteger, OSSXMLDictionaryNodeNameMode)
|
||||
{
|
||||
OSSXMLDictionaryNodeNameModeRootOnly = 0, //default
|
||||
OSSXMLDictionaryNodeNameModeAlways,
|
||||
OSSXMLDictionaryNodeNameModeNever
|
||||
};
|
||||
|
||||
typedef NS_ENUM(NSInteger, OSSBucketStorageClass)
|
||||
{
|
||||
OSSBucketStorageClassStandard,
|
||||
OSSBucketStorageClassIA,
|
||||
OSSBucketStorageClassArchive
|
||||
};
|
||||
|
||||
typedef NS_ENUM(NSInteger, OSSTerminationMode) {
|
||||
OSSTerminationModeAll = 0,
|
||||
OSSTerminationModeHasError
|
||||
};
|
||||
|
||||
typedef NSString * OSSXMLDictionaryAttributeName NS_EXTENSIBLE_STRING_ENUM;
|
||||
|
||||
OBJC_EXTERN OSSXMLDictionaryAttributeName const OSSXMLDictionaryAttributesKey;
|
||||
OBJC_EXTERN OSSXMLDictionaryAttributeName const OSSXMLDictionaryCommentsKey;
|
||||
OBJC_EXTERN OSSXMLDictionaryAttributeName const OSSXMLDictionaryTextKey;
|
||||
OBJC_EXTERN OSSXMLDictionaryAttributeName const OSSXMLDictionaryNodeNameKey;
|
||||
OBJC_EXTERN OSSXMLDictionaryAttributeName const OSSXMLDictionaryAttributePrefix;
|
||||
|
||||
OBJC_EXTERN NSString * const OSSHTTPMethodHEAD;
|
||||
OBJC_EXTERN NSString * const OSSHTTPMethodGET;
|
||||
OBJC_EXTERN NSString * const OSSHTTPMethodPUT;
|
||||
OBJC_EXTERN NSString * const OSSHTTPMethodPOST;
|
||||
OBJC_EXTERN NSString * const OSSHTTPMethodDELETE;
|
||||
|
||||
|
||||
typedef NS_ENUM(NSInteger, OSSSignVersion)
|
||||
{
|
||||
OSSSignVersionV1,
|
||||
OSSSignVersionV4
|
||||
};
|
||||
|
||||
NS_ASSUME_NONNULL_END
|
||||
21
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSConstants.m
generated
Normal file
21
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSConstants.m
generated
Normal file
@@ -0,0 +1,21 @@
|
||||
//
|
||||
// OSSConstants.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/1/22.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSConstants.h"
|
||||
|
||||
NSString * const OSSXMLDictionaryAttributesKey = @"__attributes";
|
||||
NSString * const OSSXMLDictionaryCommentsKey = @"__comments";
|
||||
NSString * const OSSXMLDictionaryTextKey = @"__text";
|
||||
NSString * const OSSXMLDictionaryNodeNameKey = @"__name";
|
||||
NSString * const OSSXMLDictionaryAttributePrefix = @"_";
|
||||
|
||||
NSString * const OSSHTTPMethodHEAD = @"HEAD";
|
||||
NSString * const OSSHTTPMethodGET = @"GET";
|
||||
NSString * const OSSHTTPMethodPUT = @"PUT";
|
||||
NSString * const OSSHTTPMethodPOST = @"POST";
|
||||
NSString * const OSSHTTPMethodDELETE = @"DELETE";
|
||||
108
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSDefine.h
generated
Normal file
108
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSDefine.h
generated
Normal file
@@ -0,0 +1,108 @@
|
||||
//
|
||||
// OSSDefine.h
|
||||
// AliyunOSSiOS
|
||||
//
|
||||
// Created by zhouzhuo on 5/1/16.
|
||||
// Copyright © 2016 zhouzhuo. All rights reserved.
|
||||
//
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
|
||||
#ifndef OSSDefine_h
|
||||
#define OSSDefine_h
|
||||
|
||||
#if TARGET_OS_IOS
|
||||
#define OSSUAPrefix @"aliyun-sdk-ios"
|
||||
#elif TARGET_OS_OSX
|
||||
#define OSSUAPrefix @"aliyun-sdk-mac"
|
||||
#endif
|
||||
#define OSSSDKVersion @"2.11.0"
|
||||
|
||||
#define OSSListBucketResultXMLTOKEN @"ListBucketResult"
|
||||
#define OSSNameXMLTOKEN @"Name"
|
||||
#define OSSDelimiterXMLTOKEN @"Delimiter"
|
||||
#define OSSMarkerXMLTOKEN @"Marker"
|
||||
#define OSSKeyMarkerXMLTOKEN @"KeyMarker"
|
||||
#define OSSNextMarkerXMLTOKEN @"NextMarker"
|
||||
#define OSSNextKeyMarkerXMLTOKEN @"NextKeyMarker"
|
||||
#define OSSUploadIdMarkerXMLTOKEN @"UploadIdMarker"
|
||||
#define OSSNextUploadIdMarkerXMLTOKEN @"NextUploadIdMarker"
|
||||
#define OSSMaxKeysXMLTOKEN @"MaxKeys"
|
||||
#define OSSMaxUploadsXMLTOKEN @"MaxUploads"
|
||||
#define OSSIsTruncatedXMLTOKEN @"IsTruncated"
|
||||
#define OSSContentsXMLTOKEN @"Contents"
|
||||
#define OSSUploadXMLTOKEN @"Upload"
|
||||
#define OSSKeyXMLTOKEN @"Key"
|
||||
#define OSSLastModifiedXMLTOKEN @"LastModified"
|
||||
#define OSSETagXMLTOKEN @"ETag"
|
||||
#define OSSTypeXMLTOKEN @"Type"
|
||||
#define OSSSizeXMLTOKEN @"Size"
|
||||
#define OSSStorageClassXMLTOKEN @"StorageClass"
|
||||
#define OSSCommonPrefixesXMLTOKEN @"CommonPrefixes"
|
||||
#define OSSOwnerXMLTOKEN @"Owner"
|
||||
#define OSSAccessControlListXMLTOKEN @"AccessControlList"
|
||||
#define OSSGrantXMLTOKEN @"Grant"
|
||||
#define OSSIDXMLTOKEN @"ID"
|
||||
#define OSSDisplayNameXMLTOKEN @"DisplayName"
|
||||
#define OSSBucketsXMLTOKEN @"Buckets"
|
||||
#define OSSBucketXMLTOKEN @"Bucket"
|
||||
#define OSSCreationDate @"CreationDate"
|
||||
#define OSSPrefixXMLTOKEN @"Prefix"
|
||||
#define OSSUploadIdXMLTOKEN @"UploadId"
|
||||
#define OSSLocationXMLTOKEN @"Location"
|
||||
#define OSSNextPartNumberMarkerXMLTOKEN @"NextPartNumberMarker"
|
||||
#define OSSMaxPartsXMLTOKEN @"MaxParts"
|
||||
#define OSSPartXMLTOKEN @"Part"
|
||||
#define OSSPartNumberXMLTOKEN @"PartNumber"
|
||||
|
||||
#define OSSClientErrorDomain @"com.aliyun.oss.clientError"
|
||||
#define OSSServerErrorDomain @"com.aliyun.oss.serverError"
|
||||
|
||||
#define OSSErrorMessageTOKEN @"ErrorMessage"
|
||||
#define OSSNetworkTaskMetrics @"NetworkTaskMetrics"
|
||||
|
||||
#define OSSHttpHeaderContentDisposition @"Content-Disposition"
|
||||
#define OSSHttpHeaderXOSSCallback @"x-oss-callback"
|
||||
#define OSSHttpHeaderXOSSCallbackVar @"x-oss-callback-var"
|
||||
#define OSSHttpHeaderContentEncoding @"Content-Encoding"
|
||||
#define OSSHttpHeaderContentType @"Content-Type"
|
||||
#define OSSHttpHeaderContentMD5 @"Content-MD5"
|
||||
#define OSSHttpHeaderCacheControl @"Cache-Control"
|
||||
#define OSSHttpHeaderExpires @"Expires"
|
||||
#define OSSHttpHeaderHashSHA1 @"x-oss-hash-sha1"
|
||||
#define OSSHttpHeaderBucketACL @"x-oss-acl"
|
||||
#define OSSHttpHeaderObjectACL @"x-oss-object-acl"
|
||||
#define OSSHttpHeaderCopySource @"x-oss-copy-source"
|
||||
#define OSSHttpHeaderSymlinkTarget @"x-oss-symlink-target"
|
||||
#define OSSHttpHeaderDate @"Date"
|
||||
#define OSSHttpHeaderDateEx @"x-oss-date"
|
||||
#define OSSHttpHeaderSecurityToken @"x-oss-security-token"
|
||||
#define OSSHttpHeaderAuthorization @"Authorization"
|
||||
#define OSSHttpHeaderHost @"Host"
|
||||
#define OSSHttpHeaderContentSha256 @"x-oss-content-sha256"
|
||||
|
||||
#define OSSRequestParameterExpires @"Expires"
|
||||
#define OSSRequestParameterAccessKeyId @"OSSAccessKeyId"
|
||||
#define OSSRequestParameterSignature @"Signature"
|
||||
|
||||
#define OSSHttpQueryProcess @"x-oss-process"
|
||||
#define OSSPrefix @"x-oss-"
|
||||
|
||||
#define OSSDefaultRetryCount 3
|
||||
#define OSSDefaultMaxConcurrentNum 5
|
||||
#define OSSDefaultTimeoutForRequestInSecond 15
|
||||
#define OSSDefaultTimeoutForResourceInSecond 7 * 24 * 60 * 60
|
||||
#define OSSDefaultThreadNum 5
|
||||
|
||||
#define OSSAuthorizationPrefix @"OSS "
|
||||
|
||||
#define OSSProductDefault @"oss"
|
||||
#define OSSProductCloudBox @"oss-cloudbox"
|
||||
|
||||
#define OSSContentStringToSign @"stringToSign"
|
||||
#define OSSContentDate @"date"
|
||||
#define OSSContentAlgorithm @"algorithm"
|
||||
#define OSSContentRegion @"region"
|
||||
#define OSSContentProduct @"product"
|
||||
|
||||
#endif /* OSSDefine_h */
|
||||
31
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSDeleteMultipleObjectsRequest.h
generated
Normal file
31
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSDeleteMultipleObjectsRequest.h
generated
Normal file
@@ -0,0 +1,31 @@
|
||||
//
|
||||
// OSSDeleteMultipleObjectsRequest.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/1/26.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
#import <Foundation/Foundation.h>
|
||||
#import "OSSRequest.h"
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
@interface OSSDeleteMultipleObjectsRequest : OSSRequest
|
||||
|
||||
@property (nonatomic, copy) NSString *bucketName;
|
||||
|
||||
@property (nonatomic, copy) NSArray<NSString *> *keys;
|
||||
|
||||
/**
|
||||
invalid value is @"url"
|
||||
*/
|
||||
@property (nonatomic, copy, nullable) NSString *encodingType;
|
||||
|
||||
/**
|
||||
whether to show verbose result,the default value is YES.
|
||||
*/
|
||||
@property (nonatomic, assign) BOOL quiet;
|
||||
|
||||
@end
|
||||
|
||||
NS_ASSUME_NONNULL_END
|
||||
22
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSDeleteMultipleObjectsRequest.m
generated
Normal file
22
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSDeleteMultipleObjectsRequest.m
generated
Normal file
@@ -0,0 +1,22 @@
|
||||
//
|
||||
// OSSDeleteMultipleObjectsRequest.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/1/26.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSDeleteMultipleObjectsRequest.h"
|
||||
|
||||
@implementation OSSDeleteMultipleObjectsRequest
|
||||
|
||||
- (instancetype)init
|
||||
{
|
||||
self = [super init];
|
||||
if (self) {
|
||||
_quiet = YES;
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
@end
|
||||
17
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSDeleteMultipleObjectsResult.h
generated
Normal file
17
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSDeleteMultipleObjectsResult.h
generated
Normal file
@@ -0,0 +1,17 @@
|
||||
//
|
||||
// OSSDeleteMultipleObjectsResult.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/1/26.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSResult.h"
|
||||
|
||||
@interface OSSDeleteMultipleObjectsResult : OSSResult
|
||||
|
||||
@property (nonatomic, copy) NSArray<NSString *> *deletedObjects;
|
||||
|
||||
@property (nonatomic, copy) NSString *encodingType;
|
||||
|
||||
@end
|
||||
13
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSDeleteMultipleObjectsResult.m
generated
Normal file
13
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSDeleteMultipleObjectsResult.m
generated
Normal file
@@ -0,0 +1,13 @@
|
||||
//
|
||||
// OSSDeleteMultipleObjectsResult.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/1/26.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSDeleteMultipleObjectsResult.h"
|
||||
|
||||
@implementation OSSDeleteMultipleObjectsResult
|
||||
|
||||
@end
|
||||
23
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSDeleteObjectTaggingRequest.h
generated
Normal file
23
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSDeleteObjectTaggingRequest.h
generated
Normal file
@@ -0,0 +1,23 @@
|
||||
//
|
||||
// OSSDeleteObjectTaggingRequest.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by ws on 2021/5/25.
|
||||
// Copyright © 2021 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSRequest.h"
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
@interface OSSDeleteObjectTaggingRequest : OSSRequest
|
||||
|
||||
/* bucket name */
|
||||
@property (nonatomic, copy) NSString *bucketName;
|
||||
|
||||
/* object name */
|
||||
@property (nonatomic, copy) NSString *objectKey;
|
||||
|
||||
@end
|
||||
|
||||
NS_ASSUME_NONNULL_END
|
||||
17
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSDeleteObjectTaggingRequest.m
generated
Normal file
17
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSDeleteObjectTaggingRequest.m
generated
Normal file
@@ -0,0 +1,17 @@
|
||||
//
|
||||
// OSSDeleteObjectTaggingRequest.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by ws on 2021/5/25.
|
||||
// Copyright © 2021 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSDeleteObjectTaggingRequest.h"
|
||||
|
||||
@implementation OSSDeleteObjectTaggingRequest
|
||||
|
||||
- (NSDictionary *)requestParams {
|
||||
return @{@"tagging": @""};
|
||||
}
|
||||
|
||||
@end
|
||||
17
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSDeleteObjectTaggingResult.h
generated
Normal file
17
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSDeleteObjectTaggingResult.h
generated
Normal file
@@ -0,0 +1,17 @@
|
||||
//
|
||||
// OSSDeleteObjectTaggingResult.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by ws on 2021/5/25.
|
||||
// Copyright © 2021 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSResult.h"
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
@interface OSSDeleteObjectTaggingResult : OSSResult
|
||||
|
||||
@end
|
||||
|
||||
NS_ASSUME_NONNULL_END
|
||||
13
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSDeleteObjectTaggingResult.m
generated
Normal file
13
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSDeleteObjectTaggingResult.m
generated
Normal file
@@ -0,0 +1,13 @@
|
||||
//
|
||||
// OSSDeleteObjectTaggingResult.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by ws on 2022/8/4.
|
||||
// Copyright © 2022 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSDeleteObjectTaggingResult.h"
|
||||
|
||||
@implementation OSSDeleteObjectTaggingResult
|
||||
|
||||
@end
|
||||
75
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSFileLog/OSSCocoaLumberjack.h
generated
Normal file
75
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSFileLog/OSSCocoaLumberjack.h
generated
Normal file
@@ -0,0 +1,75 @@
|
||||
// Software License Agreement (BSD License)
|
||||
//
|
||||
// Copyright (c) 2010-2016, Deusty, LLC
|
||||
// All rights reserved.
|
||||
//
|
||||
// Redistribution and use of this software in source and binary forms,
|
||||
// with or without modification, are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistributions of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Neither the name of Deusty nor the names of its contributors may be used
|
||||
// to endorse or promote products derived from this software without specific
|
||||
// prior written permission of Deusty, LLC.
|
||||
|
||||
/**
|
||||
* Welcome to CocoaLumberjack!
|
||||
*
|
||||
* The project page has a wealth of documentation if you have any questions.
|
||||
*
|
||||
* If you're new to the project you may wish to read "Getting Started" at:
|
||||
* Documentation/GettingStarted.md
|
||||
*
|
||||
* Otherwise, here is a quick refresher.
|
||||
* There are three steps to using the macros:
|
||||
*
|
||||
* Step 1:
|
||||
* Import the header in your implementation or prefix file:
|
||||
*
|
||||
* #import <CocoaLumberjack/CocoaLumberjack.h>
|
||||
*
|
||||
* Step 2:
|
||||
* Define your logging level in your implementation file:
|
||||
*
|
||||
* // Log levels: off, error, warn, info, verbose
|
||||
* static const DDLogLevel ddLogLevel = DDLogLevelVerbose;
|
||||
*
|
||||
* Step 2 [3rd party frameworks]:
|
||||
*
|
||||
* Define your LOG_LEVEL_DEF to a different variable/function than ddLogLevel:
|
||||
*
|
||||
* // #undef LOG_LEVEL_DEF // Undefine first only if needed
|
||||
* #define LOG_LEVEL_DEF myLibLogLevel
|
||||
*
|
||||
* Define your logging level in your implementation file:
|
||||
*
|
||||
* // Log levels: off, error, warn, info, verbose
|
||||
* static const DDLogLevel myLibLogLevel = DDLogLevelVerbose;
|
||||
*
|
||||
* Step 3:
|
||||
* Replace your NSLog statements with DDLog statements according to the severity of the message.
|
||||
*
|
||||
* NSLog(@"Fatal error, no dohickey found!"); -> OSSLogError(@"Fatal error, no dohickey found!");
|
||||
*
|
||||
* DDLog works exactly the same as NSLog.
|
||||
* This means you can pass it multiple variables just like NSLog.
|
||||
**/
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
|
||||
// Disable legacy macros
|
||||
#ifndef OSSDD_LEGACY_MACROS
|
||||
#define OSSDD_LEGACY_MACROS 0
|
||||
#endif
|
||||
|
||||
// Core
|
||||
#import "OSSDDLog.h"
|
||||
|
||||
// Main macros
|
||||
#import "OSSLogMacros.h"
|
||||
|
||||
// Loggers
|
||||
#import "OSSFileLogger.h"
|
||||
#import "OSSNSLogger.h"
|
||||
|
||||
860
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSFileLog/OSSDDLog.h
generated
Normal file
860
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSFileLog/OSSDDLog.h
generated
Normal file
@@ -0,0 +1,860 @@
|
||||
// Software License Agreement (BSD License)
|
||||
//
|
||||
// Copyright (c) 2010-2016, Deusty, LLC
|
||||
// All rights reserved.
|
||||
//
|
||||
// Redistribution and use of this software in source and binary forms,
|
||||
// with or without modification, are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistributions of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Neither the name of Deusty nor the names of its contributors may be used
|
||||
// to endorse or promote products derived from this software without specific
|
||||
// prior written permission of Deusty, LLC.
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
|
||||
// Enable 1.9.x legacy macros if imported directly
|
||||
#ifndef OSSDD_LEGACY_MACROS
|
||||
#define OSSDD_LEGACY_MACROS 1
|
||||
#endif
|
||||
|
||||
#if OS_OBJECT_USE_OBJC
|
||||
#define DISPATCH_QUEUE_REFERENCE_TYPE strong
|
||||
#else
|
||||
#define DISPATCH_QUEUE_REFERENCE_TYPE assign
|
||||
#endif
|
||||
|
||||
@class OSSDDLogMessage;
|
||||
@class OSSDDLoggerInformation;
|
||||
@protocol OSSDDLogger;
|
||||
@protocol OSSDDLogFormatter;
|
||||
|
||||
/**
|
||||
* Define the standard options.
|
||||
*
|
||||
* We default to only 4 levels because it makes it easier for beginners
|
||||
* to make the transition to a logging framework.
|
||||
*
|
||||
* More advanced users may choose to completely customize the levels (and level names) to suite their needs.
|
||||
* For more information on this see the "Custom Log Levels" page:
|
||||
* Documentation/CustomLogLevels.md
|
||||
*
|
||||
* Advanced users may also notice that we're using a bitmask.
|
||||
* This is to allow for custom fine grained logging:
|
||||
* Documentation/FineGrainedLogging.md
|
||||
*
|
||||
* -- Flags --
|
||||
*
|
||||
* Typically you will use the LOG_LEVELS (see below), but the flags may be used directly in certain situations.
|
||||
* For example, say you have a lot of warning log messages, and you wanted to disable them.
|
||||
* However, you still needed to see your error and info log messages.
|
||||
* You could accomplish that with the following:
|
||||
*
|
||||
* static const DDLogLevel ddLogLevel = DDLogFlagError | DDLogFlagInfo;
|
||||
*
|
||||
* When LOG_LEVEL_DEF is defined as ddLogLevel.
|
||||
*
|
||||
* Flags may also be consulted when writing custom log formatters,
|
||||
* as the DDLogMessage class captures the individual flag that caused the log message to fire.
|
||||
*
|
||||
* -- Levels --
|
||||
*
|
||||
* Log levels are simply the proper bitmask of the flags.
|
||||
*
|
||||
* -- Booleans --
|
||||
*
|
||||
* The booleans may be used when your logging code involves more than one line.
|
||||
* For example:
|
||||
*
|
||||
* if (LOG_VERBOSE) {
|
||||
* for (id sprocket in sprockets)
|
||||
* DDLogVerbose(@"sprocket: %@", [sprocket description])
|
||||
* }
|
||||
*
|
||||
* -- Async --
|
||||
*
|
||||
* Defines the default asynchronous options.
|
||||
* The default philosophy for asynchronous logging is very simple:
|
||||
*
|
||||
* Log messages with errors should be executed synchronously.
|
||||
* After all, an error just occurred. The application could be unstable.
|
||||
*
|
||||
* All other log messages, such as debug output, are executed asynchronously.
|
||||
* After all, if it wasn't an error, then it was just informational output,
|
||||
* or something the application was easily able to recover from.
|
||||
*
|
||||
* -- Changes --
|
||||
*
|
||||
* You are strongly discouraged from modifying this file.
|
||||
* If you do, you make it more difficult on yourself to merge future bug fixes and improvements from the project.
|
||||
* Instead, create your own MyLogging.h or ApplicationNameLogging.h or CompanyLogging.h
|
||||
*
|
||||
* For an example of customizing your logging experience, see the "Custom Log Levels" page:
|
||||
* Documentation/CustomLogLevels.md
|
||||
**/
|
||||
|
||||
/**
|
||||
* Flags accompany each log. They are used together with levels to filter out logs.
|
||||
*/
|
||||
typedef NS_OPTIONS(NSUInteger, OSSDDLogFlag){
|
||||
/**
|
||||
* 0...00001 DDLogFlagError
|
||||
*/
|
||||
OSSDDLogFlagError = (1 << 0),
|
||||
|
||||
/**
|
||||
* 0...00010 DDLogFlagWarning
|
||||
*/
|
||||
OSSDDLogFlagWarning = (1 << 1),
|
||||
|
||||
/**
|
||||
* 0...00100 DDLogFlagInfo
|
||||
*/
|
||||
OSSDDLogFlagInfo = (1 << 2),
|
||||
|
||||
/**
|
||||
* 0...01000 DDLogFlagDebug
|
||||
*/
|
||||
OSSDDLogFlagDebug = (1 << 3),
|
||||
|
||||
/**
|
||||
* 0...10000 DDLogFlagVerbose
|
||||
*/
|
||||
OSSDDLogFlagVerbose = (1 << 4)
|
||||
};
|
||||
|
||||
/**
|
||||
* Log levels are used to filter out logs. Used together with flags.
|
||||
*/
|
||||
typedef NS_ENUM(NSUInteger, OSSDDLogLevel){
|
||||
/**
|
||||
* No logs
|
||||
*/
|
||||
OSSDDLogLevelOff = 0,
|
||||
|
||||
/**
|
||||
* Error logs only
|
||||
*/
|
||||
OSSDDLogLevelError = (OSSDDLogFlagError),
|
||||
|
||||
/**
|
||||
* Error and warning logs
|
||||
*/
|
||||
OSSDDLogLevelWarning = (OSSDDLogLevelError | OSSDDLogFlagWarning),
|
||||
|
||||
/**
|
||||
* Error, warning and info logs
|
||||
*/
|
||||
OSSDDLogLevelInfo = (OSSDDLogLevelWarning | OSSDDLogFlagInfo),
|
||||
|
||||
/**
|
||||
* Error, warning, info and debug logs
|
||||
*/
|
||||
OSSDDLogLevelDebug = (OSSDDLogLevelInfo | OSSDDLogFlagDebug),
|
||||
|
||||
/**
|
||||
* Error, warning, info, debug and verbose logs
|
||||
*/
|
||||
OSSDDLogLevelVerbose = (OSSDDLogLevelDebug | OSSDDLogFlagVerbose),
|
||||
|
||||
/**
|
||||
* All logs (1...11111)
|
||||
*/
|
||||
OSSDDLogLevelAll = NSUIntegerMax
|
||||
};
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
/**
|
||||
* Extracts just the file name, no path or extension
|
||||
*
|
||||
* @param filePath input file path
|
||||
* @param copy YES if we want the result to be copied
|
||||
*
|
||||
* @return the file name
|
||||
*/
|
||||
NSString * __nullable OSSDDExtractFileNameWithoutExtension(const char *filePath, BOOL copy);
|
||||
|
||||
/**
|
||||
* The THIS_FILE macro gives you an NSString of the file name.
|
||||
* For simplicity and clarity, the file name does not include the full path or file extension.
|
||||
*
|
||||
* For example: DDLogWarn(@"%@: Unable to find thingy", THIS_FILE) -> @"MyViewController: Unable to find thingy"
|
||||
**/
|
||||
#define THIS_FILE (DDExtractFileNameWithoutExtension(__FILE__, NO))
|
||||
|
||||
/**
|
||||
* The THIS_METHOD macro gives you the name of the current objective-c method.
|
||||
*
|
||||
* For example: DDLogWarn(@"%@ - Requires non-nil strings", THIS_METHOD) -> @"setMake:model: requires non-nil strings"
|
||||
*
|
||||
* Note: This does NOT work in straight C functions (non objective-c).
|
||||
* Instead you should use the predefined __FUNCTION__ macro.
|
||||
**/
|
||||
#define THIS_METHOD NSStringFromSelector(_cmd)
|
||||
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
#pragma mark -
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
/**
|
||||
* The main class, exposes all logging mechanisms, loggers, ...
|
||||
* For most of the users, this class is hidden behind the logging functions like `DDLogInfo`
|
||||
*/
|
||||
@interface OSSDDLog : NSObject
|
||||
|
||||
/**
|
||||
* Returns the singleton `DDLog`.
|
||||
* The instance is used by `DDLog` class methods.
|
||||
*/
|
||||
@property (class, nonatomic, strong, readonly) OSSDDLog *sharedInstance;
|
||||
|
||||
/**
|
||||
* Provides access to the underlying logging queue.
|
||||
* This may be helpful to Logger classes for things like thread synchronization.
|
||||
**/
|
||||
@property (class, nonatomic, DISPATCH_QUEUE_REFERENCE_TYPE, readonly) dispatch_queue_t loggingQueue;
|
||||
|
||||
/**
|
||||
* Logging Primitive.
|
||||
*
|
||||
* This method is used by the macros or logging functions.
|
||||
* It is suggested you stick with the macros as they're easier to use.
|
||||
*
|
||||
* @param asynchronous YES if the logging is done async, NO if you want to force sync
|
||||
* @param level the log level
|
||||
* @param flag the log flag
|
||||
* @param context the context (if any is defined)
|
||||
* @param file the current file
|
||||
* @param function the current function
|
||||
* @param line the current code line
|
||||
* @param tag potential tag
|
||||
* @param format the log format
|
||||
*/
|
||||
+ (void)log:(BOOL)asynchronous
|
||||
level:(OSSDDLogLevel)level
|
||||
flag:(OSSDDLogFlag)flag
|
||||
context:(NSInteger)context
|
||||
file:(const char *)file
|
||||
function:(const char *)function
|
||||
line:(NSUInteger)line
|
||||
tag:(id __nullable)tag
|
||||
format:(NSString *)format, ... NS_FORMAT_FUNCTION(9,10);
|
||||
|
||||
/**
|
||||
* Logging Primitive.
|
||||
*
|
||||
* This method is used by the macros or logging functions.
|
||||
* It is suggested you stick with the macros as they're easier to use.
|
||||
*
|
||||
* @param asynchronous YES if the logging is done async, NO if you want to force sync
|
||||
* @param level the log level
|
||||
* @param flag the log flag
|
||||
* @param context the context (if any is defined)
|
||||
* @param file the current file
|
||||
* @param function the current function
|
||||
* @param line the current code line
|
||||
* @param tag potential tag
|
||||
* @param format the log format
|
||||
*/
|
||||
- (void)log:(BOOL)asynchronous
|
||||
level:(OSSDDLogLevel)level
|
||||
flag:(OSSDDLogFlag)flag
|
||||
context:(NSInteger)context
|
||||
file:(const char *)file
|
||||
function:(const char *)function
|
||||
line:(NSUInteger)line
|
||||
tag:(id __nullable)tag
|
||||
format:(NSString *)format, ... NS_FORMAT_FUNCTION(9,10);
|
||||
|
||||
/**
|
||||
* Logging Primitive.
|
||||
*
|
||||
* This method can be used if you have a prepared va_list.
|
||||
* Similar to `log:level:flag:context:file:function:line:tag:format:...`
|
||||
*
|
||||
* @param asynchronous YES if the logging is done async, NO if you want to force sync
|
||||
* @param level the log level
|
||||
* @param flag the log flag
|
||||
* @param context the context (if any is defined)
|
||||
* @param file the current file
|
||||
* @param function the current function
|
||||
* @param line the current code line
|
||||
* @param tag potential tag
|
||||
* @param format the log format
|
||||
* @param argList the arguments list as a va_list
|
||||
*/
|
||||
+ (void)log:(BOOL)asynchronous
|
||||
level:(OSSDDLogLevel)level
|
||||
flag:(OSSDDLogFlag)flag
|
||||
context:(NSInteger)context
|
||||
file:(const char *)file
|
||||
function:(const char *)function
|
||||
line:(NSUInteger)line
|
||||
tag:(id __nullable)tag
|
||||
format:(NSString *)format
|
||||
args:(va_list)argList NS_SWIFT_NAME(log(asynchronous:level:flag:context:file:function:line:tag:format:arguments:));
|
||||
|
||||
/**
|
||||
* Logging Primitive.
|
||||
*
|
||||
* This method can be used if you have a prepared va_list.
|
||||
* Similar to `log:level:flag:context:file:function:line:tag:format:...`
|
||||
*
|
||||
* @param asynchronous YES if the logging is done async, NO if you want to force sync
|
||||
* @param level the log level
|
||||
* @param flag the log flag
|
||||
* @param context the context (if any is defined)
|
||||
* @param file the current file
|
||||
* @param function the current function
|
||||
* @param line the current code line
|
||||
* @param tag potential tag
|
||||
* @param format the log format
|
||||
* @param argList the arguments list as a va_list
|
||||
*/
|
||||
- (void)log:(BOOL)asynchronous
|
||||
level:(OSSDDLogLevel)level
|
||||
flag:(OSSDDLogFlag)flag
|
||||
context:(NSInteger)context
|
||||
file:(const char *)file
|
||||
function:(const char *)function
|
||||
line:(NSUInteger)line
|
||||
tag:(id __nullable)tag
|
||||
format:(NSString *)format
|
||||
args:(va_list)argList NS_SWIFT_NAME(log(asynchronous:level:flag:context:file:function:line:tag:format:arguments:));
|
||||
|
||||
/**
|
||||
* Logging Primitive.
|
||||
*
|
||||
* This method can be used if you manualy prepared DDLogMessage.
|
||||
*
|
||||
* @param asynchronous YES if the logging is done async, NO if you want to force sync
|
||||
* @param logMessage the log message stored in a `DDLogMessage` model object
|
||||
*/
|
||||
+ (void)log:(BOOL)asynchronous
|
||||
message:(OSSDDLogMessage *)logMessage NS_SWIFT_NAME(log(asynchronous:message:));
|
||||
|
||||
/**
|
||||
* Logging Primitive.
|
||||
*
|
||||
* This method can be used if you manualy prepared DDLogMessage.
|
||||
*
|
||||
* @param asynchronous YES if the logging is done async, NO if you want to force sync
|
||||
* @param logMessage the log message stored in a `DDLogMessage` model object
|
||||
*/
|
||||
- (void)log:(BOOL)asynchronous
|
||||
message:(OSSDDLogMessage *)logMessage NS_SWIFT_NAME(log(asynchronous:message:));
|
||||
|
||||
/**
|
||||
* Since logging can be asynchronous, there may be times when you want to flush the logs.
|
||||
* The framework invokes this automatically when the application quits.
|
||||
**/
|
||||
+ (void)flushLog;
|
||||
|
||||
/**
|
||||
* Since logging can be asynchronous, there may be times when you want to flush the logs.
|
||||
* The framework invokes this automatically when the application quits.
|
||||
**/
|
||||
- (void)flushLog;
|
||||
|
||||
/**
|
||||
* Loggers
|
||||
*
|
||||
* In order for your log statements to go somewhere, you should create and add a logger.
|
||||
*
|
||||
* You can add multiple loggers in order to direct your log statements to multiple places.
|
||||
* And each logger can be configured separately.
|
||||
* So you could have, for example, verbose logging to the console, but a concise log file with only warnings & errors.
|
||||
**/
|
||||
|
||||
/**
|
||||
* Adds the logger to the system.
|
||||
*
|
||||
* This is equivalent to invoking `[DDLog addLogger:logger withLogLevel:DDLogLevelAll]`.
|
||||
**/
|
||||
+ (void)addLogger:(id <OSSDDLogger>)logger;
|
||||
|
||||
/**
|
||||
* Adds the logger to the system.
|
||||
*
|
||||
* This is equivalent to invoking `[DDLog addLogger:logger withLogLevel:DDLogLevelAll]`.
|
||||
**/
|
||||
- (void)addLogger:(id <OSSDDLogger>)logger;
|
||||
|
||||
/**
|
||||
* Adds the logger to the system.
|
||||
*
|
||||
* The level that you provide here is a preemptive filter (for performance).
|
||||
* That is, the level specified here will be used to filter out logMessages so that
|
||||
* the logger is never even invoked for the messages.
|
||||
*
|
||||
* More information:
|
||||
* When you issue a log statement, the logging framework iterates over each logger,
|
||||
* and checks to see if it should forward the logMessage to the logger.
|
||||
* This check is done using the level parameter passed to this method.
|
||||
*
|
||||
* For example:
|
||||
*
|
||||
* `[DDLog addLogger:consoleLogger withLogLevel:DDLogLevelVerbose];`
|
||||
* `[DDLog addLogger:fileLogger withLogLevel:DDLogLevelWarning];`
|
||||
*
|
||||
* `DDLogError(@"oh no");` => gets forwarded to consoleLogger & fileLogger
|
||||
* `DDLogInfo(@"hi");` => gets forwarded to consoleLogger only
|
||||
*
|
||||
* It is important to remember that Lumberjack uses a BITMASK.
|
||||
* Many developers & third party frameworks may define extra log levels & flags.
|
||||
* For example:
|
||||
*
|
||||
* `#define SOME_FRAMEWORK_LOG_FLAG_TRACE (1 << 6) // 0...1000000`
|
||||
*
|
||||
* So if you specify `DDLogLevelVerbose` to this method, you won't see the framework's trace messages.
|
||||
*
|
||||
* `(SOME_FRAMEWORK_LOG_FLAG_TRACE & DDLogLevelVerbose) => (01000000 & 00011111) => NO`
|
||||
*
|
||||
* Consider passing `DDLogLevelAll` to this method, which has all bits set.
|
||||
* You can also use the exclusive-or bitwise operator to get a bitmask that has all flags set,
|
||||
* except the ones you explicitly don't want. For example, if you wanted everything except verbose & debug:
|
||||
*
|
||||
* `((DDLogLevelAll ^ DDLogLevelVerbose) | DDLogLevelInfo)`
|
||||
**/
|
||||
+ (void)addLogger:(id <OSSDDLogger>)logger withLevel:(OSSDDLogLevel)level;
|
||||
|
||||
/**
|
||||
* Adds the logger to the system.
|
||||
*
|
||||
* The level that you provide here is a preemptive filter (for performance).
|
||||
* That is, the level specified here will be used to filter out logMessages so that
|
||||
* the logger is never even invoked for the messages.
|
||||
*
|
||||
* More information:
|
||||
* When you issue a log statement, the logging framework iterates over each logger,
|
||||
* and checks to see if it should forward the logMessage to the logger.
|
||||
* This check is done using the level parameter passed to this method.
|
||||
*
|
||||
* For example:
|
||||
*
|
||||
* `[DDLog addLogger:consoleLogger withLogLevel:DDLogLevelVerbose];`
|
||||
* `[DDLog addLogger:fileLogger withLogLevel:DDLogLevelWarning];`
|
||||
*
|
||||
* `DDLogError(@"oh no");` => gets forwarded to consoleLogger & fileLogger
|
||||
* `DDLogInfo(@"hi");` => gets forwarded to consoleLogger only
|
||||
*
|
||||
* It is important to remember that Lumberjack uses a BITMASK.
|
||||
* Many developers & third party frameworks may define extra log levels & flags.
|
||||
* For example:
|
||||
*
|
||||
* `#define SOME_FRAMEWORK_LOG_FLAG_TRACE (1 << 6) // 0...1000000`
|
||||
*
|
||||
* So if you specify `DDLogLevelVerbose` to this method, you won't see the framework's trace messages.
|
||||
*
|
||||
* `(SOME_FRAMEWORK_LOG_FLAG_TRACE & DDLogLevelVerbose) => (01000000 & 00011111) => NO`
|
||||
*
|
||||
* Consider passing `DDLogLevelAll` to this method, which has all bits set.
|
||||
* You can also use the exclusive-or bitwise operator to get a bitmask that has all flags set,
|
||||
* except the ones you explicitly don't want. For example, if you wanted everything except verbose & debug:
|
||||
*
|
||||
* `((DDLogLevelAll ^ DDLogLevelVerbose) | DDLogLevelInfo)`
|
||||
**/
|
||||
- (void)addLogger:(id <OSSDDLogger>)logger withLevel:(OSSDDLogLevel)level;
|
||||
|
||||
/**
|
||||
* Remove the logger from the system
|
||||
*/
|
||||
+ (void)removeLogger:(id <OSSDDLogger>)logger;
|
||||
|
||||
/**
|
||||
* Remove the logger from the system
|
||||
*/
|
||||
- (void)removeLogger:(id <OSSDDLogger>)logger;
|
||||
|
||||
/**
|
||||
* Remove all the current loggers
|
||||
*/
|
||||
+ (void)removeAllLoggers;
|
||||
|
||||
/**
|
||||
* Remove all the current loggers
|
||||
*/
|
||||
- (void)removeAllLoggers;
|
||||
|
||||
/**
|
||||
* Return all the current loggers
|
||||
*/
|
||||
@property (class, nonatomic, copy, readonly) NSArray<id<OSSDDLogger>> *allLoggers;
|
||||
|
||||
/**
|
||||
* Return all the current loggers
|
||||
*/
|
||||
@property (nonatomic, copy, readonly) NSArray<id<OSSDDLogger>> *allLoggers;
|
||||
|
||||
/**
|
||||
* Return all the current loggers with their level (aka DDLoggerInformation).
|
||||
*/
|
||||
@property (class, nonatomic, copy, readonly) NSArray<OSSDDLoggerInformation *> *allLoggersWithLevel;
|
||||
|
||||
/**
|
||||
* Return all the current loggers with their level (aka DDLoggerInformation).
|
||||
*/
|
||||
@property (nonatomic, copy, readonly) NSArray<OSSDDLoggerInformation *> *allLoggersWithLevel;
|
||||
|
||||
@end
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
#pragma mark -
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
/**
|
||||
* This protocol describes a basic logger behavior.
|
||||
* Basically, it can log messages, store a logFormatter plus a bunch of optional behaviors.
|
||||
* (i.e. flush, get its loggerQueue, get its name, ...
|
||||
*/
|
||||
@protocol OSSDDLogger <NSObject>
|
||||
|
||||
/**
|
||||
* The log message method
|
||||
*
|
||||
* @param logMessage the message (model)
|
||||
*/
|
||||
- (void)logMessage:(OSSDDLogMessage *)logMessage NS_SWIFT_NAME(log(message:));
|
||||
|
||||
/**
|
||||
* Formatters may optionally be added to any logger.
|
||||
*
|
||||
* If no formatter is set, the logger simply logs the message as it is given in logMessage,
|
||||
* or it may use its own built in formatting style.
|
||||
**/
|
||||
@property (nonatomic, strong) id <OSSDDLogFormatter> logFormatter;
|
||||
|
||||
@optional
|
||||
|
||||
/**
|
||||
* Since logging is asynchronous, adding and removing loggers is also asynchronous.
|
||||
* In other words, the loggers are added and removed at appropriate times with regards to log messages.
|
||||
*
|
||||
* - Loggers will not receive log messages that were executed prior to when they were added.
|
||||
* - Loggers will not receive log messages that were executed after they were removed.
|
||||
*
|
||||
* These methods are executed in the logging thread/queue.
|
||||
* This is the same thread/queue that will execute every logMessage: invocation.
|
||||
* Loggers may use these methods for thread synchronization or other setup/teardown tasks.
|
||||
**/
|
||||
- (void)didAddLogger;
|
||||
|
||||
/**
|
||||
* Since logging is asynchronous, adding and removing loggers is also asynchronous.
|
||||
* In other words, the loggers are added and removed at appropriate times with regards to log messages.
|
||||
*
|
||||
* - Loggers will not receive log messages that were executed prior to when they were added.
|
||||
* - Loggers will not receive log messages that were executed after they were removed.
|
||||
*
|
||||
* These methods are executed in the logging thread/queue given in parameter.
|
||||
* This is the same thread/queue that will execute every logMessage: invocation.
|
||||
* Loggers may use the queue parameter to set specific values on the queue with dispatch_set_specific() function.
|
||||
**/
|
||||
- (void)didAddLoggerInQueue:(dispatch_queue_t)queue;
|
||||
|
||||
/**
|
||||
* See the above description for `didAddLoger`
|
||||
*/
|
||||
- (void)willRemoveLogger;
|
||||
|
||||
/**
|
||||
* Some loggers may buffer IO for optimization purposes.
|
||||
* For example, a database logger may only save occasionaly as the disk IO is slow.
|
||||
* In such loggers, this method should be implemented to flush any pending IO.
|
||||
*
|
||||
* This allows invocations of DDLog's flushLog method to be propogated to loggers that need it.
|
||||
*
|
||||
* Note that DDLog's flushLog method is invoked automatically when the application quits,
|
||||
* and it may be also invoked manually by the developer prior to application crashes, or other such reasons.
|
||||
**/
|
||||
- (void)flush;
|
||||
|
||||
/**
|
||||
* Each logger is executed concurrently with respect to the other loggers.
|
||||
* Thus, a dedicated dispatch queue is used for each logger.
|
||||
* Logger implementations may optionally choose to provide their own dispatch queue.
|
||||
**/
|
||||
@property (nonatomic, DISPATCH_QUEUE_REFERENCE_TYPE, readonly) dispatch_queue_t loggerQueue;
|
||||
|
||||
/**
|
||||
* If the logger implementation does not choose to provide its own queue,
|
||||
* one will automatically be created for it.
|
||||
* The created queue will receive its name from this method.
|
||||
* This may be helpful for debugging or profiling reasons.
|
||||
**/
|
||||
@property (nonatomic, readonly) NSString *loggerName;
|
||||
|
||||
@end
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
#pragma mark -
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
/**
|
||||
* This protocol describes the behavior of a log formatter
|
||||
*/
|
||||
@protocol OSSDDLogFormatter <NSObject>
|
||||
@required
|
||||
|
||||
/**
|
||||
* Formatters may optionally be added to any logger.
|
||||
* This allows for increased flexibility in the logging environment.
|
||||
* For example, log messages for log files may be formatted differently than log messages for the console.
|
||||
*
|
||||
* For more information about formatters, see the "Custom Formatters" page:
|
||||
* Documentation/CustomFormatters.md
|
||||
*
|
||||
* The formatter may also optionally filter the log message by returning nil,
|
||||
* in which case the logger will not log the message.
|
||||
**/
|
||||
- (NSString * __nullable)formatLogMessage:(OSSDDLogMessage *)logMessage NS_SWIFT_NAME(format(message:));
|
||||
|
||||
@optional
|
||||
|
||||
/**
|
||||
* A single formatter instance can be added to multiple loggers.
|
||||
* These methods provides hooks to notify the formatter of when it's added/removed.
|
||||
*
|
||||
* This is primarily for thread-safety.
|
||||
* If a formatter is explicitly not thread-safe, it may wish to throw an exception if added to multiple loggers.
|
||||
* Or if a formatter has potentially thread-unsafe code (e.g. NSDateFormatter),
|
||||
* it could possibly use these hooks to switch to thread-safe versions of the code.
|
||||
**/
|
||||
- (void)didAddToLogger:(id <OSSDDLogger>)logger;
|
||||
|
||||
/**
|
||||
* A single formatter instance can be added to multiple loggers.
|
||||
* These methods provides hooks to notify the formatter of when it's added/removed.
|
||||
*
|
||||
* This is primarily for thread-safety.
|
||||
* If a formatter is explicitly not thread-safe, it may wish to throw an exception if added to multiple loggers.
|
||||
* Or if a formatter has potentially thread-unsafe code (e.g. NSDateFormatter),
|
||||
* it could possibly use these hooks to switch to thread-safe versions of the code or use dispatch_set_specific()
|
||||
.* to add its own specific values.
|
||||
**/
|
||||
- (void)didAddToLogger:(id <OSSDDLogger>)logger inQueue:(dispatch_queue_t)queue;
|
||||
|
||||
/**
|
||||
* See the above description for `didAddToLogger:`
|
||||
*/
|
||||
- (void)willRemoveFromLogger:(id <OSSDDLogger>)logger;
|
||||
|
||||
@end
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
#pragma mark -
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
/**
|
||||
* This protocol describes a dynamic logging component
|
||||
*/
|
||||
@protocol OSSDDRegisteredDynamicLogging
|
||||
|
||||
/**
|
||||
* Implement these methods to allow a file's log level to be managed from a central location.
|
||||
*
|
||||
* This is useful if you'd like to be able to change log levels for various parts
|
||||
* of your code from within the running application.
|
||||
*
|
||||
* Imagine pulling up the settings for your application,
|
||||
* and being able to configure the logging level on a per file basis.
|
||||
*
|
||||
* The implementation can be very straight-forward:
|
||||
*
|
||||
* ```
|
||||
* + (int)ddLogLevel
|
||||
* {
|
||||
* return ddLogLevel;
|
||||
* }
|
||||
*
|
||||
* + (void)ddSetLogLevel:(DDLogLevel)level
|
||||
* {
|
||||
* ddLogLevel = level;
|
||||
* }
|
||||
* ```
|
||||
**/
|
||||
@property (class, nonatomic, readwrite, setter=ddSetLogLevel:) OSSDDLogLevel ossLogLevel;
|
||||
|
||||
@end
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
#pragma mark -
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
#ifndef NS_DESIGNATED_INITIALIZER
|
||||
#define NS_DESIGNATED_INITIALIZER
|
||||
#endif
|
||||
|
||||
/**
|
||||
* Log message options, allow copying certain log elements
|
||||
*/
|
||||
typedef NS_OPTIONS(NSInteger, OSSDDLogMessageOptions){
|
||||
/**
|
||||
* Use this to use a copy of the file path
|
||||
*/
|
||||
OSSDDLogMessageCopyFile = 1 << 0,
|
||||
/**
|
||||
* Use this to use a copy of the function name
|
||||
*/
|
||||
OSSDDLogMessageCopyFunction = 1 << 1,
|
||||
/**
|
||||
* Use this to use avoid a copy of the message
|
||||
*/
|
||||
OSSDDLogMessageDontCopyMessage = 1 << 2
|
||||
};
|
||||
|
||||
/**
|
||||
* The `DDLogMessage` class encapsulates information about the log message.
|
||||
* If you write custom loggers or formatters, you will be dealing with objects of this class.
|
||||
**/
|
||||
@interface OSSDDLogMessage : NSObject <NSCopying>
|
||||
{
|
||||
// Direct accessors to be used only for performance
|
||||
@public
|
||||
NSString *_message;
|
||||
OSSDDLogLevel _level;
|
||||
OSSDDLogFlag _flag;
|
||||
NSInteger _context;
|
||||
NSString *_file;
|
||||
NSString *_fileName;
|
||||
NSString *_function;
|
||||
NSUInteger _line;
|
||||
id _tag;
|
||||
OSSDDLogMessageOptions _options;
|
||||
NSDate *_timestamp;
|
||||
NSString *_threadID;
|
||||
NSString *_threadName;
|
||||
NSString *_queueLabel;
|
||||
}
|
||||
|
||||
/**
|
||||
* Default `init` for empty messages.
|
||||
*/
|
||||
- (instancetype)init NS_DESIGNATED_INITIALIZER;
|
||||
|
||||
/**
|
||||
* Standard init method for a log message object.
|
||||
* Used by the logging primitives. (And the macros use the logging primitives.)
|
||||
*
|
||||
* If you find need to manually create logMessage objects, there is one thing you should be aware of:
|
||||
*
|
||||
* If no flags are passed, the method expects the file and function parameters to be string literals.
|
||||
* That is, it expects the given strings to exist for the duration of the object's lifetime,
|
||||
* and it expects the given strings to be immutable.
|
||||
* In other words, it does not copy these strings, it simply points to them.
|
||||
* This is due to the fact that __FILE__ and __FUNCTION__ are usually used to specify these parameters,
|
||||
* so it makes sense to optimize and skip the unnecessary allocations.
|
||||
* However, if you need them to be copied you may use the options parameter to specify this.
|
||||
*
|
||||
* @param message the message
|
||||
* @param level the log level
|
||||
* @param flag the log flag
|
||||
* @param context the context (if any is defined)
|
||||
* @param file the current file
|
||||
* @param function the current function
|
||||
* @param line the current code line
|
||||
* @param tag potential tag
|
||||
* @param options a bitmask which supports DDLogMessageCopyFile and DDLogMessageCopyFunction.
|
||||
* @param timestamp the log timestamp
|
||||
*
|
||||
* @return a new instance of a log message model object
|
||||
*/
|
||||
- (instancetype)initWithMessage:(NSString *)message
|
||||
level:(OSSDDLogLevel)level
|
||||
flag:(OSSDDLogFlag)flag
|
||||
context:(NSInteger)context
|
||||
file:(NSString *)file
|
||||
function:(NSString * __nullable)function
|
||||
line:(NSUInteger)line
|
||||
tag:(id __nullable)tag
|
||||
options:(OSSDDLogMessageOptions)options
|
||||
timestamp:(NSDate * __nullable)timestamp NS_DESIGNATED_INITIALIZER;
|
||||
|
||||
/**
|
||||
* Read-only properties
|
||||
**/
|
||||
|
||||
/**
|
||||
* The log message
|
||||
*/
|
||||
@property (readonly, nonatomic) NSString *message;
|
||||
@property (readonly, nonatomic) OSSDDLogLevel level;
|
||||
@property (readonly, nonatomic) OSSDDLogFlag flag;
|
||||
@property (readonly, nonatomic) NSInteger context;
|
||||
@property (readonly, nonatomic) NSString *file;
|
||||
@property (readonly, nonatomic) NSString *fileName;
|
||||
@property (readonly, nonatomic) NSString * __nullable function;
|
||||
@property (readonly, nonatomic) NSUInteger line;
|
||||
@property (readonly, nonatomic) id __nullable tag;
|
||||
@property (readonly, nonatomic) OSSDDLogMessageOptions options;
|
||||
@property (readonly, nonatomic) NSDate *timestamp;
|
||||
@property (readonly, nonatomic) NSString *threadID; // ID as it appears in NSLog calculated from the machThreadID
|
||||
@property (readonly, nonatomic) NSString *threadName;
|
||||
@property (readonly, nonatomic) NSString *queueLabel;
|
||||
|
||||
@end
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
#pragma mark -
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
/**
|
||||
* The `DDLogger` protocol specifies that an optional formatter can be added to a logger.
|
||||
* Most (but not all) loggers will want to support formatters.
|
||||
*
|
||||
* However, writting getters and setters in a thread safe manner,
|
||||
* while still maintaining maximum speed for the logging process, is a difficult task.
|
||||
*
|
||||
* To do it right, the implementation of the getter/setter has strict requiremenets:
|
||||
* - Must NOT require the `logMessage:` method to acquire a lock.
|
||||
* - Must NOT require the `logMessage:` method to access an atomic property (also a lock of sorts).
|
||||
*
|
||||
* To simplify things, an abstract logger is provided that implements the getter and setter.
|
||||
*
|
||||
* Logger implementations may simply extend this class,
|
||||
* and they can ACCESS THE FORMATTER VARIABLE DIRECTLY from within their `logMessage:` method!
|
||||
**/
|
||||
@interface OSSDDAbstractLogger : NSObject <OSSDDLogger>
|
||||
{
|
||||
// Direct accessors to be used only for performance
|
||||
@public
|
||||
id <OSSDDLogFormatter> _logFormatter;
|
||||
dispatch_queue_t _loggerQueue;
|
||||
}
|
||||
|
||||
@property (nonatomic, strong, nullable) id <OSSDDLogFormatter> logFormatter;
|
||||
@property (nonatomic, DISPATCH_QUEUE_REFERENCE_TYPE) dispatch_queue_t loggerQueue;
|
||||
|
||||
// For thread-safety assertions
|
||||
|
||||
/**
|
||||
* Return YES if the current logger uses a global queue for logging
|
||||
*/
|
||||
@property (nonatomic, readonly, getter=isOnGlobalLoggingQueue) BOOL onGlobalLoggingQueue;
|
||||
|
||||
/**
|
||||
* Return YES if the current logger uses the internal designated queue for logging
|
||||
*/
|
||||
@property (nonatomic, readonly, getter=isOnInternalLoggerQueue) BOOL onInternalLoggerQueue;
|
||||
|
||||
@end
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
#pragma mark -
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
@interface OSSDDLoggerInformation : NSObject
|
||||
|
||||
@property (nonatomic, readonly) id <OSSDDLogger> logger;
|
||||
@property (nonatomic, readonly) OSSDDLogLevel level;
|
||||
|
||||
+ (OSSDDLoggerInformation *)informationWithLogger:(id <OSSDDLogger>)logger
|
||||
andLevel:(OSSDDLogLevel)level;
|
||||
|
||||
@end
|
||||
|
||||
NS_ASSUME_NONNULL_END
|
||||
1247
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSFileLog/OSSDDLog.m
generated
Normal file
1247
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSFileLog/OSSDDLog.m
generated
Normal file
File diff suppressed because it is too large
Load Diff
509
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSFileLog/OSSFileLogger.h
generated
Normal file
509
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSFileLog/OSSFileLogger.h
generated
Normal file
@@ -0,0 +1,509 @@
|
||||
// Software License Agreement (BSD License)
|
||||
//
|
||||
// Copyright (c) 2010-2016, Deusty, LLC
|
||||
// All rights reserved.
|
||||
//
|
||||
// Redistribution and use of this software in source and binary forms,
|
||||
// with or without modification, are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistributions of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Neither the name of Deusty nor the names of its contributors may be used
|
||||
// to endorse or promote products derived from this software without specific
|
||||
// prior written permission of Deusty, LLC.
|
||||
|
||||
// Disable legacy macros
|
||||
#ifndef DD_LEGACY_MACROS
|
||||
#define DD_LEGACY_MACROS 0
|
||||
#endif
|
||||
|
||||
#import "OSSDDLog.h"
|
||||
|
||||
@class OSSDDLogFileInfo;
|
||||
|
||||
/**
|
||||
* This class provides a logger to write log statements to a file.
|
||||
**/
|
||||
|
||||
|
||||
// Default configuration and safety/sanity values.
|
||||
//
|
||||
// maximumFileSize -> kDDDefaultLogMaxFileSize
|
||||
// rollingFrequency -> kDDDefaultLogRollingFrequency
|
||||
// maximumNumberOfLogFiles -> kDDDefaultLogMaxNumLogFiles
|
||||
// logFilesDiskQuota -> kDDDefaultLogFilesDiskQuota
|
||||
//
|
||||
// You should carefully consider the proper configuration values for your application.
|
||||
|
||||
extern unsigned long long const osskDDDefaultLogMaxFileSize;
|
||||
extern NSTimeInterval const osskDDDefaultLogRollingFrequency;
|
||||
extern NSUInteger const osskDDDefaultLogMaxNumLogFiles;
|
||||
extern unsigned long long const osskDDDefaultLogFilesDiskQuota;
|
||||
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
#pragma mark -
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
/**
|
||||
* The LogFileManager protocol is designed to allow you to control all aspects of your log files.
|
||||
*
|
||||
* The primary purpose of this is to allow you to do something with the log files after they have been rolled.
|
||||
* Perhaps you want to compress them to save disk space.
|
||||
* Perhaps you want to upload them to an FTP server.
|
||||
* Perhaps you want to run some analytics on the file.
|
||||
*
|
||||
* A default LogFileManager is, of course, provided.
|
||||
* The default LogFileManager simply deletes old log files according to the maximumNumberOfLogFiles property.
|
||||
*
|
||||
* This protocol provides various methods to fetch the list of log files.
|
||||
*
|
||||
* There are two variants: sorted and unsorted.
|
||||
* If sorting is not necessary, the unsorted variant is obviously faster.
|
||||
* The sorted variant will return an array sorted by when the log files were created,
|
||||
* with the most recently created log file at index 0, and the oldest log file at the end of the array.
|
||||
*
|
||||
* You can fetch only the log file paths (full path including name), log file names (name only),
|
||||
* or an array of `DDLogFileInfo` objects.
|
||||
* The `DDLogFileInfo` class is documented below, and provides a handy wrapper that
|
||||
* gives you easy access to various file attributes such as the creation date or the file size.
|
||||
*/
|
||||
@protocol OSSDDLogFileManager <NSObject>
|
||||
@required
|
||||
|
||||
// Public properties
|
||||
|
||||
/**
|
||||
* The maximum number of archived log files to keep on disk.
|
||||
* For example, if this property is set to 3,
|
||||
* then the LogFileManager will only keep 3 archived log files (plus the current active log file) on disk.
|
||||
* Once the active log file is rolled/archived, then the oldest of the existing 3 rolled/archived log files is deleted.
|
||||
*
|
||||
* You may optionally disable this option by setting it to zero.
|
||||
**/
|
||||
@property (readwrite, assign, atomic) NSUInteger maximumNumberOfLogFiles;
|
||||
|
||||
/**
|
||||
* The maximum space that logs can take. On rolling logfile all old logfiles that exceed logFilesDiskQuota will
|
||||
* be deleted.
|
||||
*
|
||||
* You may optionally disable this option by setting it to zero.
|
||||
**/
|
||||
@property (readwrite, assign, atomic) unsigned long long logFilesDiskQuota;
|
||||
|
||||
// Public methods
|
||||
|
||||
/**
|
||||
* Returns the logs directory (path)
|
||||
*/
|
||||
@property (nonatomic, readonly, copy) NSString *logsDirectory;
|
||||
|
||||
/**
|
||||
* Returns an array of `NSString` objects,
|
||||
* each of which is the filePath to an existing log file on disk.
|
||||
**/
|
||||
@property (nonatomic, readonly, strong) NSArray<NSString *> *unsortedLogFilePaths;
|
||||
|
||||
/**
|
||||
* Returns an array of `NSString` objects,
|
||||
* each of which is the fileName of an existing log file on disk.
|
||||
**/
|
||||
@property (nonatomic, readonly, strong) NSArray<NSString *> *unsortedLogFileNames;
|
||||
|
||||
/**
|
||||
* Returns an array of `DDLogFileInfo` objects,
|
||||
* each representing an existing log file on disk,
|
||||
* and containing important information about the log file such as it's modification date and size.
|
||||
**/
|
||||
@property (nonatomic, readonly, strong) NSArray<OSSDDLogFileInfo *> *unsortedLogFileInfos;
|
||||
|
||||
/**
|
||||
* Just like the `unsortedLogFilePaths` method, but sorts the array.
|
||||
* The items in the array are sorted by creation date.
|
||||
* The first item in the array will be the most recently created log file.
|
||||
**/
|
||||
@property (nonatomic, readonly, strong) NSArray<NSString *> *sortedLogFilePaths;
|
||||
|
||||
/**
|
||||
* Just like the `unsortedLogFileNames` method, but sorts the array.
|
||||
* The items in the array are sorted by creation date.
|
||||
* The first item in the array will be the most recently created log file.
|
||||
**/
|
||||
@property (nonatomic, readonly, strong) NSArray<NSString *> *sortedLogFileNames;
|
||||
|
||||
/**
|
||||
* Just like the `unsortedLogFileInfos` method, but sorts the array.
|
||||
* The items in the array are sorted by creation date.
|
||||
* The first item in the array will be the most recently created log file.
|
||||
**/
|
||||
@property (nonatomic, readonly, strong) NSArray<OSSDDLogFileInfo *> *sortedLogFileInfos;
|
||||
|
||||
// Private methods (only to be used by DDFileLogger)
|
||||
|
||||
/**
|
||||
* Generates a new unique log file path, and creates the corresponding log file.
|
||||
**/
|
||||
- (NSString *)createNewLogFile;
|
||||
|
||||
@optional
|
||||
|
||||
// Notifications from DDFileLogger
|
||||
|
||||
/**
|
||||
* Called when a log file was archieved
|
||||
*/
|
||||
- (void)didArchiveLogFile:(NSString *)logFilePath NS_SWIFT_NAME(didArchiveLogFile(atPath:));
|
||||
|
||||
/**
|
||||
* Called when the roll action was executed and the log was archieved
|
||||
*/
|
||||
- (void)didRollAndArchiveLogFile:(NSString *)logFilePath NS_SWIFT_NAME(didRollAndArchiveLogFile(atPath:));
|
||||
|
||||
@end
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
#pragma mark -
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
/**
|
||||
* Default log file manager.
|
||||
*
|
||||
* All log files are placed inside the logsDirectory.
|
||||
* If a specific logsDirectory isn't specified, the default directory is used.
|
||||
* On Mac, this is in `~/Library/Logs/<Application Name>`.
|
||||
* On iPhone, this is in `~/Library/Caches/Logs`.
|
||||
*
|
||||
* Log files are named `"<bundle identifier> <date> <time>.log"`
|
||||
* Example: `com.organization.myapp 2013-12-03 17-14.log`
|
||||
*
|
||||
* Archived log files are automatically deleted according to the `maximumNumberOfLogFiles` property.
|
||||
**/
|
||||
@interface OSSDDLogFileManagerDefault : NSObject <OSSDDLogFileManager>
|
||||
|
||||
/**
|
||||
* Default initializer
|
||||
*/
|
||||
- (instancetype)init;
|
||||
|
||||
/**
|
||||
* Designated initialized, requires the logs directory
|
||||
*/
|
||||
- (instancetype)initWithLogsDirectory:(NSString *)logsDirectory NS_DESIGNATED_INITIALIZER;
|
||||
|
||||
#if TARGET_OS_IPHONE
|
||||
/*
|
||||
* Calling this constructor you can override the default "automagically" chosen NSFileProtection level.
|
||||
* Useful if you are writing a command line utility / CydiaSubstrate addon for iOS that has no NSBundle
|
||||
* or like SpringBoard no BackgroundModes key in the NSBundle:
|
||||
* iPhone:~ root# cycript -p SpringBoard
|
||||
* cy# [NSBundle mainBundle]
|
||||
* #"NSBundle </System/Library/CoreServices/SpringBoard.app> (loaded)"
|
||||
* cy# [[NSBundle mainBundle] objectForInfoDictionaryKey:@"UIBackgroundModes"];
|
||||
* null
|
||||
* cy#
|
||||
**/
|
||||
- (instancetype)initWithLogsDirectory:(NSString *)logsDirectory defaultFileProtectionLevel:(NSFileProtectionType)fileProtectionLevel;
|
||||
#endif
|
||||
|
||||
/*
|
||||
* Methods to override.
|
||||
*
|
||||
* Log files are named `"<bundle identifier> <date> <time>.log"`
|
||||
* Example: `com.organization.myapp 2013-12-03 17-14.log`
|
||||
*
|
||||
* If you wish to change default filename, you can override following two methods.
|
||||
* - `newLogFileName` method would be called on new logfile creation.
|
||||
* - `isLogFile:` method would be called to filter logfiles from all other files in logsDirectory.
|
||||
* You have to parse given filename and return YES if it is logFile.
|
||||
*
|
||||
* **NOTE**
|
||||
* `newLogFileName` returns filename. If appropriate file already exists, number would be added
|
||||
* to filename before extension. You have to handle this case in isLogFile: method.
|
||||
*
|
||||
* Example:
|
||||
* - newLogFileName returns `"com.organization.myapp 2013-12-03.log"`,
|
||||
* file `"com.organization.myapp 2013-12-03.log"` would be created.
|
||||
* - after some time `"com.organization.myapp 2013-12-03.log"` is archived
|
||||
* - newLogFileName again returns `"com.organization.myapp 2013-12-03.log"`,
|
||||
* file `"com.organization.myapp 2013-12-03 2.log"` would be created.
|
||||
* - after some time `"com.organization.myapp 2013-12-03 1.log"` is archived
|
||||
* - newLogFileName again returns `"com.organization.myapp 2013-12-03.log"`,
|
||||
* file `"com.organization.myapp 2013-12-03 3.log"` would be created.
|
||||
**/
|
||||
|
||||
/**
|
||||
* Generates log file name with default format `"<bundle identifier> <date> <time>.log"`
|
||||
* Example: `MobileSafari 2013-12-03 17-14.log`
|
||||
*
|
||||
* You can change it by overriding `newLogFileName` and `isLogFile:` methods.
|
||||
**/
|
||||
@property (readonly, copy) NSString *newLogFileName;
|
||||
|
||||
/**
|
||||
* Default log file name is `"<bundle identifier> <date> <time>.log"`.
|
||||
* Example: `MobileSafari 2013-12-03 17-14.log`
|
||||
*
|
||||
* You can change it by overriding `newLogFileName` and `isLogFile:` methods.
|
||||
**/
|
||||
- (BOOL)isLogFile:(NSString *)fileName NS_SWIFT_NAME(isLogFile(withName:));
|
||||
|
||||
/* Inherited from DDLogFileManager protocol:
|
||||
|
||||
@property (readwrite, assign, atomic) NSUInteger maximumNumberOfLogFiles;
|
||||
@property (readwrite, assign, atomic) NSUInteger logFilesDiskQuota;
|
||||
|
||||
- (NSString *)logsDirectory;
|
||||
|
||||
- (NSArray *)unsortedLogFilePaths;
|
||||
- (NSArray *)unsortedLogFileNames;
|
||||
- (NSArray *)unsortedLogFileInfos;
|
||||
|
||||
- (NSArray *)sortedLogFilePaths;
|
||||
- (NSArray *)sortedLogFileNames;
|
||||
- (NSArray *)sortedLogFileInfos;
|
||||
|
||||
*/
|
||||
|
||||
@end
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
#pragma mark -
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
/**
|
||||
* Most users will want file log messages to be prepended with the date and time.
|
||||
* Rather than forcing the majority of users to write their own formatter,
|
||||
* we will supply a logical default formatter.
|
||||
* Users can easily replace this formatter with their own by invoking the `setLogFormatter:` method.
|
||||
* It can also be removed by calling `setLogFormatter:`, and passing a nil parameter.
|
||||
*
|
||||
* In addition to the convenience of having a logical default formatter,
|
||||
* it will also provide a template that makes it easy for developers to copy and change.
|
||||
**/
|
||||
@interface OSSDDLogFileFormatterDefault : NSObject <OSSDDLogFormatter>
|
||||
|
||||
/**
|
||||
* Default initializer
|
||||
*/
|
||||
- (instancetype)init;
|
||||
|
||||
/**
|
||||
* Designated initializer, requires a date formatter
|
||||
*/
|
||||
- (instancetype)initWithDateFormatter:(NSDateFormatter *)dateFormatter NS_DESIGNATED_INITIALIZER;
|
||||
|
||||
@end
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
#pragma mark -
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
/**
|
||||
* The standard implementation for a file logger
|
||||
*/
|
||||
@interface OSSDDFileLogger : OSSDDAbstractLogger <OSSDDLogger> {
|
||||
OSSDDLogFileInfo *_currentLogFileInfo;
|
||||
}
|
||||
|
||||
/**
|
||||
* Default initializer
|
||||
*/
|
||||
- (instancetype)init;
|
||||
|
||||
/**
|
||||
* Designated initializer, requires a `DDLogFileManager` instance
|
||||
*/
|
||||
- (instancetype)initWithLogFileManager:(id <OSSDDLogFileManager>)logFileManager NS_DESIGNATED_INITIALIZER;
|
||||
|
||||
/**
|
||||
* Called when the logger is about to write message. Call super before your implementation.
|
||||
*/
|
||||
- (void)willLogMessage NS_REQUIRES_SUPER;
|
||||
|
||||
/**
|
||||
* Called when the logger wrote message. Call super after your implementation.
|
||||
*/
|
||||
- (void)didLogMessage NS_REQUIRES_SUPER;
|
||||
|
||||
/**
|
||||
* Called when the logger checks archive or not current log file.
|
||||
* Override this method to exdend standart behavior. By default returns NO.
|
||||
*/
|
||||
- (BOOL)shouldArchiveRecentLogFileInfo:(OSSDDLogFileInfo *)recentLogFileInfo;
|
||||
|
||||
/**
|
||||
* Log File Rolling:
|
||||
*
|
||||
* `maximumFileSize`:
|
||||
* The approximate maximum size (in bytes) to allow log files to grow.
|
||||
* If a log file is larger than this value after a log statement is appended,
|
||||
* then the log file is rolled.
|
||||
*
|
||||
* `rollingFrequency`
|
||||
* How often to roll the log file.
|
||||
* The frequency is given as an `NSTimeInterval`, which is a double that specifies the interval in seconds.
|
||||
* Once the log file gets to be this old, it is rolled.
|
||||
*
|
||||
* `doNotReuseLogFiles`
|
||||
* When set, will always create a new log file at application launch.
|
||||
*
|
||||
* Both the `maximumFileSize` and the `rollingFrequency` are used to manage rolling.
|
||||
* Whichever occurs first will cause the log file to be rolled.
|
||||
*
|
||||
* For example:
|
||||
* The `rollingFrequency` is 24 hours,
|
||||
* but the log file surpasses the `maximumFileSize` after only 20 hours.
|
||||
* The log file will be rolled at that 20 hour mark.
|
||||
* A new log file will be created, and the 24 hour timer will be restarted.
|
||||
*
|
||||
* You may optionally disable rolling due to filesize by setting `maximumFileSize` to zero.
|
||||
* If you do so, rolling is based solely on `rollingFrequency`.
|
||||
*
|
||||
* You may optionally disable rolling due to time by setting `rollingFrequency` to zero (or any non-positive number).
|
||||
* If you do so, rolling is based solely on `maximumFileSize`.
|
||||
*
|
||||
* If you disable both `maximumFileSize` and `rollingFrequency`, then the log file won't ever be rolled.
|
||||
* This is strongly discouraged.
|
||||
**/
|
||||
@property (readwrite, assign) unsigned long long maximumFileSize;
|
||||
|
||||
/**
|
||||
* See description for `maximumFileSize`
|
||||
*/
|
||||
@property (readwrite, assign) NSTimeInterval rollingFrequency;
|
||||
|
||||
/**
|
||||
* See description for `maximumFileSize`
|
||||
*/
|
||||
@property (readwrite, assign, atomic) BOOL doNotReuseLogFiles;
|
||||
|
||||
/**
|
||||
* The DDLogFileManager instance can be used to retrieve the list of log files,
|
||||
* and configure the maximum number of archived log files to keep.
|
||||
*
|
||||
* @see DDLogFileManager.maximumNumberOfLogFiles
|
||||
**/
|
||||
@property (strong, nonatomic, readonly) id <OSSDDLogFileManager> logFileManager;
|
||||
|
||||
/**
|
||||
* When using a custom formatter you can set the `logMessage` method not to append
|
||||
* `\n` character after each output. This allows for some greater flexibility with
|
||||
* custom formatters. Default value is YES.
|
||||
**/
|
||||
@property (nonatomic, readwrite, assign) BOOL automaticallyAppendNewlineForCustomFormatters;
|
||||
|
||||
/**
|
||||
* You can optionally force the current log file to be rolled with this method.
|
||||
* CompletionBlock will be called on main queue.
|
||||
*/
|
||||
- (void)rollLogFileWithCompletionBlock:(void (^)(void))completionBlock NS_SWIFT_NAME(rollLogFile(withCompletion:));
|
||||
|
||||
/**
|
||||
* Method is deprecated.
|
||||
* @deprecated Use `rollLogFileWithCompletionBlock:` method instead.
|
||||
*/
|
||||
- (void)rollLogFile __attribute((deprecated));
|
||||
|
||||
// Inherited from DDAbstractLogger
|
||||
|
||||
// - (id <DDLogFormatter>)logFormatter;
|
||||
// - (void)setLogFormatter:(id <DDLogFormatter>)formatter;
|
||||
|
||||
/**
|
||||
* Returns the log file that should be used.
|
||||
* If there is an existing log file that is suitable,
|
||||
* within the constraints of `maximumFileSize` and `rollingFrequency`, then it is returned.
|
||||
*
|
||||
* Otherwise a new file is created and returned.
|
||||
**/
|
||||
@property (nonatomic, readonly, strong) OSSDDLogFileInfo *currentLogFileInfo;
|
||||
|
||||
@end
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
#pragma mark -
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
/**
|
||||
* `DDLogFileInfo` is a simple class that provides access to various file attributes.
|
||||
* It provides good performance as it only fetches the information if requested,
|
||||
* and it caches the information to prevent duplicate fetches.
|
||||
*
|
||||
* It was designed to provide quick snapshots of the current state of log files,
|
||||
* and to help sort log files in an array.
|
||||
*
|
||||
* This class does not monitor the files, or update it's cached attribute values if the file changes on disk.
|
||||
* This is not what the class was designed for.
|
||||
*
|
||||
* If you absolutely must get updated values,
|
||||
* you can invoke the reset method which will clear the cache.
|
||||
**/
|
||||
@interface OSSDDLogFileInfo : NSObject
|
||||
|
||||
@property (strong, nonatomic, readonly) NSString *filePath;
|
||||
@property (strong, nonatomic, readonly) NSString *fileName;
|
||||
|
||||
#if FOUNDATION_SWIFT_SDK_EPOCH_AT_LEAST(8)
|
||||
@property (strong, nonatomic, readonly) NSDictionary<NSFileAttributeKey, id> *fileAttributes;
|
||||
#else
|
||||
@property (strong, nonatomic, readonly) NSDictionary<NSString *, id> *fileAttributes;
|
||||
#endif
|
||||
|
||||
@property (strong, nonatomic, readonly) NSDate *creationDate;
|
||||
@property (strong, nonatomic, readonly) NSDate *modificationDate;
|
||||
|
||||
@property (nonatomic, readonly) unsigned long long fileSize;
|
||||
|
||||
@property (nonatomic, readonly) NSTimeInterval age;
|
||||
|
||||
@property (nonatomic, readwrite) BOOL isArchived;
|
||||
|
||||
+ (instancetype)logFileWithPath:(NSString *)filePath NS_SWIFT_UNAVAILABLE("Use init(filePath:)");
|
||||
|
||||
- (instancetype)init NS_UNAVAILABLE;
|
||||
- (instancetype)initWithFilePath:(NSString *)filePath NS_DESIGNATED_INITIALIZER;
|
||||
|
||||
- (void)reset;
|
||||
- (void)renameFile:(NSString *)newFileName NS_SWIFT_NAME(renameFile(to:));
|
||||
|
||||
#if TARGET_IPHONE_SIMULATOR
|
||||
|
||||
// So here's the situation.
|
||||
// Extended attributes are perfect for what we're trying to do here (marking files as archived).
|
||||
// This is exactly what extended attributes were designed for.
|
||||
//
|
||||
// But Apple screws us over on the simulator.
|
||||
// Everytime you build-and-go, they copy the application into a new folder on the hard drive,
|
||||
// and as part of the process they strip extended attributes from our log files.
|
||||
// Normally, a copy of a file preserves extended attributes.
|
||||
// So obviously Apple has gone to great lengths to piss us off.
|
||||
//
|
||||
// Thus we use a slightly different tactic for marking log files as archived in the simulator.
|
||||
// That way it "just works" and there's no confusion when testing.
|
||||
//
|
||||
// The difference in method names is indicative of the difference in functionality.
|
||||
// On the simulator we add an attribute by appending a filename extension.
|
||||
//
|
||||
// For example:
|
||||
// "mylog.txt" -> "mylog.archived.txt"
|
||||
// "mylog" -> "mylog.archived"
|
||||
|
||||
- (BOOL)hasExtensionAttributeWithName:(NSString *)attrName;
|
||||
|
||||
- (void)addExtensionAttributeWithName:(NSString *)attrName;
|
||||
- (void)removeExtensionAttributeWithName:(NSString *)attrName;
|
||||
|
||||
#else /* if TARGET_IPHONE_SIMULATOR */
|
||||
|
||||
// Normal use of extended attributes used everywhere else,
|
||||
// such as on Macs and on iPhone devices.
|
||||
|
||||
- (BOOL)hasExtendedAttributeWithName:(NSString *)attrName;
|
||||
|
||||
- (void)addExtendedAttributeWithName:(NSString *)attrName;
|
||||
- (void)removeExtendedAttributeWithName:(NSString *)attrName;
|
||||
|
||||
#endif /* if TARGET_IPHONE_SIMULATOR */
|
||||
|
||||
@end
|
||||
1460
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSFileLog/OSSFileLogger.m
generated
Normal file
1460
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSFileLog/OSSFileLogger.m
generated
Normal file
File diff suppressed because it is too large
Load Diff
82
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSFileLog/OSSLogMacros.h
generated
Normal file
82
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSFileLog/OSSLogMacros.h
generated
Normal file
@@ -0,0 +1,82 @@
|
||||
// Software License Agreement (BSD License)
|
||||
//
|
||||
// Copyright (c) 2010-2016, Deusty, LLC
|
||||
// All rights reserved.
|
||||
//
|
||||
// Redistribution and use of this software in source and binary forms,
|
||||
// with or without modification, are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistributions of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
//
|
||||
// * Neither the name of Deusty nor the names of its contributors may be used
|
||||
// to endorse or promote products derived from this software without specific
|
||||
// prior written permission of Deusty, LLC.
|
||||
|
||||
// Disable legacy macros
|
||||
#ifndef OSSDD_LEGACY_MACROS
|
||||
#define OSSDD_LEGACY_MACROS 0
|
||||
#endif
|
||||
|
||||
#import "OSSDDLog.h"
|
||||
|
||||
/**
|
||||
* The constant/variable/method responsible for controlling the current log level.
|
||||
**/
|
||||
#ifndef OSSLOG_LEVEL_DEF
|
||||
#define OSSLOG_LEVEL_DEF ossLogLevel
|
||||
#endif
|
||||
|
||||
/**
|
||||
* Whether async should be used by log messages, excluding error messages that are always sent sync.
|
||||
**/
|
||||
#ifndef OSSLOG_ASYNC_ENABLED
|
||||
#define OSSLOG_ASYNC_ENABLED YES
|
||||
#endif
|
||||
|
||||
/**
|
||||
* These are the two macros that all other macros below compile into.
|
||||
* These big multiline macros makes all the other macros easier to read.
|
||||
**/
|
||||
#define OSSLOG_MACRO(isAsynchronous, lvl, flg, ctx, atag, fnct, frmt, ...) \
|
||||
[OSSDDLog log : isAsynchronous \
|
||||
level : lvl \
|
||||
flag : flg \
|
||||
context : ctx \
|
||||
file : __FILE__ \
|
||||
function : fnct \
|
||||
line : __LINE__ \
|
||||
tag : atag \
|
||||
format : (frmt), ## __VA_ARGS__]
|
||||
|
||||
/**
|
||||
* Define version of the macro that only execute if the log level is above the threshold.
|
||||
* The compiled versions essentially look like this:
|
||||
*
|
||||
* if (logFlagForThisLogMsg & ddLogLevel) { execute log message }
|
||||
*
|
||||
* When LOG_LEVEL_DEF is defined as ddLogLevel.
|
||||
*
|
||||
* As shown further below, Lumberjack actually uses a bitmask as opposed to primitive log levels.
|
||||
* This allows for a great amount of flexibility and some pretty advanced fine grained logging techniques.
|
||||
*
|
||||
* Note that when compiler optimizations are enabled (as they are for your release builds),
|
||||
* the log messages above your logging threshold will automatically be compiled out.
|
||||
*
|
||||
* (If the compiler sees LOG_LEVEL_DEF/ddLogLevel declared as a constant, the compiler simply checks to see
|
||||
* if the 'if' statement would execute, and if not it strips it from the binary.)
|
||||
*
|
||||
* We also define shorthand versions for asynchronous and synchronous logging.
|
||||
**/
|
||||
#define OSSLOG_MAYBE(async, lvl, flg, ctx, tag, fnct, frmt, ...) \
|
||||
do { if(lvl & flg) OSSLOG_MACRO(async, lvl, flg, ctx, tag, fnct, frmt, ##__VA_ARGS__); } while(0)
|
||||
|
||||
/**
|
||||
* Ready to use log macros with no context or tag.
|
||||
**/
|
||||
#define OSSDDLogError(frmt, ...) OSSLOG_MAYBE(NO, OSSLOG_LEVEL_DEF, OSSDDLogFlagError, 0, nil, __PRETTY_FUNCTION__, frmt, ##__VA_ARGS__)
|
||||
#define OSSDDLogWarn(frmt, ...) OSSLOG_MAYBE(OSSLOG_ASYNC_ENABLED, OSSLOG_LEVEL_DEF, OSSDDLogFlagWarning, 0, nil, __PRETTY_FUNCTION__, frmt, ##__VA_ARGS__)
|
||||
#define OSSDDLogInfo(frmt, ...) OSSLOG_MAYBE(OSSLOG_ASYNC_ENABLED, OSSLOG_LEVEL_DEF, OSSDDLogFlagInfo, 0, nil, __PRETTY_FUNCTION__, frmt, ##__VA_ARGS__)
|
||||
#define OSSDDLogDebug(frmt, ...) OSSLOG_MAYBE(OSSLOG_ASYNC_ENABLED, OSSLOG_LEVEL_DEF, OSSDDLogFlagDebug, 0, nil, __PRETTY_FUNCTION__, frmt, ##__VA_ARGS__)
|
||||
#define OSSDDLogVerbose(frmt, ...) OSSLOG_MAYBE(OSSLOG_ASYNC_ENABLED, OSSLOG_LEVEL_DEF, OSSDDLogFlagVerbose, 0, nil, __PRETTY_FUNCTION__, frmt, ##__VA_ARGS__)
|
||||
|
||||
14
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSFileLog/OSSNSLogger.h
generated
Normal file
14
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSFileLog/OSSNSLogger.h
generated
Normal file
@@ -0,0 +1,14 @@
|
||||
//
|
||||
// OSSNSLogger.h
|
||||
// AliyunOSSiOS
|
||||
//
|
||||
// Created by jingdan on 2017/10/24.
|
||||
// Copyright © 2017年 zhouzhuo. All rights reserved.
|
||||
//
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
#import "OSSDDLog.h"
|
||||
|
||||
@interface OSSNSLogger : OSSDDAbstractLogger <OSSDDLogger>
|
||||
@property (class, readonly, strong) OSSNSLogger *sharedInstance;
|
||||
@end
|
||||
32
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSFileLog/OSSNSLogger.m
generated
Normal file
32
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSFileLog/OSSNSLogger.m
generated
Normal file
@@ -0,0 +1,32 @@
|
||||
//
|
||||
// OSSNSLogger.m
|
||||
// AliyunOSSiOS
|
||||
//
|
||||
// Created by jingdan on 2017/10/24.
|
||||
// Copyright © 2017年 zhouzhuo. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSNSLogger.h"
|
||||
|
||||
static OSSNSLogger *sharedInstance;
|
||||
|
||||
@implementation OSSNSLogger
|
||||
+ (instancetype)sharedInstance {
|
||||
static dispatch_once_t OSSNSLoggerOnceToken;
|
||||
|
||||
dispatch_once(&OSSNSLoggerOnceToken, ^{
|
||||
sharedInstance = [[[self class] alloc] init];
|
||||
});
|
||||
|
||||
return sharedInstance;
|
||||
}
|
||||
|
||||
- (void)logMessage:(OSSDDLogMessage *)logMessage {
|
||||
NSString * message = _logFormatter ? [_logFormatter formatLogMessage:logMessage] : logMessage->_message;
|
||||
|
||||
if (message) {
|
||||
NSLog(@"%@",message);
|
||||
}
|
||||
}
|
||||
|
||||
@end
|
||||
64
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSFileLog/OSSReachability.h
generated
Normal file
64
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSFileLog/OSSReachability.h
generated
Normal file
@@ -0,0 +1,64 @@
|
||||
/*
|
||||
Copyright (C) 2016 Apple Inc. All Rights Reserved.
|
||||
See LICENSE.txt for this sample’s licensing information
|
||||
|
||||
Abstract:
|
||||
Basic demonstration of how to use the SystemConfiguration Reachablity APIs.
|
||||
*/
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
#import <SystemConfiguration/SystemConfiguration.h>
|
||||
#import <netinet/in.h>
|
||||
|
||||
|
||||
typedef enum : NSInteger {
|
||||
OSSNotReachable = 0,
|
||||
OSSReachableViaWiFi,
|
||||
OSSReachableViaWWAN
|
||||
} OSSNetworkStatus;
|
||||
|
||||
#pragma mark IPv6 Support
|
||||
//Reachability fully support IPv6. For full details, see ReadMe.md.
|
||||
|
||||
|
||||
extern NSString *ossReachabilityChangedNotification;
|
||||
|
||||
|
||||
@interface OSSReachability : NSObject
|
||||
|
||||
/*!
|
||||
* Use to check the reachability of a given host name.
|
||||
*/
|
||||
+ (instancetype)reachabilityWithHostName:(NSString *)hostName;
|
||||
|
||||
/*!
|
||||
* Use to check the reachability of a given IP address.
|
||||
*/
|
||||
+ (instancetype)reachabilityWithAddress:(const struct sockaddr *)hostAddress;
|
||||
|
||||
/*!
|
||||
* Checks whether the default route is available. Should be used by applications that do not connect to a particular host.
|
||||
*/
|
||||
+ (instancetype)reachabilityForInternetConnection;
|
||||
|
||||
|
||||
#pragma mark reachabilityForLocalWiFi
|
||||
//reachabilityForLocalWiFi has been removed from the sample. See ReadMe.md for more information.
|
||||
//+ (instancetype)reachabilityForLocalWiFi;
|
||||
|
||||
/*!
|
||||
* Start listening for reachability notifications on the current run loop.
|
||||
*/
|
||||
- (BOOL)startNotifier;
|
||||
- (void)stopNotifier;
|
||||
|
||||
- (OSSNetworkStatus)currentReachabilityStatus;
|
||||
|
||||
/*!
|
||||
* WWAN may be available, but not active until a connection has been established. WiFi may require a connection for VPN on Demand.
|
||||
*/
|
||||
- (BOOL)connectionRequired;
|
||||
|
||||
@end
|
||||
|
||||
|
||||
248
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSFileLog/OSSReachability.m
generated
Normal file
248
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSFileLog/OSSReachability.m
generated
Normal file
@@ -0,0 +1,248 @@
|
||||
/*
|
||||
Copyright (C) 2016 Apple Inc. All Rights Reserved.
|
||||
See LICENSE.txt for this sample’s licensing information
|
||||
|
||||
Abstract:
|
||||
Basic demonstration of how to use the SystemConfiguration Reachablity APIs.
|
||||
*/
|
||||
|
||||
#import <arpa/inet.h>
|
||||
#import <ifaddrs.h>
|
||||
#import <netdb.h>
|
||||
#import <sys/socket.h>
|
||||
#import <netinet/in.h>
|
||||
#import <CoreFoundation/CoreFoundation.h>
|
||||
|
||||
#import "OSSReachability.h"
|
||||
|
||||
#pragma mark IPv6 Support
|
||||
//Reachability fully support IPv6. For full details, see ReadMe.md.
|
||||
|
||||
|
||||
NSString *ossReachabilityChangedNotification = @"ossNetworkReachabilityChangedNotification";
|
||||
|
||||
#ifndef kShouldPrintReachabilityFlags
|
||||
#if TARGET_OS_IOS
|
||||
#define kShouldPrintReachabilityFlags 1
|
||||
#else
|
||||
#define kShouldPrintReachabilityFlags 0
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#pragma mark - Supporting functions
|
||||
static void PrintReachabilityFlags(SCNetworkReachabilityFlags flags, const char* comment)
|
||||
{
|
||||
#if kShouldPrintReachabilityFlags
|
||||
|
||||
NSLog(@"Reachability Flag Status: %c%c %c%c%c%c%c%c%c %s\n",
|
||||
(flags & kSCNetworkReachabilityFlagsIsWWAN) ? 'W' : '-',
|
||||
(flags & kSCNetworkReachabilityFlagsReachable) ? 'R' : '-',
|
||||
|
||||
(flags & kSCNetworkReachabilityFlagsTransientConnection) ? 't' : '-',
|
||||
(flags & kSCNetworkReachabilityFlagsConnectionRequired) ? 'c' : '-',
|
||||
(flags & kSCNetworkReachabilityFlagsConnectionOnTraffic) ? 'C' : '-',
|
||||
(flags & kSCNetworkReachabilityFlagsInterventionRequired) ? 'i' : '-',
|
||||
(flags & kSCNetworkReachabilityFlagsConnectionOnDemand) ? 'D' : '-',
|
||||
(flags & kSCNetworkReachabilityFlagsIsLocalAddress) ? 'l' : '-',
|
||||
(flags & kSCNetworkReachabilityFlagsIsDirect) ? 'd' : '-',
|
||||
comment
|
||||
);
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
static void ReachabilityCallback(SCNetworkReachabilityRef target, SCNetworkReachabilityFlags flags, void* info)
|
||||
{
|
||||
#pragma unused (target, flags)
|
||||
NSCAssert(info != NULL, @"info was NULL in ReachabilityCallback");
|
||||
NSCAssert([(__bridge NSObject*) info isKindOfClass: [OSSReachability class]], @"info was wrong class in ReachabilityCallback");
|
||||
|
||||
OSSReachability* noteObject = (__bridge OSSReachability *)info;
|
||||
// Post a notification to notify the client that the network reachability changed.
|
||||
[[NSNotificationCenter defaultCenter] postNotificationName: ossReachabilityChangedNotification object: noteObject];
|
||||
}
|
||||
|
||||
|
||||
#pragma mark - Reachability implementation
|
||||
|
||||
@implementation OSSReachability
|
||||
{
|
||||
SCNetworkReachabilityRef _reachabilityRef;
|
||||
}
|
||||
|
||||
+ (instancetype)reachabilityWithHostName:(NSString *)hostName
|
||||
{
|
||||
OSSReachability* returnValue = NULL;
|
||||
SCNetworkReachabilityRef reachability = SCNetworkReachabilityCreateWithName(NULL, [hostName UTF8String]);
|
||||
if (reachability != NULL)
|
||||
{
|
||||
returnValue= [[self alloc] init];
|
||||
if (returnValue != NULL)
|
||||
{
|
||||
returnValue->_reachabilityRef = reachability;
|
||||
}
|
||||
else {
|
||||
CFRelease(reachability);
|
||||
}
|
||||
}
|
||||
return returnValue;
|
||||
}
|
||||
|
||||
|
||||
+ (instancetype)reachabilityWithAddress:(const struct sockaddr *)hostAddress
|
||||
{
|
||||
SCNetworkReachabilityRef reachability = SCNetworkReachabilityCreateWithAddress(kCFAllocatorDefault, hostAddress);
|
||||
|
||||
OSSReachability* returnValue = NULL;
|
||||
|
||||
if (reachability != NULL)
|
||||
{
|
||||
returnValue = [[self alloc] init];
|
||||
if (returnValue != NULL)
|
||||
{
|
||||
returnValue->_reachabilityRef = reachability;
|
||||
}
|
||||
else {
|
||||
CFRelease(reachability);
|
||||
}
|
||||
}
|
||||
return returnValue;
|
||||
}
|
||||
|
||||
|
||||
+ (instancetype)reachabilityForInternetConnection
|
||||
{
|
||||
struct sockaddr_in zeroAddress;
|
||||
bzero(&zeroAddress, sizeof(zeroAddress));
|
||||
zeroAddress.sin_len = sizeof(zeroAddress);
|
||||
zeroAddress.sin_family = AF_INET;
|
||||
|
||||
return [self reachabilityWithAddress: (const struct sockaddr *) &zeroAddress];
|
||||
}
|
||||
|
||||
#pragma mark reachabilityForLocalWiFi
|
||||
//reachabilityForLocalWiFi has been removed from the sample. See ReadMe.md for more information.
|
||||
//+ (instancetype)reachabilityForLocalWiFi
|
||||
|
||||
|
||||
|
||||
#pragma mark - Start and stop notifier
|
||||
|
||||
- (BOOL)startNotifier
|
||||
{
|
||||
BOOL returnValue = NO;
|
||||
SCNetworkReachabilityContext context = {0, (__bridge void *)(self), NULL, NULL, NULL};
|
||||
|
||||
if (SCNetworkReachabilitySetCallback(_reachabilityRef, ReachabilityCallback, &context))
|
||||
{
|
||||
if (SCNetworkReachabilityScheduleWithRunLoop(_reachabilityRef, CFRunLoopGetCurrent(), kCFRunLoopDefaultMode))
|
||||
{
|
||||
returnValue = YES;
|
||||
}
|
||||
}
|
||||
|
||||
return returnValue;
|
||||
}
|
||||
|
||||
|
||||
- (void)stopNotifier
|
||||
{
|
||||
if (_reachabilityRef != NULL)
|
||||
{
|
||||
SCNetworkReachabilityUnscheduleFromRunLoop(_reachabilityRef, CFRunLoopGetCurrent(), kCFRunLoopDefaultMode);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
- (void)dealloc
|
||||
{
|
||||
[self stopNotifier];
|
||||
if (_reachabilityRef != NULL)
|
||||
{
|
||||
CFRelease(_reachabilityRef);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
#pragma mark - Network Flag Handling
|
||||
|
||||
- (OSSNetworkStatus)networkStatusForFlags:(SCNetworkReachabilityFlags)flags
|
||||
{
|
||||
PrintReachabilityFlags(flags, "networkStatusForFlags");
|
||||
if ((flags & kSCNetworkReachabilityFlagsReachable) == 0)
|
||||
{
|
||||
// The target host is not reachable.
|
||||
return OSSNotReachable;
|
||||
}
|
||||
|
||||
OSSNetworkStatus returnValue = OSSNotReachable;
|
||||
|
||||
if ((flags & kSCNetworkReachabilityFlagsConnectionRequired) == 0)
|
||||
{
|
||||
/*
|
||||
If the target host is reachable and no connection is required then we'll assume (for now) that you're on Wi-Fi...
|
||||
*/
|
||||
returnValue = OSSReachableViaWiFi;
|
||||
}
|
||||
|
||||
if ((((flags & kSCNetworkReachabilityFlagsConnectionOnDemand ) != 0) ||
|
||||
(flags & kSCNetworkReachabilityFlagsConnectionOnTraffic) != 0))
|
||||
{
|
||||
/*
|
||||
... and the connection is on-demand (or on-traffic) if the calling application is using the CFSocketStream or higher APIs...
|
||||
*/
|
||||
|
||||
if ((flags & kSCNetworkReachabilityFlagsInterventionRequired) == 0)
|
||||
{
|
||||
/*
|
||||
... and no [user] intervention is needed...
|
||||
*/
|
||||
returnValue = OSSReachableViaWiFi;
|
||||
}
|
||||
}
|
||||
|
||||
#if TARGET_OS_IOS
|
||||
if ((flags & kSCNetworkReachabilityFlagsIsWWAN) == kSCNetworkReachabilityFlagsIsWWAN)
|
||||
{
|
||||
/*
|
||||
... but WWAN connections are OK if the calling application is using the CFNetwork APIs.
|
||||
*/
|
||||
returnValue = OSSReachableViaWWAN;
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
return returnValue;
|
||||
}
|
||||
|
||||
|
||||
- (BOOL)connectionRequired
|
||||
{
|
||||
NSAssert(_reachabilityRef != NULL, @"connectionRequired called with NULL reachabilityRef");
|
||||
SCNetworkReachabilityFlags flags;
|
||||
|
||||
if (SCNetworkReachabilityGetFlags(_reachabilityRef, &flags))
|
||||
{
|
||||
return (flags & kSCNetworkReachabilityFlagsConnectionRequired);
|
||||
}
|
||||
|
||||
return NO;
|
||||
}
|
||||
|
||||
|
||||
- (OSSNetworkStatus)currentReachabilityStatus
|
||||
{
|
||||
NSAssert(_reachabilityRef != NULL, @"currentOSSNetworkStatus called with NULL SCNetworkReachabilityRef");
|
||||
OSSNetworkStatus returnValue = OSSNotReachable;
|
||||
SCNetworkReachabilityFlags flags;
|
||||
|
||||
if (SCNetworkReachabilityGetFlags(_reachabilityRef, &flags))
|
||||
{
|
||||
returnValue = [self networkStatusForFlags:flags];
|
||||
}
|
||||
|
||||
return returnValue;
|
||||
}
|
||||
|
||||
|
||||
@end
|
||||
15
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetBucketInfoRequest.h
generated
Normal file
15
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetBucketInfoRequest.h
generated
Normal file
@@ -0,0 +1,15 @@
|
||||
//
|
||||
// OSSGetBucketInfoRequest.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/7/10.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSRequest.h"
|
||||
|
||||
@interface OSSGetBucketInfoRequest : OSSRequest
|
||||
|
||||
@property (nonatomic, copy) NSString *bucketName;
|
||||
|
||||
@end
|
||||
17
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetBucketInfoRequest.m
generated
Normal file
17
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetBucketInfoRequest.m
generated
Normal file
@@ -0,0 +1,17 @@
|
||||
//
|
||||
// OSSGetBucketInfoRequest.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/7/10.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSGetBucketInfoRequest.h"
|
||||
|
||||
@implementation OSSGetBucketInfoRequest
|
||||
|
||||
- (NSDictionary *)requestParams {
|
||||
return @{@"bucketInfo": @""};
|
||||
}
|
||||
|
||||
@end
|
||||
57
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetBucketInfoResult.h
generated
Normal file
57
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetBucketInfoResult.h
generated
Normal file
@@ -0,0 +1,57 @@
|
||||
//
|
||||
// OSSGetBucketInfoResult.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/7/10.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSResult.h"
|
||||
|
||||
@interface OSSBucketOwner : NSObject
|
||||
|
||||
@property (nonatomic, copy) NSString *userName;
|
||||
|
||||
@property (nonatomic, copy) NSString *userId;
|
||||
|
||||
@end
|
||||
|
||||
@interface OSSAccessControlList : NSObject
|
||||
|
||||
@property (nonatomic, copy) NSString *grant;
|
||||
|
||||
@end
|
||||
|
||||
|
||||
|
||||
@interface OSSGetBucketInfoResult : OSSResult
|
||||
|
||||
/// Created date.
|
||||
@property (nonatomic, copy) NSString *creationDate;
|
||||
|
||||
/// Bucket name.
|
||||
@property (nonatomic, copy) NSString *bucketName;
|
||||
|
||||
/// Bucket location.
|
||||
@property (nonatomic, copy) NSString *location;
|
||||
|
||||
/// Storage class (Standard, IA, Archive)
|
||||
@property (nonatomic, copy) NSString *storageClass;
|
||||
|
||||
/**
|
||||
Internal endpoint. It could be accessed within AliCloud under the same
|
||||
location.
|
||||
*/
|
||||
@property (nonatomic, copy) NSString *intranetEndpoint;
|
||||
|
||||
/**
|
||||
External endpoint.It could be accessed from anywhere.
|
||||
*/
|
||||
@property (nonatomic, copy) NSString *extranetEndpoint;
|
||||
|
||||
/// Bucket owner.
|
||||
@property (nonatomic, strong) OSSBucketOwner *owner;
|
||||
|
||||
@property (nonatomic, strong) OSSAccessControlList *acl;
|
||||
|
||||
@end
|
||||
23
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetBucketInfoResult.m
generated
Normal file
23
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetBucketInfoResult.m
generated
Normal file
@@ -0,0 +1,23 @@
|
||||
//
|
||||
// OSSGetBucketInfoResult.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/7/10.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSGetBucketInfoResult.h"
|
||||
|
||||
@implementation OSSBucketOwner
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSAccessControlList
|
||||
|
||||
@end
|
||||
|
||||
|
||||
|
||||
@implementation OSSGetBucketInfoResult
|
||||
|
||||
@end
|
||||
26
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetObjectACLRequest.h
generated
Normal file
26
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetObjectACLRequest.h
generated
Normal file
@@ -0,0 +1,26 @@
|
||||
//
|
||||
// OSSGetObjectACLRequest.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/1/26.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSRequest.h"
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
@interface OSSGetObjectACLRequest : OSSRequest
|
||||
|
||||
/**
|
||||
the bucket's name which object stored
|
||||
*/
|
||||
@property (nonatomic, copy) NSString *bucketName;
|
||||
|
||||
/**
|
||||
the name of object
|
||||
*/
|
||||
@property (nonatomic, copy) NSString *objectName;
|
||||
|
||||
|
||||
@end
|
||||
NS_ASSUME_NONNULL_END
|
||||
13
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetObjectACLRequest.m
generated
Normal file
13
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetObjectACLRequest.m
generated
Normal file
@@ -0,0 +1,13 @@
|
||||
//
|
||||
// OSSGetObjectACLRequest.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/1/26.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSGetObjectACLRequest.h"
|
||||
|
||||
@implementation OSSGetObjectACLRequest
|
||||
|
||||
@end
|
||||
19
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetObjectACLResult.h
generated
Normal file
19
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetObjectACLResult.h
generated
Normal file
@@ -0,0 +1,19 @@
|
||||
//
|
||||
// OSSGetObjectACLResult.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/1/26.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSResult.h"
|
||||
|
||||
@interface OSSGetObjectACLResult : OSSResult
|
||||
|
||||
/**
|
||||
the ACL of object,valid values: @"private",@"public-read",@"public-read-write".
|
||||
if object's ACL inherit from bucket,it will return @"default".
|
||||
*/
|
||||
@property (nonatomic, copy) NSString *grant;
|
||||
|
||||
@end
|
||||
13
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetObjectACLResult.m
generated
Normal file
13
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetObjectACLResult.m
generated
Normal file
@@ -0,0 +1,13 @@
|
||||
//
|
||||
// OSSGetObjectACLResult.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/1/26.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSGetObjectACLResult.h"
|
||||
|
||||
@implementation OSSGetObjectACLResult
|
||||
|
||||
@end
|
||||
23
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetObjectTaggingRequest.h
generated
Normal file
23
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetObjectTaggingRequest.h
generated
Normal file
@@ -0,0 +1,23 @@
|
||||
//
|
||||
// GetObjectTaggingRequest.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by ws on 2021/5/25.
|
||||
// Copyright © 2021 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSRequest.h"
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
@interface OSSGetObjectTaggingRequest : OSSRequest
|
||||
|
||||
/* bucket name */
|
||||
@property (nonatomic, copy) NSString *bucketName;
|
||||
|
||||
/* object name */
|
||||
@property (nonatomic, copy) NSString *objectKey;
|
||||
|
||||
@end
|
||||
|
||||
NS_ASSUME_NONNULL_END
|
||||
17
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetObjectTaggingRequest.m
generated
Normal file
17
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetObjectTaggingRequest.m
generated
Normal file
@@ -0,0 +1,17 @@
|
||||
//
|
||||
// GetObjectTaggingRequest.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by ws on 2021/5/25.
|
||||
// Copyright © 2021 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSGetObjectTaggingRequest.h"
|
||||
|
||||
@implementation OSSGetObjectTaggingRequest
|
||||
|
||||
- (NSDictionary *)requestParams {
|
||||
return @{@"tagging": @""};
|
||||
}
|
||||
|
||||
@end
|
||||
19
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetObjectTaggingResult.h
generated
Normal file
19
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetObjectTaggingResult.h
generated
Normal file
@@ -0,0 +1,19 @@
|
||||
//
|
||||
// GetObjectTaggingResult.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by ws on 2021/5/25.
|
||||
// Copyright © 2021 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSResult.h"
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
@interface OSSGetObjectTaggingResult : OSSResult
|
||||
|
||||
@property (nonatomic, strong) NSDictionary *tags;
|
||||
|
||||
@end
|
||||
|
||||
NS_ASSUME_NONNULL_END
|
||||
13
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetObjectTaggingResult.m
generated
Normal file
13
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetObjectTaggingResult.m
generated
Normal file
@@ -0,0 +1,13 @@
|
||||
//
|
||||
// GetObjectTaggingResult.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by ws on 2021/5/25.
|
||||
// Copyright © 2021 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSGetObjectTaggingResult.h"
|
||||
|
||||
@implementation OSSGetObjectTaggingResult
|
||||
|
||||
@end
|
||||
17
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetSymlinkRequest.h
generated
Normal file
17
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetSymlinkRequest.h
generated
Normal file
@@ -0,0 +1,17 @@
|
||||
//
|
||||
// OSSGetSymlinkRequest.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/8/1.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSRequest.h"
|
||||
|
||||
@interface OSSGetSymlinkRequest : OSSRequest
|
||||
|
||||
@property (nonatomic, copy) NSString *bucketName;
|
||||
|
||||
@property (nonatomic, copy) NSString *objectKey;
|
||||
|
||||
@end
|
||||
17
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetSymlinkRequest.m
generated
Normal file
17
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetSymlinkRequest.m
generated
Normal file
@@ -0,0 +1,17 @@
|
||||
//
|
||||
// OSSGetSymlinkRequest.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/8/1.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSGetSymlinkRequest.h"
|
||||
|
||||
@implementation OSSGetSymlinkRequest
|
||||
|
||||
- (NSDictionary *)requestParams {
|
||||
return @{@"symlink": @""};
|
||||
}
|
||||
|
||||
@end
|
||||
13
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetSymlinkResult.h
generated
Normal file
13
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetSymlinkResult.h
generated
Normal file
@@ -0,0 +1,13 @@
|
||||
//
|
||||
// OSSGetSymlinkResult.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/8/1.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSResult.h"
|
||||
|
||||
@interface OSSGetSymlinkResult : OSSResult
|
||||
|
||||
@end
|
||||
13
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetSymlinkResult.m
generated
Normal file
13
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSGetSymlinkResult.m
generated
Normal file
@@ -0,0 +1,13 @@
|
||||
//
|
||||
// OSSGetSymlinkResult.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/8/1.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSGetSymlinkResult.h"
|
||||
|
||||
@implementation OSSGetSymlinkResult
|
||||
|
||||
@end
|
||||
39
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSHttpResponseParser.h
generated
Normal file
39
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSHttpResponseParser.h
generated
Normal file
@@ -0,0 +1,39 @@
|
||||
//
|
||||
// OSSHttpResponseParser.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/1/22.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
#import "OSSConstants.h"
|
||||
#import "OSSTask.h"
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
/**
|
||||
HTTP response parser
|
||||
*/
|
||||
@interface OSSHttpResponseParser : NSObject
|
||||
|
||||
@property (nonatomic, copy) OSSNetworkingOnRecieveDataBlock onRecieveBlock;
|
||||
|
||||
@property (nonatomic, strong) NSURL *downloadingFileURL;
|
||||
|
||||
/**
|
||||
* A Boolean value that determines whether verfifying crc64.
|
||||
When set to YES, it will verify crc64 when transmission is completed normally.
|
||||
The default value of this property is NO.
|
||||
*/
|
||||
@property (nonatomic, assign) BOOL crc64Verifiable;
|
||||
|
||||
- (instancetype)initForOperationType:(OSSOperationType)operationType;
|
||||
- (void)consumeHttpResponse:(NSHTTPURLResponse *)response;
|
||||
- (OSSTask *)consumeHttpResponseBody:(NSData *)data;
|
||||
- (nullable id)constructResultObject;
|
||||
- (void)reset;
|
||||
|
||||
@end
|
||||
|
||||
NS_ASSUME_NONNULL_END
|
||||
704
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSHttpResponseParser.m
generated
Normal file
704
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSHttpResponseParser.m
generated
Normal file
@@ -0,0 +1,704 @@
|
||||
//
|
||||
// OSSHttpResponseParser.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/1/22.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSHttpResponseParser.h"
|
||||
|
||||
#import "NSMutableData+OSS_CRC.h"
|
||||
#import "OSSXMLDictionary.h"
|
||||
#import "OSSDefine.h"
|
||||
#import "OSSModel.h"
|
||||
#import "OSSUtil.h"
|
||||
#import "OSSLog.h"
|
||||
#import "OSSGetObjectACLResult.h"
|
||||
#import "OSSDeleteMultipleObjectsResult.h"
|
||||
#import "OSSGetBucketInfoResult.h"
|
||||
#import "OSSRestoreObjectResult.h"
|
||||
#import "OSSPutSymlinkResult.h"
|
||||
#import "OSSGetSymlinkResult.h"
|
||||
#import "OSSGetObjectTaggingResult.h"
|
||||
#import "OSSPutObjectTaggingResult.h"
|
||||
#import "OSSDeleteObjectTaggingResult.h"
|
||||
|
||||
|
||||
@implementation OSSHttpResponseParser {
|
||||
|
||||
OSSOperationType _operationTypeForThisParser;
|
||||
|
||||
NSFileHandle * _fileHandle;
|
||||
NSMutableData * _collectingData;
|
||||
NSHTTPURLResponse * _response;
|
||||
uint64_t _crc64ecma;
|
||||
}
|
||||
|
||||
- (void)reset {
|
||||
_collectingData = nil;
|
||||
_fileHandle = nil;
|
||||
_response = nil;
|
||||
}
|
||||
|
||||
- (instancetype)initForOperationType:(OSSOperationType)operationType {
|
||||
if (self = [super init]) {
|
||||
_operationTypeForThisParser = operationType;
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
- (void)consumeHttpResponse:(NSHTTPURLResponse *)response {
|
||||
_response = response;
|
||||
}
|
||||
|
||||
- (OSSTask *)consumeHttpResponseBody:(NSData *)data
|
||||
{
|
||||
if (_crc64Verifiable&&(_operationTypeForThisParser == OSSOperationTypeGetObject))
|
||||
{
|
||||
NSMutableData *mutableData = [NSMutableData dataWithData:data];
|
||||
if (_crc64ecma != 0)
|
||||
{
|
||||
_crc64ecma = [OSSUtil crc64ForCombineCRC1:_crc64ecma
|
||||
CRC2:[mutableData oss_crc64]
|
||||
length:mutableData.length];
|
||||
}else
|
||||
{
|
||||
_crc64ecma = [mutableData oss_crc64];
|
||||
}
|
||||
}
|
||||
|
||||
if (self.onRecieveBlock) {
|
||||
self.onRecieveBlock(data);
|
||||
return [OSSTask taskWithResult:nil];
|
||||
}
|
||||
|
||||
NSError * error;
|
||||
if (self.downloadingFileURL)
|
||||
{
|
||||
if (!_fileHandle)
|
||||
{
|
||||
NSFileManager * fm = [NSFileManager defaultManager];
|
||||
NSString * dirName = [[self.downloadingFileURL path] stringByDeletingLastPathComponent];
|
||||
if (![fm fileExistsAtPath:dirName])
|
||||
{
|
||||
[fm createDirectoryAtPath:dirName withIntermediateDirectories:YES attributes:nil error:&error];
|
||||
}
|
||||
if (![fm fileExistsAtPath:dirName] || error)
|
||||
{
|
||||
return [OSSTask taskWithError:[NSError errorWithDomain:OSSClientErrorDomain
|
||||
code:OSSClientErrorCodeFileCantWrite
|
||||
userInfo:@{OSSErrorMessageTOKEN: [NSString stringWithFormat:@"Can't create dir at %@", dirName]}]];
|
||||
}
|
||||
[fm createFileAtPath:[self.downloadingFileURL path] contents:nil attributes:nil];
|
||||
if (![fm fileExistsAtPath:[self.downloadingFileURL path]])
|
||||
{
|
||||
return [OSSTask taskWithError:[NSError errorWithDomain:OSSClientErrorDomain
|
||||
code:OSSClientErrorCodeFileCantWrite
|
||||
userInfo:@{OSSErrorMessageTOKEN: [NSString stringWithFormat:@"Can't create file at %@", [self.downloadingFileURL path]]}]];
|
||||
}
|
||||
_fileHandle = [NSFileHandle fileHandleForWritingToURL:self.downloadingFileURL error:&error];
|
||||
if (error)
|
||||
{
|
||||
return [OSSTask taskWithError:[NSError errorWithDomain:OSSClientErrorDomain
|
||||
code:OSSClientErrorCodeFileCantWrite
|
||||
userInfo:[error userInfo]]];
|
||||
}
|
||||
[_fileHandle writeData:data];
|
||||
} else
|
||||
{
|
||||
@try {
|
||||
[_fileHandle writeData:data];
|
||||
}
|
||||
@catch (NSException *exception) {
|
||||
return [OSSTask taskWithError:[NSError errorWithDomain:OSSServerErrorDomain
|
||||
code:OSSClientErrorCodeFileCantWrite
|
||||
userInfo:@{OSSErrorMessageTOKEN: [exception description]}]];
|
||||
}
|
||||
}
|
||||
} else
|
||||
{
|
||||
if (!_collectingData)
|
||||
{
|
||||
_collectingData = [[NSMutableData alloc] initWithData:data];
|
||||
}
|
||||
else
|
||||
{
|
||||
[_collectingData appendData:data];
|
||||
}
|
||||
}
|
||||
return [OSSTask taskWithResult:nil];
|
||||
}
|
||||
|
||||
- (void)parseResponseHeader:(NSHTTPURLResponse *)response toResultObject:(OSSResult *)result
|
||||
{
|
||||
result.httpResponseCode = [_response statusCode];
|
||||
result.httpResponseHeaderFields = [NSDictionary dictionaryWithDictionary:[_response allHeaderFields]];
|
||||
[[_response allHeaderFields] enumerateKeysAndObjectsUsingBlock:^(id key, id obj, BOOL *stop) {
|
||||
NSString * keyString = (NSString *)key;
|
||||
if ([keyString isEqualToString:@"x-oss-request-id"])
|
||||
{
|
||||
result.requestId = obj;
|
||||
}
|
||||
else if ([keyString isEqualToString:@"x-oss-hash-crc64ecma"])
|
||||
{
|
||||
result.remoteCRC64ecma = obj;
|
||||
}
|
||||
}];
|
||||
}
|
||||
|
||||
- (NSDictionary *)parseResponseHeaderToGetMeta:(NSHTTPURLResponse *)response
|
||||
{
|
||||
NSMutableDictionary * meta = [NSMutableDictionary new];
|
||||
|
||||
/* define a constant array to contain all meta header name */
|
||||
static NSArray * OSSObjectMetaFieldNames = nil;
|
||||
static dispatch_once_t onceToken;
|
||||
dispatch_once(&onceToken, ^{
|
||||
OSSObjectMetaFieldNames = @[@"Content-Type", @"Content-Length", @"Etag", @"Last-Modified", @"x-oss-request-id", @"x-oss-object-type",
|
||||
@"If-Modified-Since", @"If-Unmodified-Since", @"If-Match", @"If-None-Match"];
|
||||
});
|
||||
/****************************************************************/
|
||||
|
||||
[[_response allHeaderFields] enumerateKeysAndObjectsUsingBlock:^(id key, id obj, BOOL *stop) {
|
||||
NSString * keyString = (NSString *)key;
|
||||
if ([OSSObjectMetaFieldNames containsObject:keyString] || [keyString hasPrefix:@"x-oss-meta"]) {
|
||||
[meta setObject:obj forKey:key];
|
||||
}
|
||||
}];
|
||||
return meta;
|
||||
}
|
||||
|
||||
- (nullable id)constructResultObject
|
||||
{
|
||||
if (self.onRecieveBlock)
|
||||
{
|
||||
return nil;
|
||||
}
|
||||
|
||||
switch (_operationTypeForThisParser)
|
||||
{
|
||||
case OSSOperationTypeGetService:
|
||||
{
|
||||
OSSGetServiceResult * getServiceResult = [OSSGetServiceResult new];
|
||||
if (_response)
|
||||
{
|
||||
[self parseResponseHeader:_response toResultObject:getServiceResult];
|
||||
}
|
||||
if (_collectingData)
|
||||
{
|
||||
NSDictionary * parseDict = [NSDictionary oss_dictionaryWithXMLData:_collectingData];
|
||||
OSSLogVerbose(@"Get service dict: %@", parseDict);
|
||||
if (parseDict)
|
||||
{
|
||||
getServiceResult.ownerId = [[parseDict objectForKey:OSSOwnerXMLTOKEN] objectForKey:OSSIDXMLTOKEN];
|
||||
getServiceResult.ownerDispName = [[parseDict objectForKey:OSSOwnerXMLTOKEN] objectForKey:OSSDisplayNameXMLTOKEN];
|
||||
getServiceResult.prefix = [parseDict objectForKey:OSSPrefixXMLTOKEN];
|
||||
getServiceResult.marker = [parseDict objectForKey:OSSMarkerXMLTOKEN];
|
||||
getServiceResult.maxKeys = [[parseDict objectForKey:OSSMaxKeysXMLTOKEN] intValue];
|
||||
getServiceResult.isTruncated = [[parseDict objectForKey:OSSIsTruncatedXMLTOKEN] boolValue];
|
||||
getServiceResult.nextMarker = [parseDict objectForKey:OSSNextMarkerXMLTOKEN];
|
||||
|
||||
id bucketObject = [[parseDict objectForKey:OSSBucketsXMLTOKEN] objectForKey:OSSBucketXMLTOKEN];
|
||||
if ([bucketObject isKindOfClass:[NSArray class]]) {
|
||||
getServiceResult.buckets = bucketObject;
|
||||
} else if ([bucketObject isKindOfClass:[NSDictionary class]]) {
|
||||
NSArray * arr = [NSArray arrayWithObject:bucketObject];
|
||||
getServiceResult.buckets = arr;
|
||||
} else {
|
||||
getServiceResult.buckets = nil;
|
||||
}
|
||||
}
|
||||
}
|
||||
return getServiceResult;
|
||||
}
|
||||
|
||||
case OSSOperationTypeCreateBucket:
|
||||
{
|
||||
OSSCreateBucketResult * createBucketResult = [OSSCreateBucketResult new];
|
||||
if (_response)
|
||||
{
|
||||
[self parseResponseHeader:_response toResultObject:createBucketResult];
|
||||
[_response.allHeaderFields enumerateKeysAndObjectsUsingBlock:^(id key, id obj, BOOL *stop) {
|
||||
if ([((NSString *)key) isEqualToString:@"Location"]) {
|
||||
createBucketResult.location = obj;
|
||||
*stop = YES;
|
||||
}
|
||||
}];
|
||||
}
|
||||
return createBucketResult;
|
||||
}
|
||||
|
||||
case OSSOperationTypeGetBucketACL:
|
||||
{
|
||||
OSSGetBucketACLResult * getBucketACLResult = [OSSGetBucketACLResult new];
|
||||
if (_response)
|
||||
{
|
||||
[self parseResponseHeader:_response toResultObject:getBucketACLResult];
|
||||
}
|
||||
if (_collectingData)
|
||||
{
|
||||
NSDictionary * parseDict = [NSDictionary oss_dictionaryWithXMLData:_collectingData];
|
||||
OSSLogVerbose(@"Get service dict: %@", parseDict);
|
||||
if (parseDict)
|
||||
{
|
||||
getBucketACLResult.aclGranted = [[parseDict objectForKey:OSSAccessControlListXMLTOKEN] objectForKey:OSSGrantXMLTOKEN];
|
||||
}
|
||||
}
|
||||
return getBucketACLResult;
|
||||
}
|
||||
|
||||
case OSSOperationTypeDeleteBucket:
|
||||
{
|
||||
OSSDeleteBucketResult * deleteBucketResult = [OSSDeleteBucketResult new];
|
||||
if (_response) {
|
||||
[self parseResponseHeader:_response toResultObject:deleteBucketResult];
|
||||
}
|
||||
return deleteBucketResult;
|
||||
}
|
||||
|
||||
case OSSOperationTypeGetBucket:
|
||||
{
|
||||
OSSGetBucketResult * getBucketResult = [OSSGetBucketResult new];
|
||||
if (_response) {
|
||||
[self parseResponseHeader:_response toResultObject:getBucketResult];
|
||||
}
|
||||
if (_collectingData) {
|
||||
NSDictionary * parsedDict = [NSDictionary oss_dictionaryWithXMLData:_collectingData];
|
||||
OSSLogVerbose(@"Get bucket dict: %@", parsedDict);
|
||||
|
||||
if (parsedDict) {
|
||||
getBucketResult.bucketName = [parsedDict objectForKey:OSSNameXMLTOKEN];
|
||||
getBucketResult.prefix = [parsedDict objectForKey:OSSPrefixXMLTOKEN];
|
||||
getBucketResult.marker = [parsedDict objectForKey:OSSMarkerXMLTOKEN];
|
||||
getBucketResult.nextMarker = [parsedDict objectForKey:OSSNextMarkerXMLTOKEN];
|
||||
getBucketResult.maxKeys = (int32_t)[[parsedDict objectForKey:OSSMaxKeysXMLTOKEN] integerValue];
|
||||
getBucketResult.delimiter = [parsedDict objectForKey:OSSDelimiterXMLTOKEN];
|
||||
getBucketResult.isTruncated = [[parsedDict objectForKey:OSSIsTruncatedXMLTOKEN] boolValue];
|
||||
|
||||
id contentObject = [parsedDict objectForKey:OSSContentsXMLTOKEN];
|
||||
if ([contentObject isKindOfClass:[NSArray class]]) {
|
||||
getBucketResult.contents = contentObject;
|
||||
} else if ([contentObject isKindOfClass:[NSDictionary class]]) {
|
||||
NSArray * arr = [NSArray arrayWithObject:contentObject];
|
||||
getBucketResult.contents = arr;
|
||||
} else {
|
||||
getBucketResult.contents = nil;
|
||||
}
|
||||
|
||||
NSMutableArray * commentPrefixesArr = [NSMutableArray new];
|
||||
id commentPrefixes = [parsedDict objectForKey:OSSCommonPrefixesXMLTOKEN];
|
||||
if ([commentPrefixes isKindOfClass:[NSArray class]]) {
|
||||
for (NSDictionary * prefix in commentPrefixes) {
|
||||
[commentPrefixesArr addObject:[prefix objectForKey:@"Prefix"]];
|
||||
}
|
||||
} else if ([commentPrefixes isKindOfClass:[NSDictionary class]]) {
|
||||
[commentPrefixesArr addObject:[(NSDictionary *)commentPrefixes objectForKey:@"Prefix"]];
|
||||
} else {
|
||||
commentPrefixesArr = nil;
|
||||
}
|
||||
|
||||
getBucketResult.commentPrefixes = commentPrefixesArr;
|
||||
}
|
||||
}
|
||||
return getBucketResult;
|
||||
}
|
||||
|
||||
case OSSOperationTypeListMultipartUploads:
|
||||
{
|
||||
OSSListMultipartUploadsResult * listMultipartUploadsResult = [OSSListMultipartUploadsResult new];
|
||||
if (_response) {
|
||||
[self parseResponseHeader:_response toResultObject:listMultipartUploadsResult];
|
||||
}
|
||||
if (_collectingData) {
|
||||
NSDictionary * parsedDict = [NSDictionary oss_dictionaryWithXMLData:_collectingData];
|
||||
OSSLogVerbose(@"List multipart uploads dict: %@", parsedDict);
|
||||
|
||||
if (parsedDict) {
|
||||
listMultipartUploadsResult.bucketName = [parsedDict objectForKey:OSSBucketXMLTOKEN];
|
||||
listMultipartUploadsResult.prefix = [parsedDict objectForKey:OSSPrefixXMLTOKEN];
|
||||
listMultipartUploadsResult.uploadIdMarker = [parsedDict objectForKey:OSSUploadIdMarkerXMLTOKEN];
|
||||
listMultipartUploadsResult.nextUploadIdMarker = [parsedDict objectForKey:OSSUploadIdMarkerXMLTOKEN];
|
||||
listMultipartUploadsResult.keyMarker = [parsedDict objectForKey:OSSKeyMarkerXMLTOKEN];
|
||||
listMultipartUploadsResult.nextKeyMarker = [parsedDict objectForKey:OSSNextKeyMarkerXMLTOKEN];
|
||||
listMultipartUploadsResult.maxUploads = (int32_t)[[parsedDict objectForKey:OSSMaxUploadsXMLTOKEN] integerValue];
|
||||
listMultipartUploadsResult.delimiter = [parsedDict objectForKey:OSSDelimiterXMLTOKEN];
|
||||
listMultipartUploadsResult.isTruncated = [[parsedDict objectForKey:OSSIsTruncatedXMLTOKEN] boolValue];
|
||||
|
||||
id contentObject = [parsedDict objectForKey:OSSUploadXMLTOKEN];
|
||||
if ([contentObject isKindOfClass:[NSArray class]]) {
|
||||
listMultipartUploadsResult.uploads = contentObject;
|
||||
} else if ([contentObject isKindOfClass:[NSDictionary class]]) {
|
||||
NSArray * arr = [NSArray arrayWithObject:contentObject];
|
||||
listMultipartUploadsResult.uploads = arr;
|
||||
} else {
|
||||
listMultipartUploadsResult.uploads = nil;
|
||||
}
|
||||
|
||||
NSMutableArray * commentPrefixesArr = [NSMutableArray new];
|
||||
id commentPrefixes = [parsedDict objectForKey:OSSCommonPrefixesXMLTOKEN];
|
||||
if ([commentPrefixes isKindOfClass:[NSArray class]]) {
|
||||
for (NSDictionary * prefix in commentPrefixes) {
|
||||
[commentPrefixesArr addObject:[prefix objectForKey:@"Prefix"]];
|
||||
}
|
||||
} else if ([commentPrefixes isKindOfClass:[NSDictionary class]]) {
|
||||
[commentPrefixesArr addObject:[(NSDictionary *)commentPrefixes objectForKey:@"Prefix"]];
|
||||
} else {
|
||||
commentPrefixesArr = nil;
|
||||
}
|
||||
|
||||
listMultipartUploadsResult.commonPrefixes = commentPrefixesArr;
|
||||
}
|
||||
}
|
||||
return listMultipartUploadsResult;
|
||||
}
|
||||
|
||||
case OSSOperationTypeHeadObject:
|
||||
{
|
||||
OSSHeadObjectResult * headObjectResult = [OSSHeadObjectResult new];
|
||||
if (_response)
|
||||
{
|
||||
[self parseResponseHeader:_response toResultObject:headObjectResult];
|
||||
headObjectResult.objectMeta = [self parseResponseHeaderToGetMeta:_response];
|
||||
}
|
||||
return headObjectResult;
|
||||
}
|
||||
|
||||
case OSSOperationTypeGetObject:
|
||||
{
|
||||
OSSGetObjectResult * getObejctResult = [OSSGetObjectResult new];
|
||||
OSSLogDebug(@"GetObjectResponse: %@", _response);
|
||||
if (_response)
|
||||
{
|
||||
[self parseResponseHeader:_response toResultObject:getObejctResult];
|
||||
getObejctResult.objectMeta = [self parseResponseHeaderToGetMeta:_response];
|
||||
if (_crc64ecma != 0)
|
||||
{
|
||||
getObejctResult.localCRC64ecma = [NSString stringWithFormat:@"%llu",_crc64ecma];
|
||||
}
|
||||
}
|
||||
if (_fileHandle) {
|
||||
[_fileHandle closeFile];
|
||||
}
|
||||
|
||||
if (_collectingData) {
|
||||
getObejctResult.downloadedData = _collectingData;
|
||||
}
|
||||
return getObejctResult;
|
||||
}
|
||||
case OSSOperationTypeGetObjectACL:
|
||||
{
|
||||
OSSGetObjectACLResult * getObjectACLResult = [OSSGetObjectACLResult new];
|
||||
OSSLogDebug(@"GetObjectResponse: %@", _response);
|
||||
if (_response)
|
||||
{
|
||||
[self parseResponseHeader:_response toResultObject:getObjectACLResult];
|
||||
}
|
||||
|
||||
if (_collectingData) {
|
||||
NSDictionary * parseDict = [NSDictionary oss_dictionaryWithXMLData:_collectingData];
|
||||
OSSLogVerbose(@"Get service dict: %@", parseDict);
|
||||
getObjectACLResult.grant = parseDict[@"AccessControlList"][@"Grant"];
|
||||
}
|
||||
|
||||
|
||||
return getObjectACLResult;
|
||||
}
|
||||
|
||||
case OSSOperationTypePutObject:
|
||||
{
|
||||
OSSPutObjectResult * putObjectResult = [OSSPutObjectResult new];
|
||||
if (_response)
|
||||
{
|
||||
[self parseResponseHeader:_response toResultObject:putObjectResult];
|
||||
[_response.allHeaderFields enumerateKeysAndObjectsUsingBlock:^(id key, id obj, BOOL *stop) {
|
||||
if ([((NSString *)key) isEqualToString:@"Etag"]) {
|
||||
putObjectResult.eTag = obj;
|
||||
*stop = YES;
|
||||
}
|
||||
}];
|
||||
}
|
||||
if (_collectingData) {
|
||||
putObjectResult.serverReturnJsonString = [[NSString alloc] initWithData:_collectingData encoding:NSUTF8StringEncoding];
|
||||
}
|
||||
return putObjectResult;
|
||||
}
|
||||
|
||||
case OSSOperationTypeAppendObject:
|
||||
{
|
||||
OSSAppendObjectResult * appendObjectResult = [OSSAppendObjectResult new];
|
||||
if (_response) {
|
||||
[self parseResponseHeader:_response toResultObject:appendObjectResult];
|
||||
[_response.allHeaderFields enumerateKeysAndObjectsUsingBlock:^(id key, id obj, BOOL *stop) {
|
||||
if ([((NSString *)key) isEqualToString:@"Etag"]) {
|
||||
appendObjectResult.eTag = obj;
|
||||
}
|
||||
if ([((NSString *)key) isEqualToString:@"x-oss-next-append-position"]) {
|
||||
appendObjectResult.xOssNextAppendPosition = [((NSString *)obj) longLongValue];
|
||||
}
|
||||
}];
|
||||
}
|
||||
return appendObjectResult;
|
||||
}
|
||||
|
||||
case OSSOperationTypeDeleteObject: {
|
||||
OSSDeleteObjectResult * deleteObjectResult = [OSSDeleteObjectResult new];
|
||||
if (_response) {
|
||||
[self parseResponseHeader:_response toResultObject:deleteObjectResult];
|
||||
}
|
||||
return deleteObjectResult;
|
||||
}
|
||||
case OSSOperationTypeDeleteMultipleObjects: {
|
||||
OSSDeleteMultipleObjectsResult * deleteObjectResult = [OSSDeleteMultipleObjectsResult new];
|
||||
if (_response) {
|
||||
[self parseResponseHeader:_response toResultObject:deleteObjectResult];
|
||||
}
|
||||
|
||||
if (_collectingData) {
|
||||
NSDictionary *dict = [NSDictionary oss_dictionaryWithXMLData:_collectingData];
|
||||
deleteObjectResult.encodingType = dict[@"EncodingType"];
|
||||
deleteObjectResult.deletedObjects = dict[@"Deleted"];
|
||||
}
|
||||
|
||||
return deleteObjectResult;
|
||||
}
|
||||
case OSSOperationTypePutObjectACL: {
|
||||
OSSPutObjectACLResult * putObjectACLResult = [OSSPutObjectACLResult new];
|
||||
if (_response) {
|
||||
[self parseResponseHeader:_response toResultObject:putObjectACLResult];
|
||||
}
|
||||
return putObjectACLResult;
|
||||
}
|
||||
|
||||
case OSSOperationTypeCopyObject: {
|
||||
OSSCopyObjectResult * copyObjectResult = [OSSCopyObjectResult new];
|
||||
if (_response) {
|
||||
[self parseResponseHeader:_response toResultObject:copyObjectResult];
|
||||
}
|
||||
if (_collectingData) {
|
||||
OSSLogVerbose(@"copy object dict: %@", [NSDictionary oss_dictionaryWithXMLData:_collectingData]);
|
||||
NSDictionary * parsedDict = [NSDictionary oss_dictionaryWithXMLData:_collectingData];
|
||||
if (parsedDict) {
|
||||
copyObjectResult.lastModifed = [parsedDict objectForKey:OSSLastModifiedXMLTOKEN];
|
||||
copyObjectResult.eTag = [parsedDict objectForKey:OSSETagXMLTOKEN];
|
||||
}
|
||||
}
|
||||
return copyObjectResult;
|
||||
}
|
||||
|
||||
case OSSOperationTypeInitMultipartUpload: {
|
||||
OSSInitMultipartUploadResult * initMultipartUploadResult = [OSSInitMultipartUploadResult new];
|
||||
if (_response) {
|
||||
[self parseResponseHeader:_response toResultObject:initMultipartUploadResult];
|
||||
}
|
||||
if (_collectingData) {
|
||||
NSDictionary * parsedDict = [NSDictionary oss_dictionaryWithXMLData:_collectingData];
|
||||
OSSLogVerbose(@"init multipart upload result: %@", parsedDict);
|
||||
if (parsedDict) {
|
||||
initMultipartUploadResult.uploadId = [parsedDict objectForKey:OSSUploadIdXMLTOKEN];
|
||||
}
|
||||
}
|
||||
return initMultipartUploadResult;
|
||||
}
|
||||
|
||||
case OSSOperationTypeUploadPart: {
|
||||
OSSUploadPartResult * uploadPartResult = [OSSUploadPartResult new];
|
||||
if (_response) {
|
||||
[self parseResponseHeader:_response toResultObject:uploadPartResult];
|
||||
[_response.allHeaderFields enumerateKeysAndObjectsUsingBlock:^(id key, id obj, BOOL *stop) {
|
||||
if ([((NSString *)key) isEqualToString:@"Etag"]) {
|
||||
uploadPartResult.eTag = obj;
|
||||
*stop = YES;
|
||||
}
|
||||
}];
|
||||
}
|
||||
return uploadPartResult;
|
||||
}
|
||||
|
||||
case OSSOperationTypeCompleteMultipartUpload: {
|
||||
OSSCompleteMultipartUploadResult * completeMultipartUploadResult = [OSSCompleteMultipartUploadResult new];
|
||||
if (_response) {
|
||||
[self parseResponseHeader:_response toResultObject:completeMultipartUploadResult];
|
||||
}
|
||||
if (_collectingData) {
|
||||
if ([[[_response.allHeaderFields objectForKey:OSSHttpHeaderContentType] description] isEqual:@"application/xml"]) {
|
||||
OSSLogVerbose(@"complete multipart upload result: %@", [NSDictionary oss_dictionaryWithXMLData:_collectingData]);
|
||||
NSDictionary * parsedDict = [NSDictionary oss_dictionaryWithXMLData:_collectingData];
|
||||
if (parsedDict) {
|
||||
completeMultipartUploadResult.location = [parsedDict objectForKey:OSSLocationXMLTOKEN];
|
||||
completeMultipartUploadResult.eTag = [parsedDict objectForKey:OSSETagXMLTOKEN];
|
||||
}
|
||||
} else {
|
||||
completeMultipartUploadResult.serverReturnJsonString = [[NSString alloc] initWithData:_collectingData encoding:NSUTF8StringEncoding];
|
||||
}
|
||||
}
|
||||
return completeMultipartUploadResult;
|
||||
}
|
||||
|
||||
case OSSOperationTypeListMultipart: {
|
||||
OSSListPartsResult * listPartsReuslt = [OSSListPartsResult new];
|
||||
if (_response) {
|
||||
[self parseResponseHeader:_response toResultObject:listPartsReuslt];
|
||||
}
|
||||
if (_collectingData) {
|
||||
NSDictionary * parsedDict = [NSDictionary oss_dictionaryWithXMLData:_collectingData];
|
||||
OSSLogVerbose(@"list multipart upload result: %@", parsedDict);
|
||||
if (parsedDict) {
|
||||
listPartsReuslt.nextPartNumberMarker = [[parsedDict objectForKey:OSSNextPartNumberMarkerXMLTOKEN] intValue];
|
||||
listPartsReuslt.maxParts = [[parsedDict objectForKey:OSSMaxPartsXMLTOKEN] intValue];
|
||||
listPartsReuslt.isTruncated = [[parsedDict objectForKey:OSSIsTruncatedXMLTOKEN] boolValue];
|
||||
|
||||
id partsObject = [parsedDict objectForKey:OSSPartXMLTOKEN];
|
||||
if ([partsObject isKindOfClass:[NSArray class]]) {
|
||||
listPartsReuslt.parts = partsObject;
|
||||
} else if ([partsObject isKindOfClass:[NSDictionary class]]) {
|
||||
NSArray * arr = [NSArray arrayWithObject:partsObject];
|
||||
listPartsReuslt.parts = arr;
|
||||
} else {
|
||||
listPartsReuslt.parts = nil;
|
||||
}
|
||||
}
|
||||
}
|
||||
return listPartsReuslt;
|
||||
}
|
||||
|
||||
case OSSOperationTypeAbortMultipartUpload: {
|
||||
OSSAbortMultipartUploadResult * abortMultipartUploadResult = [OSSAbortMultipartUploadResult new];
|
||||
if (_response) {
|
||||
[self parseResponseHeader:_response toResultObject:abortMultipartUploadResult];
|
||||
}
|
||||
return abortMultipartUploadResult;
|
||||
}
|
||||
case OSSOperationTypeTriggerCallBack: {
|
||||
OSSCallBackResult *callbackResult = [OSSCallBackResult new];
|
||||
if (_response) {
|
||||
[self parseResponseHeader:_response toResultObject:callbackResult];
|
||||
}
|
||||
|
||||
if (_collectingData) {
|
||||
if ([[[_response.allHeaderFields objectForKey:OSSHttpHeaderContentType] description] isEqual:@"application/xml"]) {
|
||||
NSDictionary * parsedDict = [NSDictionary oss_dictionaryWithXMLData:_collectingData];
|
||||
OSSLogVerbose(@"callback trigger result<xml>: %@", parsedDict);
|
||||
callbackResult.serverReturnXML = parsedDict;
|
||||
} else if ([[[_response.allHeaderFields objectForKey:OSSHttpHeaderContentType] description] isEqual:@"application/json"]) {
|
||||
callbackResult.serverReturnJsonString = [[NSString alloc] initWithData:_collectingData encoding:NSUTF8StringEncoding];
|
||||
OSSLogVerbose(@"callback trigger result<json>: %@", callbackResult.serverReturnJsonString);
|
||||
}
|
||||
}
|
||||
return callbackResult;
|
||||
}
|
||||
case OSSOperationTypeImagePersist: {
|
||||
OSSImagePersistResult *imagePersistResult = [OSSImagePersistResult new];
|
||||
if (_response) {
|
||||
[self parseResponseHeader:_response toResultObject:imagePersistResult];
|
||||
}
|
||||
return imagePersistResult;
|
||||
}
|
||||
case OSSOperationTypeGetBucketInfo: {
|
||||
OSSGetBucketInfoResult *bucketInfoResult = [[OSSGetBucketInfoResult alloc] init];
|
||||
if (_collectingData)
|
||||
{
|
||||
NSDictionary * parseDict = [NSDictionary oss_dictionaryWithXMLData:_collectingData];
|
||||
if ([parseDict valueForKey:@"Bucket"])
|
||||
{
|
||||
NSDictionary *result = [parseDict valueForKey:@"Bucket"];
|
||||
OSSLogVerbose(@"Get bucketInfo dict: %@", parseDict);
|
||||
bucketInfoResult.bucketName = [result valueForKey:@"Name"];
|
||||
bucketInfoResult.storageClass = [result valueForKey:@"StorageClass"];
|
||||
bucketInfoResult.location = [result valueForKey:@"Location"];
|
||||
bucketInfoResult.intranetEndpoint = [result valueForKey:@"IntranetEndpoint"];
|
||||
bucketInfoResult.extranetEndpoint = [result valueForKey:@"ExtranetEndpoint"];
|
||||
bucketInfoResult.creationDate = [result valueForKey:@"CreationDate"];
|
||||
|
||||
if ([result valueForKey:@"Owner"]) {
|
||||
bucketInfoResult.owner = [[OSSBucketOwner alloc] init];
|
||||
bucketInfoResult.owner.userName = [[result valueForKey:@"Owner"] valueForKey:@"DisplayName"];
|
||||
bucketInfoResult.owner.userId = [[result valueForKey:@"Owner"] valueForKey:@"ID"];
|
||||
}
|
||||
|
||||
if ([result valueForKey:@"AccessControlList"]) {
|
||||
bucketInfoResult.acl = [OSSAccessControlList new];
|
||||
bucketInfoResult.acl.grant = [[result valueForKey:@"AccessControlList"] valueForKey:@"Grant"];
|
||||
}
|
||||
}
|
||||
}
|
||||
if (_response) {
|
||||
[self parseResponseHeader:_response toResultObject:bucketInfoResult];
|
||||
}
|
||||
return bucketInfoResult;
|
||||
}
|
||||
case OSSOperationTypeRestoreObject: {
|
||||
OSSRestoreObjectResult * restoreObjectResult = [OSSRestoreObjectResult new];
|
||||
if (_response) {
|
||||
[self parseResponseHeader:_response toResultObject:restoreObjectResult];
|
||||
}
|
||||
return restoreObjectResult;
|
||||
}
|
||||
case OSSOperationTypePutSymlink: {
|
||||
OSSPutSymlinkResult * putSymlinkResult = [OSSPutSymlinkResult new];
|
||||
if (_response) {
|
||||
[self parseResponseHeader:_response toResultObject:putSymlinkResult];
|
||||
}
|
||||
return putSymlinkResult;
|
||||
}
|
||||
case OSSOperationTypeGetSymlink: {
|
||||
OSSGetSymlinkResult * getSymlinkResult = [OSSGetSymlinkResult new];
|
||||
if (_response) {
|
||||
[self parseResponseHeader:_response toResultObject:getSymlinkResult];
|
||||
}
|
||||
return getSymlinkResult;
|
||||
}
|
||||
case OSSOperationTypeGetObjectTagging: {
|
||||
OSSGetObjectTaggingResult *result = [OSSGetObjectTaggingResult new];
|
||||
NSMutableDictionary *tags = [NSMutableDictionary dictionary];
|
||||
if (_collectingData)
|
||||
{
|
||||
NSDictionary * parseDict = [NSDictionary oss_dictionaryWithXMLData:_collectingData];
|
||||
NSDictionary *tagSet = [parseDict objectForKey:@"TagSet"];
|
||||
if (tagSet) {
|
||||
if ([tagSet[@"Tag"] isKindOfClass:[NSArray class]]) {
|
||||
for (NSDictionary * tag in tagSet[@"Tag"]) {
|
||||
NSString *key = tag[@"Key"];
|
||||
NSString *value = tag[@"Value"];
|
||||
if (key && value) {
|
||||
[tags setObject:value forKey:key];
|
||||
}
|
||||
}
|
||||
} else if ([tagSet[@"Tag"] isKindOfClass:[NSDictionary class]]) {
|
||||
NSString *key = tagSet[@"Tag"][@"Key"];
|
||||
NSString *value = tagSet[@"Tag"][@"Value"];
|
||||
if (key && value) {
|
||||
[tags setObject:value forKey:key];
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
result.tags = tags;
|
||||
if (_response) {
|
||||
[self parseResponseHeader:_response toResultObject:result];
|
||||
}
|
||||
return result;
|
||||
}
|
||||
case OSSOperationTypePutObjectTagging: {
|
||||
OSSPutObjectTaggingResult *result = [OSSPutObjectTaggingResult new];
|
||||
if (_response) {
|
||||
[self parseResponseHeader:_response toResultObject:result];
|
||||
}
|
||||
return result;
|
||||
}
|
||||
case OSSOperationTypeDeleteObjectTagging: {
|
||||
OSSDeleteObjectTaggingResult *result = [OSSDeleteObjectTaggingResult new];
|
||||
if (_response) {
|
||||
[self parseResponseHeader:_response toResultObject:result];
|
||||
}
|
||||
return result;
|
||||
}
|
||||
default: {
|
||||
OSSLogError(@"unknown operation type");
|
||||
break;
|
||||
}
|
||||
}
|
||||
return nil;
|
||||
}
|
||||
|
||||
@end
|
||||
16
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSHttpdns.h
generated
Normal file
16
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSHttpdns.h
generated
Normal file
@@ -0,0 +1,16 @@
|
||||
//
|
||||
// OSSHttpdns.h
|
||||
// AliyunOSSiOS
|
||||
//
|
||||
// Created by zhouzhuo on 5/1/16.
|
||||
// Copyright © 2016 zhouzhuo. All rights reserved.
|
||||
//
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
|
||||
@interface OSSHttpdns : NSObject
|
||||
|
||||
+ (instancetype)sharedInstance;
|
||||
|
||||
- (NSString *)asynGetIpByHost:(NSString *)host;
|
||||
@end
|
||||
147
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSHttpdns.m
generated
Normal file
147
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSHttpdns.m
generated
Normal file
@@ -0,0 +1,147 @@
|
||||
//
|
||||
// OSSHttpdns.m
|
||||
// AliyunOSSiOS
|
||||
//
|
||||
// Created by zhouzhuo on 5/1/16.
|
||||
// Copyright © 2016 zhouzhuo. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSLog.h"
|
||||
#import "OSSHttpdns.h"
|
||||
#import "OSSIPv6Adapter.h"
|
||||
|
||||
NSString * const OSS_HTTPDNS_SERVER_IP = @"203.107.1.1";
|
||||
NSString * const OSS_HTTPDNS_SERVER_PORT = @"80";
|
||||
|
||||
NSString * const ACCOUNT_ID = @"181345";
|
||||
NSTimeInterval const MAX_ENDURABLE_EXPIRED_TIME_IN_SECOND = 60; // The DNS entry's expiration time in seconds. After it expires, the entry is invalid.
|
||||
NSTimeInterval const PRERESOLVE_IN_ADVANCE_IN_SECOND = 10; // Once the remaining valid time of an DNS entry is less than this number, issue a DNS request to prefetch the data.
|
||||
|
||||
@interface IpObject : NSObject
|
||||
|
||||
@property (nonatomic, copy) NSString * ip;
|
||||
@property (nonatomic, assign) NSTimeInterval expiredTime;
|
||||
|
||||
@end
|
||||
|
||||
@implementation IpObject
|
||||
@end
|
||||
|
||||
|
||||
@implementation OSSHttpdns {
|
||||
NSMutableDictionary * gHostIpMap;
|
||||
NSMutableSet * penddingSet;
|
||||
}
|
||||
|
||||
+ (instancetype)sharedInstance {
|
||||
static OSSHttpdns * sharedInstance = nil;
|
||||
static dispatch_once_t onceToken;
|
||||
dispatch_once(&onceToken, ^{
|
||||
sharedInstance = [OSSHttpdns new];
|
||||
});
|
||||
return sharedInstance;
|
||||
}
|
||||
|
||||
- (instancetype)init {
|
||||
if (self = [super init]) {
|
||||
gHostIpMap = [NSMutableDictionary new];
|
||||
penddingSet = [NSMutableSet new];
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
/**
|
||||
* OSS SDK specific
|
||||
*
|
||||
* @param host it needs strictly follow the domain's format, such as oss-cn-hangzhou.aliyuncs.com
|
||||
*
|
||||
* @return an ip in the ip list of the resolved host.
|
||||
*/
|
||||
- (NSString *)asynGetIpByHost:(NSString *)host {
|
||||
IpObject * ipObject = [gHostIpMap objectForKey:host];
|
||||
if (!ipObject) {
|
||||
|
||||
// if the host is not resolved, asynchronously resolve it and return nil
|
||||
[self resolveHost:host];
|
||||
return nil;
|
||||
} else if ([[NSDate date] timeIntervalSince1970] - ipObject.expiredTime > MAX_ENDURABLE_EXPIRED_TIME_IN_SECOND) {
|
||||
|
||||
// If the entry is expired, asynchronously resolve it and return nil.
|
||||
[self resolveHost:host];
|
||||
return nil;
|
||||
} else if (ipObject.expiredTime -[[NSDate date] timeIntervalSince1970] < PRERESOLVE_IN_ADVANCE_IN_SECOND) {
|
||||
|
||||
// If the entry is about to expire, asynchronously resolve it and return the current value.
|
||||
[self resolveHost:host];
|
||||
return ipObject.ip;
|
||||
} else {
|
||||
|
||||
// returns the current result.
|
||||
return ipObject.ip;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* resolve the host asynchronously
|
||||
|
||||
* If the host is being resolved, the call will be skipped.
|
||||
*
|
||||
* @param host the host to resolve
|
||||
*/
|
||||
- (void)resolveHost:(NSString *)host {
|
||||
|
||||
@synchronized (self) {
|
||||
if ([penddingSet containsObject:host]) {
|
||||
return;
|
||||
} else {
|
||||
[penddingSet addObject:host];
|
||||
}
|
||||
}
|
||||
|
||||
NSURL * url = [NSURL URLWithString:[NSString stringWithFormat:@"https://%@/%@/d?host=%@", [[OSSIPv6Adapter getInstance] handleIpv4Address:OSS_HTTPDNS_SERVER_IP], ACCOUNT_ID, host]];
|
||||
NSURLSession * session = [NSURLSession sharedSession];
|
||||
|
||||
NSURLSessionDataTask * dataTask = [session dataTaskWithURL:url completionHandler:^(NSData * _Nullable data, NSURLResponse * _Nullable response, NSError * _Nullable error) {
|
||||
|
||||
IpObject * ipObject = nil;
|
||||
NSUInteger statusCode = ((NSHTTPURLResponse *)response).statusCode;
|
||||
if (statusCode != 200) {
|
||||
OSSLogError(@"Httpdns resolve host: %@ failed, responseCode: %lu", host, (unsigned long)statusCode);
|
||||
} else {
|
||||
NSError *error = nil;
|
||||
NSDictionary *json = nil;
|
||||
if (data != nil){
|
||||
json = [NSJSONSerialization JSONObjectWithData:data options:kNilOptions error:&error];
|
||||
}
|
||||
|
||||
if (error != nil || json == nil){
|
||||
return;
|
||||
}
|
||||
|
||||
NSTimeInterval expiredTime = [[NSDate new] timeIntervalSince1970] + [[json objectForKey:@"ttl"] longLongValue];
|
||||
|
||||
NSArray *ips = [json objectForKey:@"ips"];
|
||||
if (ips == nil || [ips count] == 0) {
|
||||
OSSLogError(@"Httpdns resolve host: %@ failed, ip list empty.", host);
|
||||
} else {
|
||||
NSString * ip = ips[0];
|
||||
ipObject = [IpObject new];
|
||||
ipObject.expiredTime = expiredTime;
|
||||
ipObject.ip = ip;
|
||||
OSSLogDebug(@"Httpdns resolve host: %@ success, ip: %@, expiredTime: %lf", host, ipObject.ip, ipObject.expiredTime);
|
||||
}
|
||||
}
|
||||
|
||||
@synchronized (self) {
|
||||
if (ipObject) {
|
||||
gHostIpMap[host] = ipObject;
|
||||
}
|
||||
|
||||
[penddingSet removeObject:host];
|
||||
}
|
||||
}];
|
||||
|
||||
[dataTask resume];
|
||||
}
|
||||
|
||||
@end
|
||||
114
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSIPv6/OSSIPv6Adapter.h
generated
Normal file
114
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSIPv6/OSSIPv6Adapter.h
generated
Normal file
@@ -0,0 +1,114 @@
|
||||
/*
|
||||
* Copyright (c) 2000-2015 Apple Inc. All rights reserved.
|
||||
*
|
||||
* @APPLE_OSREFERENCE_LICENSE_HEADER_START@
|
||||
*
|
||||
* This file contains Original Code and/or Modifications of Original Code
|
||||
* as defined in and that are subject to the Apple Public Source License
|
||||
* Version 2.0 (the 'License'). You may not use this file except in
|
||||
* compliance with the License. The rights granted to you under the License
|
||||
* may not be used to create, or enable the creation or redistribution of,
|
||||
* unlawful or unlicensed copies of an Apple operating system, or to
|
||||
* circumvent, violate, or enable the circumvention or violation of, any
|
||||
* terms of an Apple operating system software license agreement.
|
||||
*
|
||||
* Please obtain a copy of the License at
|
||||
* https://www.opensource.apple.com/apsl/ and read it before using this file.
|
||||
*
|
||||
* The Original Code and all software distributed under the License are
|
||||
* distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
|
||||
* EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
|
||||
* INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT.
|
||||
* Please see the License for the specific language governing rights and
|
||||
* limitations under the License.
|
||||
*
|
||||
* @APPLE_OSREFERENCE_LICENSE_HEADER_END@
|
||||
*/
|
||||
/*
|
||||
* Copyright (c) 1980, 1986, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)route.h 8.3 (Berkeley) 4/19/94
|
||||
* $FreeBSD: src/sys/net/route.h,v 1.36.2.1 2000/08/16 06:14:23 jayanth Exp $
|
||||
*/
|
||||
|
||||
|
||||
#ifndef AlicloudIPv6Adapter_h
|
||||
#define AlicloudIPv6Adapter_h
|
||||
#import <Foundation/Foundation.h>
|
||||
|
||||
@interface OSSIPv6Adapter : NSObject
|
||||
|
||||
+ (instancetype)getInstance;
|
||||
|
||||
/**
|
||||
* @brief Checks if it's a IPv6-only network. If it's true, it's IPv6-only.
|
||||
*
|
||||
* @return return YES for IPv6-only network,otherWise return NO
|
||||
*/
|
||||
- (BOOL)isIPv6OnlyNetwork;
|
||||
|
||||
/**
|
||||
* @brief Refresh the IPV6-only check
|
||||
*
|
||||
* @return return YES for IPv6-only network,otherWise return NO
|
||||
*/
|
||||
- (BOOL)reResolveIPv6OnlyStatus;
|
||||
|
||||
/**
|
||||
* @brief Adapts the IPv4 address into IPv6 format under IPv6-only network.
|
||||
* For example:
|
||||
42.156.220.114 -> 64:ff9b::2a9c:dc72
|
||||
* @param addr
|
||||
* ip address
|
||||
*
|
||||
* @return return an IPv6 address
|
||||
*/
|
||||
- (NSString *)handleIpv4Address:(NSString *)addr;
|
||||
|
||||
/**
|
||||
* @brief Checks if it's an IPv4 address.
|
||||
*
|
||||
* @return return YES while addr is an IPv4 address,otherwise return NO
|
||||
*/
|
||||
- (BOOL)isIPv4Address:(NSString *)addr;
|
||||
|
||||
/**
|
||||
* @brief Checks if it's an IPv6 address
|
||||
*
|
||||
* @return return YES while addr is an IPv6 address,otherwise return NO
|
||||
*/
|
||||
- (BOOL)isIPv6Address:(NSString *)addr;
|
||||
|
||||
@end
|
||||
|
||||
#endif /* OSSIPv6Adapter_h */
|
||||
196
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSIPv6/OSSIPv6Adapter.m
generated
Normal file
196
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSIPv6/OSSIPv6Adapter.m
generated
Normal file
@@ -0,0 +1,196 @@
|
||||
//
|
||||
// OSSIPv6Adapter.m
|
||||
//
|
||||
// Created by lingkun on 16/5/16.
|
||||
// Copyright © 2016 Ali. All rights reserved.
|
||||
//
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
#import "OSSIPv6Adapter.h"
|
||||
#import "OSSIPv6PrefixResolver.h"
|
||||
#import "OSSLog.h"
|
||||
|
||||
#include <arpa/inet.h>
|
||||
#include <dns.h>
|
||||
#include <err.h>
|
||||
#include <ifaddrs.h>
|
||||
#include <net/if.h>
|
||||
#include <netdb.h>
|
||||
#include <netinet/in.h>
|
||||
#include <resolv.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <sys/socket.h>
|
||||
#include <sys/sysctl.h>
|
||||
|
||||
#if TARGET_OS_IOS
|
||||
#import <UIKit/UIApplication.h>
|
||||
#elif TARGET_OS_OSX
|
||||
#import <AppKit/NSApplication.h>
|
||||
#endif
|
||||
|
||||
#define UNKNOWN_STACK 0
|
||||
#define SUPPORT_IPV4_STACK 1
|
||||
#define SUPPORT_IPV6_STACK 2
|
||||
#define ROUNDUP_LEN(a) \
|
||||
((a) > 0 ? (1 + (((a) - 1) | (sizeof(long) - 1))) : sizeof(long))
|
||||
#define TypeEN "en0"
|
||||
|
||||
#define IOS_9_VERSION @"9.0"
|
||||
|
||||
@implementation OSSIPv6Adapter
|
||||
{
|
||||
BOOL isIPv6Only;
|
||||
BOOL isIPv6OnlyResolved;
|
||||
}
|
||||
|
||||
- (instancetype)init {
|
||||
if (self = [super init]) {
|
||||
isIPv6Only = NO;
|
||||
isIPv6OnlyResolved = NO;
|
||||
|
||||
NSString *notificationName;
|
||||
#if TARGET_OS_IOS
|
||||
notificationName = UIApplicationDidBecomeActiveNotification;
|
||||
#elif TARGET_OS_OSX
|
||||
notificationName = NSApplicationDidBecomeActiveNotification;
|
||||
#endif
|
||||
|
||||
// When App switches to active status, refresh the IPv6-only check.
|
||||
NSNotificationCenter *defaultCenter = [NSNotificationCenter defaultCenter];
|
||||
[defaultCenter addObserver:self
|
||||
selector:@selector(appDidBecomeActiveFunc)
|
||||
name:notificationName
|
||||
object:nil];
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
+ (instancetype)getInstance {
|
||||
static id singletonInstance = nil;
|
||||
static dispatch_once_t once_token;
|
||||
dispatch_once(&once_token, ^{
|
||||
if (!singletonInstance) {
|
||||
singletonInstance = [[super allocWithZone:NULL] init];
|
||||
}
|
||||
});
|
||||
return singletonInstance;
|
||||
}
|
||||
|
||||
- (BOOL)isIPv6OnlyNetwork {
|
||||
@synchronized(self) {
|
||||
if (isIPv6OnlyResolved) {
|
||||
return isIPv6Only;
|
||||
}
|
||||
|
||||
OSSLogDebug(@"Start resolved network to see if in IPv6-Only env.");
|
||||
int localStack = 0;
|
||||
|
||||
localStack = SUPPORT_IPV4_STACK | SUPPORT_IPV6_STACK;
|
||||
localStack &= [self getDNSServersIpStack];
|
||||
|
||||
if (localStack & SUPPORT_IPV4_STACK) {
|
||||
// support IPv4
|
||||
isIPv6Only = NO;
|
||||
} else if (localStack & SUPPORT_IPV6_STACK) {
|
||||
// IPv6-Only
|
||||
isIPv6Only = YES;
|
||||
[[OSSIPv6PrefixResolver getInstance] updateIPv6Prefix];
|
||||
} else {
|
||||
OSSLogDebug(@"[%s]: Error.", __FUNCTION__);
|
||||
isIPv6Only = NO;
|
||||
}
|
||||
isIPv6OnlyResolved = YES;
|
||||
if (isIPv6Only) {
|
||||
OSSLogDebug(@"[%s]: IPv6-Only network now.", __FUNCTION__);
|
||||
} else {
|
||||
OSSLogDebug(@"[%s]: Not IPv6-Only network now.", __FUNCTION__);
|
||||
}
|
||||
return isIPv6Only;
|
||||
}
|
||||
}
|
||||
|
||||
- (void)appDidBecomeActiveFunc {
|
||||
OSSLogDebug(@"[%s]: App become active, refresh IPv6-Only status.", __FUNCTION__);
|
||||
[self reResolveIPv6OnlyStatus];
|
||||
}
|
||||
|
||||
- (BOOL)reResolveIPv6OnlyStatus {
|
||||
isIPv6OnlyResolved = NO;
|
||||
return [self isIPv6OnlyNetwork];
|
||||
}
|
||||
|
||||
- (NSString *)handleIpv4Address:(NSString *)addr {
|
||||
if (addr == nil || addr.length == 0) {
|
||||
return nil;
|
||||
}
|
||||
|
||||
if ([self isIPv6Address:addr]) return [NSString stringWithFormat:@"[%@]", addr];
|
||||
|
||||
NSString *convertedAddr;
|
||||
if ([self isIPv6OnlyNetwork]) {
|
||||
convertedAddr = [[OSSIPv6PrefixResolver getInstance] convertIPv4toIPv6:addr];
|
||||
return [NSString stringWithFormat:@"[%@]", convertedAddr];
|
||||
} else {
|
||||
convertedAddr = addr;
|
||||
}
|
||||
return convertedAddr;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Looks up the DNS server stack and returns the flag combinations of SUPPORT_IPV4_STACK and SUPPORT_IPV6_STACK.
|
||||
*
|
||||
* @return the flag combinations of SUPPORT_IPV4_STACK and SUPPORT_IPV6_STACK
|
||||
*/
|
||||
- (int)getDNSServersIpStack {
|
||||
int dns_stack = 0;
|
||||
res_state res = malloc(sizeof(struct __res_state));
|
||||
int result = res_ninit(res);
|
||||
if (result == 0) {
|
||||
union res_9_sockaddr_union *addr_union = malloc(res->nscount * sizeof(union res_9_sockaddr_union));
|
||||
res_getservers(res, addr_union, res->nscount);
|
||||
for (int i = 0; i < res->nscount; i++) {
|
||||
if (addr_union[i].sin.sin_family == AF_INET) {
|
||||
char ip[INET_ADDRSTRLEN];
|
||||
if (inet_ntop(AF_INET, &(addr_union[i].sin.sin_addr), ip, INET_ADDRSTRLEN)) {
|
||||
dns_stack |= SUPPORT_IPV4_STACK;
|
||||
}
|
||||
} else if (addr_union[i].sin6.sin6_family == AF_INET6) {
|
||||
char ip[INET6_ADDRSTRLEN];
|
||||
if (inet_ntop(AF_INET6, &(addr_union[i].sin6.sin6_addr), ip, INET6_ADDRSTRLEN)) {
|
||||
dns_stack |= SUPPORT_IPV6_STACK;
|
||||
}
|
||||
} else {
|
||||
OSSLogDebug(@"%s: Undefined family.", __FUNCTION__);
|
||||
}
|
||||
}
|
||||
free(addr_union);
|
||||
}
|
||||
res_ndestroy(res);
|
||||
free(res);
|
||||
return dns_stack;
|
||||
}
|
||||
|
||||
- (BOOL)isIPv4Address:(NSString *)addr {
|
||||
if (addr == nil) {
|
||||
return NO;
|
||||
}
|
||||
const char *utf8 = [addr UTF8String];
|
||||
// Check valid IPv4.
|
||||
struct in_addr dst;
|
||||
int success = inet_pton(AF_INET, utf8, &(dst.s_addr));
|
||||
return success == 1;
|
||||
}
|
||||
|
||||
- (BOOL)isIPv6Address:(NSString *)addr {
|
||||
if (addr == nil) {
|
||||
return NO;
|
||||
}
|
||||
const char *utf8 = [addr UTF8String];
|
||||
// Check valid IPv6.
|
||||
struct in6_addr dst6;
|
||||
int success = inet_pton(AF_INET6, utf8, &dst6);
|
||||
return (success == 1);
|
||||
}
|
||||
|
||||
@end
|
||||
23
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSIPv6/OSSIPv6PrefixResolver.h
generated
Normal file
23
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSIPv6/OSSIPv6PrefixResolver.h
generated
Normal file
@@ -0,0 +1,23 @@
|
||||
//
|
||||
// OSSIPv6PrefixResolver.h
|
||||
//
|
||||
// Created by lingkun on 16/5/16.
|
||||
// Edit by zhouzhuo on 16/5/22
|
||||
// Copyright © 2016 Ali. All rights reserved.
|
||||
//
|
||||
|
||||
#ifndef AlicloudIPv6PrefixResolver_h
|
||||
#define AlicloudIPv6PrefixResolver_h
|
||||
#import <Foundation/Foundation.h>
|
||||
|
||||
@interface OSSIPv6PrefixResolver : NSObject
|
||||
|
||||
+ (instancetype)getInstance;
|
||||
|
||||
- (void)updateIPv6Prefix;
|
||||
|
||||
- (NSString *)convertIPv4toIPv6:(NSString *)ipv4;
|
||||
|
||||
@end
|
||||
|
||||
#endif /* OSSIPv6PrefixResolver_h */
|
||||
205
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSIPv6/OSSIPv6PrefixResolver.m
generated
Normal file
205
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSIPv6/OSSIPv6PrefixResolver.m
generated
Normal file
@@ -0,0 +1,205 @@
|
||||
//
|
||||
// OSSIPv6PrefixResolver.m
|
||||
//
|
||||
// Created by lingkun on 16/5/16.
|
||||
// Edit by zhouzhuo on 2016/5/22
|
||||
// Copyright © 2016 Ali. All rights reserved.
|
||||
|
||||
#import "OSSIPv6PrefixResolver.h"
|
||||
#import "OSSLog.h"
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
#include <arpa/inet.h>
|
||||
#include <netdb.h>
|
||||
#include <netinet/in.h>
|
||||
#include <sys/socket.h>
|
||||
|
||||
static const __uint8_t NS_PREFIX_32[4] = {0x20, 0x01, 0x0d, 0xb8};
|
||||
static const __uint8_t NS_PREFIX_40[5] = {0x20, 0x01, 0x0d, 0xb8, 0x01};
|
||||
static const __uint8_t NS_PREFIX_48[6] = {0x20, 0x01, 0x0d, 0xb8, 0x01, 0x22};
|
||||
static const __uint8_t NS_PREFIX_56[7] = {0x20, 0x01, 0x0d, 0xb8, 0x01, 0x22, 0x03};
|
||||
static const __uint8_t NS_PREFIX_64[8] = {0x20, 0x01, 0x0d, 0xb8, 0x01, 0x22, 0x03, 0x44};
|
||||
static const __uint8_t NS_PREFIX_96[12] = {0x20, 0x01, 0x0d, 0xb8, 0x01, 0x22, 0x03, 0x44, 0x00, 0x00, 0x00, 0x00};
|
||||
static const __uint8_t WK_PREFIX_96[12] = {0x00, 0x64, 0xff, 0x9b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00};
|
||||
|
||||
static const __uint8_t* V6_PREFIX_CONTENT_TABLE[7] = {
|
||||
WK_PREFIX_96,
|
||||
NS_PREFIX_32,
|
||||
NS_PREFIX_40,
|
||||
NS_PREFIX_48,
|
||||
NS_PREFIX_56,
|
||||
NS_PREFIX_64,
|
||||
NS_PREFIX_96};
|
||||
|
||||
static const __uint8_t V6_PREFIX_SIZE_TABLE[7] = {
|
||||
sizeof(WK_PREFIX_96)/sizeof(__uint8_t),
|
||||
sizeof(NS_PREFIX_32)/sizeof(__uint8_t),
|
||||
sizeof(NS_PREFIX_40)/sizeof(__uint8_t),
|
||||
sizeof(NS_PREFIX_48)/sizeof(__uint8_t),
|
||||
sizeof(NS_PREFIX_56)/sizeof(__uint8_t),
|
||||
sizeof(NS_PREFIX_64)/sizeof(__uint8_t),
|
||||
sizeof(NS_PREFIX_96)/sizeof(__uint8_t)};
|
||||
|
||||
static const __uint8_t V6_PREFIX_TABLE_SIZE = 7;
|
||||
|
||||
typedef enum {
|
||||
IPv6PrefixUnResolved = 0,
|
||||
IPv6PrefixResolving,
|
||||
IPv6PrefixResolved
|
||||
} IPv6PrefixResolveStatus;
|
||||
|
||||
@implementation OSSIPv6PrefixResolver {
|
||||
IPv6PrefixResolveStatus ipv6PrefixResolveStatus;
|
||||
__uint8_t *ipv6Prefix;
|
||||
int prefixLen;
|
||||
}
|
||||
|
||||
- (instancetype)init {
|
||||
if (self = [super init]) {
|
||||
ipv6PrefixResolveStatus = IPv6PrefixUnResolved;
|
||||
ipv6Prefix = (__uint8_t *)V6_PREFIX_CONTENT_TABLE[0];
|
||||
prefixLen = V6_PREFIX_SIZE_TABLE[0];
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
+ (instancetype)getInstance {
|
||||
static id singletonInstance = nil;
|
||||
static dispatch_once_t once_token;
|
||||
dispatch_once(&once_token, ^{
|
||||
if (!singletonInstance) {
|
||||
singletonInstance = [[super allocWithZone:NULL] init];
|
||||
}
|
||||
});
|
||||
return singletonInstance;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Updates IPv6 Prefix
|
||||
*/
|
||||
- (void)updateIPv6Prefix {
|
||||
@synchronized(self) {
|
||||
ipv6PrefixResolveStatus = IPv6PrefixUnResolved;
|
||||
[self resolveIPv6Prefix:ipv6Prefix];
|
||||
}
|
||||
}
|
||||
|
||||
- (BOOL)isIPv6Prefix:(__uint8_t *)v6Prefix
|
||||
withPrefixLen:(int)pLen
|
||||
withIP:(__uint8_t *)ip
|
||||
withIPLen:(int)ipLen {
|
||||
for (int i = 0; i < pLen && i < ipLen; i++) {
|
||||
if (*(v6Prefix + i) != *(ip + i)) {
|
||||
return NO;
|
||||
}
|
||||
}
|
||||
return YES;
|
||||
}
|
||||
|
||||
- (__uint8_t)resolveIPv6Prefix:(__uint8_t *)prefix {
|
||||
if ( !prefix ) {
|
||||
return 0;
|
||||
}
|
||||
__uint8_t len = prefixLen;
|
||||
memcpy(prefix, ipv6Prefix, prefixLen);
|
||||
@synchronized(self) {
|
||||
if (ipv6PrefixResolveStatus==IPv6PrefixUnResolved ) {
|
||||
ipv6PrefixResolveStatus = IPv6PrefixResolving;
|
||||
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
|
||||
struct addrinfo hints, *addr;
|
||||
memset(&hints, 0, sizeof(hints));
|
||||
hints.ai_family = PF_INET6;
|
||||
hints.ai_socktype = SOCK_STREAM;
|
||||
hints.ai_flags = AI_DEFAULT;
|
||||
|
||||
if (0 != getaddrinfo("ipv4only.arpa", "http", &hints, &addr)) {
|
||||
ipv6PrefixResolveStatus = IPv6PrefixUnResolved;
|
||||
return;
|
||||
}
|
||||
|
||||
if (addr && AF_INET6 == addr->ai_addr->sa_family) {
|
||||
struct sockaddr_in6 *addr6 = (struct sockaddr_in6 *)(addr->ai_addr);
|
||||
if ( !addr6 ) {
|
||||
ipv6PrefixResolveStatus = IPv6PrefixUnResolved;
|
||||
return;
|
||||
}
|
||||
|
||||
__uint8_t* u8 = addr6->sin6_addr.__u6_addr.__u6_addr8;
|
||||
for (__uint8_t i=0; i < V6_PREFIX_TABLE_SIZE; i++) {
|
||||
if ([self isIPv6Prefix:(__uint8_t *)V6_PREFIX_CONTENT_TABLE[i]
|
||||
withPrefixLen:V6_PREFIX_SIZE_TABLE[i]
|
||||
withIP:u8
|
||||
withIPLen:16]) {
|
||||
|
||||
ipv6Prefix = (__uint8_t *)V6_PREFIX_CONTENT_TABLE[i];
|
||||
prefixLen = V6_PREFIX_SIZE_TABLE[i];
|
||||
ipv6PrefixResolveStatus = IPv6PrefixResolved;
|
||||
break;
|
||||
}
|
||||
}
|
||||
ipv6PrefixResolveStatus = IPv6PrefixUnResolved;
|
||||
}
|
||||
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
return len;
|
||||
}
|
||||
|
||||
- (NSString *)convertIPv4toIPv6:(NSString *)ipv4 {
|
||||
if ([ipv4 length] <= 0) {
|
||||
return nil;
|
||||
}
|
||||
|
||||
__uint8_t ipv6[16] = {0x00};
|
||||
__uint8_t length = [self resolveIPv6Prefix:ipv6];
|
||||
|
||||
if (length <= 0) {
|
||||
return nil;
|
||||
}
|
||||
|
||||
in_addr_t addr_v4 = inet_addr([ipv4 UTF8String]);
|
||||
|
||||
// 按length的不同情况进行处理
|
||||
if (length==4 || length==12) { //32 bits or 96 bits
|
||||
ipv6[length+0] |= (__uint8_t)(addr_v4>>0 & 0xff);
|
||||
ipv6[length+1] |= (__uint8_t)(addr_v4>>8 & 0xff);
|
||||
ipv6[length+2] |= (__uint8_t)(addr_v4>>16 & 0xff);
|
||||
ipv6[length+3] |= (__uint8_t)(addr_v4>>24 & 0xff);
|
||||
}
|
||||
else if (length == 5) { //40 bits :a.b.c.0.d
|
||||
ipv6[length+0] |= (__uint8_t)(addr_v4>>0 & 0xff);
|
||||
ipv6[length+1] |= (__uint8_t)(addr_v4>>8 & 0xff);
|
||||
ipv6[length+2] |= (__uint8_t)(addr_v4>>16 & 0xff);
|
||||
ipv6[length+4] |= (__uint8_t)(addr_v4>>24 & 0xff);
|
||||
}
|
||||
else if (length == 6) { //48 bits :a.b.0.c.d
|
||||
ipv6[length+0] |= (__uint8_t)(addr_v4>>0 & 0xff);
|
||||
ipv6[length+1] |= (__uint8_t)(addr_v4>>8 & 0xff);
|
||||
ipv6[length+3] |= (__uint8_t)(addr_v4>>16 & 0xff);
|
||||
ipv6[length+4] |= (__uint8_t)(addr_v4>>24 & 0xff);
|
||||
}
|
||||
else if (length == 7) { //56 bits :a.0.b.c.d
|
||||
ipv6[length+0] |= (__uint8_t)(addr_v4>>0 & 0xff);
|
||||
ipv6[length+2] |= (__uint8_t)(addr_v4>>8 & 0xff);
|
||||
ipv6[length+3] |= (__uint8_t)(addr_v4>>16 & 0xff);
|
||||
ipv6[length+4] |= (__uint8_t)(addr_v4>>24 & 0xff);
|
||||
}
|
||||
else if (length == 8) { //64 bits :0.a.b.c.d
|
||||
ipv6[length+1] |= (__uint8_t)(addr_v4>>0 & 0xff);
|
||||
ipv6[length+2] |= (__uint8_t)(addr_v4>>8 & 0xff);
|
||||
ipv6[length+3] |= (__uint8_t)(addr_v4>>16 & 0xff);
|
||||
ipv6[length+4] |= (__uint8_t)(addr_v4>>24 & 0xff);
|
||||
}
|
||||
|
||||
// constructs the IPv6 structure
|
||||
char addr_text[ MAX(INET_ADDRSTRLEN, INET6_ADDRSTRLEN) ];
|
||||
if(inet_ntop(AF_INET6, ipv6, addr_text, INET6_ADDRSTRLEN)) {
|
||||
NSString *ret = [NSString stringWithUTF8String:addr_text];
|
||||
return ret;
|
||||
}
|
||||
return nil;
|
||||
}
|
||||
|
||||
@end
|
||||
22
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSInputStreamHelper.h
generated
Normal file
22
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSInputStreamHelper.h
generated
Normal file
@@ -0,0 +1,22 @@
|
||||
//
|
||||
// OSSInputStreamHelper.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by 怀叙 on 2017/12/7.
|
||||
// Copyright © 2017年 阿里云. All rights reserved.
|
||||
//
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
@interface OSSInputStreamHelper : NSObject
|
||||
|
||||
@property (nonatomic, assign) uint64_t crc64;
|
||||
|
||||
- (instancetype)initWithFileAtPath:(nonnull NSString *)path;
|
||||
- (instancetype)initWithURL:(nonnull NSURL *)URL;
|
||||
|
||||
- (void)syncReadBuffers;
|
||||
|
||||
@end
|
||||
NS_ASSUME_NONNULL_END
|
||||
80
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSInputStreamHelper.m
generated
Normal file
80
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSInputStreamHelper.m
generated
Normal file
@@ -0,0 +1,80 @@
|
||||
//
|
||||
// OSSInputStreamHelper.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by 怀叙 on 2017/12/7.
|
||||
// Copyright © 2017年 阿里云. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSInputStreamHelper.h"
|
||||
#import "OSSLog.h"
|
||||
#import "aos_crc64.h"
|
||||
|
||||
@interface OSSInputStreamHelper ()
|
||||
{
|
||||
NSInputStream *_inputStream;
|
||||
CFAbsoluteTime _startTime;
|
||||
dispatch_semaphore_t _semaphore;
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSInputStreamHelper
|
||||
|
||||
- (instancetype)initWithFileAtPath:(nonnull NSString *)path
|
||||
{
|
||||
self = [super init];
|
||||
if (self) {
|
||||
_crc64 = 0;
|
||||
_inputStream = [NSInputStream inputStreamWithFileAtPath:path];
|
||||
_semaphore = dispatch_semaphore_create(1);
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
- (instancetype)initWithURL:(nonnull NSURL *)URL
|
||||
{
|
||||
self = [super init];
|
||||
if (self) {
|
||||
_crc64 = 0;
|
||||
_inputStream = [NSInputStream inputStreamWithURL:URL];
|
||||
_semaphore = dispatch_semaphore_create(1);
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
- (void)syncReadBuffers
|
||||
{
|
||||
dispatch_semaphore_wait(_semaphore, DISPATCH_TIME_FOREVER);
|
||||
|
||||
_startTime = CFAbsoluteTimeGetCurrent();
|
||||
[_inputStream open];
|
||||
NSInteger length = 1;
|
||||
while (length > 0)
|
||||
{
|
||||
@autoreleasepool{
|
||||
uint8_t streamData[1024 * 4];
|
||||
length = [_inputStream read:streamData maxLength:1024 * 4];
|
||||
if (length > 0) {
|
||||
_crc64 = aos_crc64(_crc64, streamData, length);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (length < 0) {
|
||||
OSSLogError(@"there is an error when reading buffer from file!");
|
||||
}
|
||||
[_inputStream close];
|
||||
|
||||
CFAbsoluteTime duration = CFAbsoluteTimeGetCurrent() - _startTime;
|
||||
OSSLogDebug(@"read file cost time is :%f",duration);
|
||||
|
||||
dispatch_semaphore_signal(_semaphore);
|
||||
}
|
||||
|
||||
- (uint64_t)crc64
|
||||
{
|
||||
return _crc64;
|
||||
}
|
||||
|
||||
@end
|
||||
54
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSLog.h
generated
Normal file
54
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSLog.h
generated
Normal file
@@ -0,0 +1,54 @@
|
||||
//
|
||||
// OSSLog.h
|
||||
// oss_ios_sdk
|
||||
//
|
||||
// Created by zhouzhuo on 8/16/15.
|
||||
// Copyright (c) 2015 aliyun.com. All rights reserved.
|
||||
//
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
#import "OSSCocoaLumberjack.h"
|
||||
static const OSSDDLogLevel ossLogLevel = OSSDDLogLevelAll;
|
||||
|
||||
// colorful log configuration
|
||||
// see https://github.com/robbiehanson/XcodeColors
|
||||
|
||||
#define XCODE_COLORS_ESCAPE @"\033["
|
||||
|
||||
#define XCODE_COLORS_RESET_FG XCODE_COLORS_ESCAPE @"fg;" // Clear any foreground color
|
||||
#define XCODE_COLORS_RESET_BG XCODE_COLORS_ESCAPE @"bg;" // Clear any background color
|
||||
#define XCODE_COLORS_RESET XCODE_COLORS_ESCAPE @";" // Clear any foreground or background color
|
||||
|
||||
#define OSSLogVerbose(frmt, ...)\
|
||||
if ([OSSLog isLogEnable]) {\
|
||||
OSSDDLogVerbose(@"[Verbose]: %@", [NSString stringWithFormat:(frmt), ##__VA_ARGS__]);\
|
||||
}
|
||||
|
||||
#define OSSLogDebug(frmt, ...)\
|
||||
if ([OSSLog isLogEnable]) {\
|
||||
OSSDDLogDebug(@"[Debug]: %@", [NSString stringWithFormat:(frmt), ##__VA_ARGS__]);\
|
||||
}
|
||||
|
||||
#define OSSLogDebugNoFile(frmt, ...)\
|
||||
if ([OSSLog isLogEnable]) {\
|
||||
NSLog(@"[Debug]: %@", [NSString stringWithFormat:(frmt), ##__VA_ARGS__]);\
|
||||
}
|
||||
|
||||
#define OSSLogError(frmt, ...)\
|
||||
if ([OSSLog isLogEnable]) {\
|
||||
OSSDDLogError(@"[Error]: %@", [NSString stringWithFormat:(frmt), ##__VA_ARGS__]);\
|
||||
}
|
||||
|
||||
#define OSSLogWarn(frmt, ...)\
|
||||
if ([OSSLog isLogEnable]) {\
|
||||
OSSDDLogWarn(@"[Warning]: %@", [NSString stringWithFormat:(frmt), ##__VA_ARGS__]);\
|
||||
}
|
||||
|
||||
static BOOL isEnable;
|
||||
|
||||
@interface OSSLog : NSObject
|
||||
|
||||
+ (void)enableLog;
|
||||
+ (void)disableLog;
|
||||
+ (BOOL)isLogEnable;
|
||||
@end
|
||||
31
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSLog.m
generated
Normal file
31
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSLog.m
generated
Normal file
@@ -0,0 +1,31 @@
|
||||
//
|
||||
// OSSLog.m
|
||||
// oss_ios_sdk
|
||||
//
|
||||
// Created by zhouzhuo on 8/16/15.
|
||||
// Copyright (c) 2015 aliyun.com. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSLog.h"
|
||||
#import "OSSUtil.h"
|
||||
|
||||
@implementation OSSLog
|
||||
+ (void)enableLog {
|
||||
if([OSSUtil hasPhoneFreeSpace]){
|
||||
isEnable = YES;
|
||||
[OSSDDLog removeAllLoggers];
|
||||
[OSSDDLog addLogger:[OSSNSLogger sharedInstance]];
|
||||
OSSDDFileLogger *fileLogger = [[OSSDDFileLogger alloc] init];
|
||||
[OSSDDLog addLogger:fileLogger];
|
||||
}
|
||||
}
|
||||
|
||||
+ (void)disableLog {
|
||||
isEnable = NO;
|
||||
}
|
||||
|
||||
+ (BOOL)isLogEnable {
|
||||
return isEnable;
|
||||
}
|
||||
|
||||
@end
|
||||
1538
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSModel.h
generated
Normal file
1538
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSModel.h
generated
Normal file
File diff suppressed because it is too large
Load Diff
805
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSModel.m
generated
Normal file
805
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSModel.m
generated
Normal file
@@ -0,0 +1,805 @@
|
||||
//
|
||||
// OSSModel.m
|
||||
// oss_ios_sdk
|
||||
//
|
||||
// Created by zhouzhuo on 8/16/15.
|
||||
// Copyright (c) 2015 aliyun.com. All rights reserved.
|
||||
//
|
||||
#import "OSSDefine.h"
|
||||
#import "OSSModel.h"
|
||||
#import "OSSBolts.h"
|
||||
#import "OSSUtil.h"
|
||||
#import "OSSNetworking.h"
|
||||
#import "OSSLog.h"
|
||||
#import "OSSXMLDictionary.h"
|
||||
#import "OSSSignerParams.h"
|
||||
#import "OSSSignerBase.h"
|
||||
#if TARGET_OS_IOS
|
||||
#import <UIKit/UIDevice.h>
|
||||
#import <UIKit/UIApplication.h>
|
||||
#endif
|
||||
|
||||
#import "OSSAllRequestNeededMessage.h"
|
||||
#import "OSSNetworkingRequestDelegate.h"
|
||||
|
||||
@implementation NSDictionary (OSS)
|
||||
|
||||
- (NSString *)base64JsonString {
|
||||
NSError * error;
|
||||
NSData * jsonData = [NSJSONSerialization dataWithJSONObject:self
|
||||
options:0
|
||||
error:&error];
|
||||
|
||||
if (!jsonData) {
|
||||
return @"e30="; // base64("{}");
|
||||
} else {
|
||||
NSString * jsonStr = [[[NSString alloc] initWithData:jsonData encoding:NSUTF8StringEncoding] stringByReplacingOccurrencesOfString:@"\\/" withString:@"/"];
|
||||
NSLog(@"callback json - %@", jsonStr);
|
||||
return [[jsonStr dataUsingEncoding:NSUTF8StringEncoding] base64EncodedStringWithOptions:0];
|
||||
}
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSSyncMutableDictionary
|
||||
|
||||
- (instancetype)init {
|
||||
if (self = [super init]) {
|
||||
_dictionary = [NSMutableDictionary dictionary];
|
||||
_dispatchQueue = dispatch_queue_create("com.aliyun.aliyunsycmutabledictionary", DISPATCH_QUEUE_SERIAL);
|
||||
}
|
||||
|
||||
return self;
|
||||
}
|
||||
|
||||
- (void)dealloc {
|
||||
[[NSNotificationCenter defaultCenter] removeObserver:self];
|
||||
}
|
||||
|
||||
- (void)addObserverForResetCurrentRetryCount {
|
||||
#if TARGET_OS_IOS
|
||||
NSString *notificationName = UIApplicationWillEnterForegroundNotification;
|
||||
// When App switches to active status, refresh the IPv6-only check.
|
||||
NSNotificationCenter *defaultCenter = [NSNotificationCenter defaultCenter];
|
||||
[defaultCenter addObserver:self
|
||||
selector:@selector(appWillEnterForeground)
|
||||
name:notificationName
|
||||
object:nil];
|
||||
#endif
|
||||
}
|
||||
|
||||
- (NSArray *)allKeys {
|
||||
__block NSArray *allKeys = nil;
|
||||
dispatch_sync(self.dispatchQueue, ^{
|
||||
allKeys = [self.dictionary allKeys];
|
||||
});
|
||||
return allKeys;
|
||||
}
|
||||
|
||||
- (id)objectForKey:(id)aKey {
|
||||
__block id returnObject = nil;
|
||||
|
||||
dispatch_sync(self.dispatchQueue, ^{
|
||||
returnObject = [self.dictionary objectForKey:aKey];
|
||||
});
|
||||
|
||||
return returnObject;
|
||||
}
|
||||
|
||||
- (void)setObject:(id)anObject forKey:(id <NSCopying>)aKey {
|
||||
dispatch_sync(self.dispatchQueue, ^{
|
||||
[self.dictionary oss_setObject:anObject forKey:aKey];
|
||||
});
|
||||
}
|
||||
|
||||
- (void)removeObjectForKey:(id)aKey {
|
||||
dispatch_sync(self.dispatchQueue, ^{
|
||||
[self.dictionary removeObjectForKey:aKey];
|
||||
});
|
||||
}
|
||||
|
||||
- (void)appWillEnterForeground {
|
||||
dispatch_sync(self.dispatchQueue, ^{
|
||||
for (NSString *key in self.dictionary.allKeys) {
|
||||
OSSNetworkingRequestDelegate *delegate = self.dictionary[key];
|
||||
delegate.currentRetryCount = 0;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSFederationToken
|
||||
|
||||
- (NSString *)description
|
||||
{
|
||||
return [NSString stringWithFormat:@"OSSFederationToken<%p>:{AccessKeyId: %@\nAccessKeySecret: %@\nSecurityToken: %@\nExpiration: %@}", self, _tAccessKey, _tSecretKey, _tToken, _expirationTimeInGMTFormat];
|
||||
}
|
||||
|
||||
- (BOOL)useSecurityToken {
|
||||
return self.tToken != nil;
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSPlainTextAKSKPairCredentialProvider
|
||||
|
||||
- (instancetype)initWithPlainTextAccessKey:(nonnull NSString *)accessKey secretKey:(nonnull NSString *)secretKey {
|
||||
if (self = [super init]) {
|
||||
self.accessKey = [accessKey oss_trim];
|
||||
self.secretKey = [secretKey oss_trim];
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
- (nullable NSString *)sign:(NSString *)content error:(NSError **)error {
|
||||
if (![self.accessKey oss_isNotEmpty] || ![self.secretKey oss_isNotEmpty])
|
||||
{
|
||||
if (error != nil)
|
||||
{
|
||||
*error = [NSError errorWithDomain:OSSClientErrorDomain
|
||||
code:OSSClientErrorCodeSignFailed
|
||||
userInfo:@{OSSErrorMessageTOKEN: @"accessKey or secretKey can't be null"}];
|
||||
}
|
||||
|
||||
return nil;
|
||||
}
|
||||
NSString * sign = [OSSUtil calBase64Sha1WithData:content withSecret:self.secretKey];
|
||||
return [NSString stringWithFormat:@"OSS %@:%@", self.accessKey, sign];
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSCustomSignerCredentialProvider
|
||||
|
||||
- (instancetype)initWithImplementedSigner:(OSSCustomSignContentBlock)signContent
|
||||
{
|
||||
NSParameterAssert(signContent);
|
||||
if (self = [super init])
|
||||
{
|
||||
_signContent = signContent;
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
- (NSString *)sign:(NSString *)content error:(NSError **)error
|
||||
{
|
||||
NSString * signature = @"";
|
||||
@synchronized(self) {
|
||||
signature = self.signContent(content, error);
|
||||
}
|
||||
if (*error) {
|
||||
*error = [NSError errorWithDomain:OSSClientErrorDomain
|
||||
code:OSSClientErrorCodeSignFailed
|
||||
userInfo:[[NSDictionary alloc] initWithDictionary:[*error userInfo]]];
|
||||
return nil;
|
||||
}
|
||||
return signature;
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSFederationCredentialProvider
|
||||
|
||||
- (instancetype)initWithFederationTokenGetter:(OSSGetFederationTokenBlock)federationTokenGetter {
|
||||
if (self = [super init]) {
|
||||
self.federationTokenGetter = federationTokenGetter;
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
- (nullable OSSFederationToken *)getToken:(NSError **)error {
|
||||
OSSFederationToken * validToken = nil;
|
||||
@synchronized(self) {
|
||||
if (self.cachedToken == nil) {
|
||||
|
||||
self.cachedToken = self.federationTokenGetter();
|
||||
} else {
|
||||
if (self.cachedToken.expirationTimeInGMTFormat) {
|
||||
NSDateFormatter * fm = [NSDateFormatter new];
|
||||
fm.locale = [NSLocale localeWithLocaleIdentifier:@"en_US_POSIX"];
|
||||
[fm setDateFormat:@"yyyy-MM-dd'T'HH:mm:ssZ"];
|
||||
self.cachedToken.expirationTimeInMilliSecond = [[fm dateFromString:self.cachedToken.expirationTimeInGMTFormat] timeIntervalSince1970] * 1000;
|
||||
self.cachedToken.expirationTimeInGMTFormat = nil;
|
||||
OSSLogVerbose(@"Transform GMT date to expirationTimeInMilliSecond: %lld", self.cachedToken.expirationTimeInMilliSecond);
|
||||
}
|
||||
|
||||
NSDate * expirationDate = [NSDate dateWithTimeIntervalSince1970:(NSTimeInterval)(self.cachedToken.expirationTimeInMilliSecond / 1000)];
|
||||
NSTimeInterval interval = [expirationDate timeIntervalSinceDate:[NSDate oss_clockSkewFixedDate]];
|
||||
/* if this token will be expired after less than 5 min, we abort it in case of when request arrived oss server,
|
||||
it's expired already. */
|
||||
if (interval < 5 * 60) {
|
||||
OSSLogDebug(@"get federation token, but after %lf second it would be expired", interval);
|
||||
self.cachedToken = self.federationTokenGetter();
|
||||
}
|
||||
}
|
||||
|
||||
validToken = self.cachedToken;
|
||||
}
|
||||
if (!validToken)
|
||||
{
|
||||
if (error != nil)
|
||||
{
|
||||
*error = [NSError errorWithDomain:OSSClientErrorDomain
|
||||
code:OSSClientErrorCodeSignFailed
|
||||
userInfo:@{OSSErrorMessageTOKEN: @"Can't get a federation token"}];
|
||||
}
|
||||
|
||||
return nil;
|
||||
}
|
||||
return validToken;
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSStsTokenCredentialProvider
|
||||
|
||||
- (OSSFederationToken *)getToken {
|
||||
OSSFederationToken * token = [OSSFederationToken new];
|
||||
token.tAccessKey = self.accessKeyId;
|
||||
token.tSecretKey = self.secretKeyId;
|
||||
token.tToken = self.securityToken;
|
||||
token.expirationTimeInMilliSecond = NSIntegerMax;
|
||||
return token;
|
||||
}
|
||||
|
||||
- (instancetype)initWithAccessKeyId:(NSString *)accessKeyId secretKeyId:(NSString *)secretKeyId securityToken:(NSString *)securityToken {
|
||||
if (self = [super init]) {
|
||||
self.accessKeyId = [accessKeyId oss_trim];
|
||||
self.secretKeyId = [secretKeyId oss_trim];
|
||||
self.securityToken = [securityToken oss_trim];
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
- (NSString *)sign:(NSString *)content error:(NSError **)error {
|
||||
NSString * sign = [OSSUtil calBase64Sha1WithData:content withSecret:self.secretKeyId];
|
||||
return [NSString stringWithFormat:@"OSS %@:%@", self.accessKeyId, sign];
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSAuthCredentialProvider
|
||||
|
||||
- (instancetype)initWithAuthServerUrl:(NSString *)authServerUrl
|
||||
{
|
||||
return [self initWithAuthServerUrl:authServerUrl responseDecoder:nil];
|
||||
}
|
||||
|
||||
- (instancetype)initWithAuthServerUrl:(NSString *)authServerUrl responseDecoder:(nullable OSSResponseDecoderBlock)decoder
|
||||
{
|
||||
self = [super initWithFederationTokenGetter:^OSSFederationToken * {
|
||||
NSURL * url = [NSURL URLWithString:self.authServerUrl];
|
||||
NSURLRequest * request = [NSURLRequest requestWithURL:url];
|
||||
OSSTaskCompletionSource * tcs = [OSSTaskCompletionSource taskCompletionSource];
|
||||
NSURLSession * session = [NSURLSession sharedSession];
|
||||
NSURLSessionTask * sessionTask = [session dataTaskWithRequest:request
|
||||
completionHandler:^(NSData *data, NSURLResponse *response, NSError *error) {
|
||||
if (error) {
|
||||
[tcs setError:error];
|
||||
return;
|
||||
}
|
||||
[tcs setResult:data];
|
||||
}];
|
||||
[sessionTask resume];
|
||||
[tcs.task waitUntilFinished];
|
||||
if (tcs.task.error) {
|
||||
return nil;
|
||||
} else {
|
||||
NSData* data = tcs.task.result;
|
||||
if(decoder){
|
||||
data = decoder(data);
|
||||
}
|
||||
NSDictionary * object = [NSJSONSerialization JSONObjectWithData:data
|
||||
options:kNilOptions
|
||||
error:nil];
|
||||
int statusCode = [[object objectForKey:@"StatusCode"] intValue];
|
||||
if (statusCode == 200) {
|
||||
OSSFederationToken * token = [OSSFederationToken new];
|
||||
// All the entries below are mandatory.
|
||||
token.tAccessKey = [object objectForKey:@"AccessKeyId"];
|
||||
token.tSecretKey = [object objectForKey:@"AccessKeySecret"];
|
||||
token.tToken = [object objectForKey:@"SecurityToken"];
|
||||
token.expirationTimeInGMTFormat = [object objectForKey:@"Expiration"];
|
||||
OSSLogDebug(@"token: %@ %@ %@ %@", token.tAccessKey, token.tSecretKey, token.tToken, [object objectForKey:@"Expiration"]);
|
||||
return token;
|
||||
}else{
|
||||
return nil;
|
||||
}
|
||||
|
||||
}
|
||||
}];
|
||||
if(self){
|
||||
self.authServerUrl = authServerUrl;
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
NSString * const BACKGROUND_SESSION_IDENTIFIER = @"com.aliyun.oss.backgroundsession";
|
||||
|
||||
@implementation OSSClientConfiguration
|
||||
|
||||
- (instancetype)init {
|
||||
if (self = [super init]) {
|
||||
self.maxRetryCount = OSSDefaultRetryCount;
|
||||
self.maxConcurrentRequestCount = OSSDefaultMaxConcurrentNum;
|
||||
self.enableBackgroundTransmitService = NO;
|
||||
self.isHttpdnsEnable = NO;
|
||||
self.backgroundSesseionIdentifier = BACKGROUND_SESSION_IDENTIFIER;
|
||||
self.timeoutIntervalForRequest = OSSDefaultTimeoutForRequestInSecond;
|
||||
self.timeoutIntervalForResource = OSSDefaultTimeoutForResourceInSecond;
|
||||
self.isPathStyleAccessEnable = NO;
|
||||
self.isCustomPathPrefixEnable = NO;
|
||||
self.cnameExcludeList = @[];
|
||||
self.isAllowUACarrySystemInfo = YES;
|
||||
self.isFollowRedirectsEnable = YES;
|
||||
// When the value <= 0, do not set HTTPMaximumConnectionsPerHost and use the default value of NSURLSessionConfiguration
|
||||
self.HTTPMaximumConnectionsPerHost = 0;
|
||||
self.isAllowResetRetryCount = NO;
|
||||
self.isAllowNetworkMetricInfo = NO;
|
||||
self.signVersion = OSSSignVersionV1;
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
- (void)setCnameExcludeList:(NSArray *)cnameExcludeList {
|
||||
NSMutableArray * array = [NSMutableArray new];
|
||||
[cnameExcludeList enumerateObjectsUsingBlock:^(id _Nonnull obj, NSUInteger idx, BOOL * _Nonnull stop) {
|
||||
NSString * host = [(NSString *)obj lowercaseString];
|
||||
if ([host containsString:@"://"]) {
|
||||
NSString * trimHost = [host substringFromIndex:[host rangeOfString:@"://"].location + 3];
|
||||
[array addObject:trimHost];
|
||||
} else {
|
||||
[array addObject:host];
|
||||
}
|
||||
}];
|
||||
_cnameExcludeList = array.copy;
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSSignerInterceptor
|
||||
|
||||
- (instancetype)initWithCredentialProvider:(id<OSSCredentialProvider>)credentialProvider {
|
||||
if (self = [super init]) {
|
||||
self.credentialProvider = credentialProvider;
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
- (OSSTask *)interceptRequestMessage:(OSSAllRequestNeededMessage *)requestMessage {
|
||||
OSSLogVerbose(@"signing intercepting - ");
|
||||
NSString *resource = @"/";
|
||||
if (requestMessage.bucketName) {
|
||||
resource = [NSString stringWithFormat:@"/%@/", requestMessage.bucketName];
|
||||
}
|
||||
if (requestMessage.objectKey) {
|
||||
resource = [resource oss_stringByAppendingPathComponentForURL:requestMessage.objectKey];
|
||||
}
|
||||
OSSSignerParams *signerParams = [[OSSSignerParams alloc] init];
|
||||
signerParams.region = self.region;
|
||||
signerParams.cloudBoxId = self.cloudBoxId;
|
||||
signerParams.resourcePath = resource;
|
||||
signerParams.credentialProvider = self.credentialProvider;
|
||||
|
||||
id<OSSRequestSigner> requestSigner = [OSSSignerBase createRequestSignerWithSignerVersion:self.version
|
||||
signerParams:signerParams];
|
||||
|
||||
return [requestSigner sign:requestMessage];
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSUASettingInterceptor
|
||||
|
||||
- (instancetype)initWithClientConfiguration:(OSSClientConfiguration *)clientConfiguration{
|
||||
if (self = [super init]) {
|
||||
self.clientConfiguration = clientConfiguration;
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
- (OSSTask *)interceptRequestMessage:(OSSAllRequestNeededMessage *)request {
|
||||
NSString * userAgent = [self getUserAgent:self.clientConfiguration.userAgentMark];
|
||||
[request.headerParams oss_setObject:userAgent forKey:@"User-Agent"];
|
||||
return [OSSTask taskWithResult:nil];
|
||||
}
|
||||
|
||||
|
||||
- (NSString *)getUserAgent:(NSString *)customUserAgent {
|
||||
static NSString * userAgent = nil;
|
||||
static dispatch_once_t once;
|
||||
NSString * tempUserAgent = nil;
|
||||
dispatch_once(&once, ^{
|
||||
NSString *localeIdentifier = [[NSLocale currentLocale] localeIdentifier];
|
||||
#if TARGET_OS_IOS
|
||||
if (self.clientConfiguration.isAllowUACarrySystemInfo) {
|
||||
NSString *systemName = [[[UIDevice currentDevice] systemName] stringByReplacingOccurrencesOfString:@" " withString:@"-"];
|
||||
NSString *systemVersion = [[UIDevice currentDevice] systemVersion];
|
||||
userAgent = [NSString stringWithFormat:@"%@/%@(/%@/%@/%@)", OSSUAPrefix, OSSSDKVersion, systemName, systemVersion, localeIdentifier];
|
||||
} else {
|
||||
userAgent = [NSString stringWithFormat:@"%@/%@(/%@)", OSSUAPrefix, OSSSDKVersion, localeIdentifier];
|
||||
}
|
||||
#elif TARGET_OS_OSX
|
||||
userAgent = [NSString stringWithFormat:@"%@/%@(/%@/%@/%@)", OSSUAPrefix, OSSSDKVersion, @"OSX", [NSProcessInfo processInfo].operatingSystemVersionString, localeIdentifier];
|
||||
#endif
|
||||
});
|
||||
if(customUserAgent){
|
||||
if(userAgent){
|
||||
tempUserAgent = [[userAgent stringByAppendingString:@"/"] stringByAppendingString:customUserAgent];
|
||||
}else{
|
||||
tempUserAgent = customUserAgent;
|
||||
}
|
||||
}else{
|
||||
tempUserAgent = userAgent;
|
||||
}
|
||||
return tempUserAgent;
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSTimeSkewedFixingInterceptor
|
||||
|
||||
- (OSSTask *)interceptRequestMessage:(OSSAllRequestNeededMessage *)request {
|
||||
request.date = [[NSDate oss_clockSkewFixedDate] oss_asStringValue];
|
||||
return [OSSTask taskWithResult:nil];
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSRange
|
||||
|
||||
- (instancetype)initWithStart:(int64_t)start withEnd:(int64_t)end {
|
||||
if (self = [super init]) {
|
||||
self.startPosition = start;
|
||||
self.endPosition = end;
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
- (NSString *)toHeaderString {
|
||||
|
||||
NSString * rangeString = nil;
|
||||
|
||||
if (self.startPosition < 0 && self.endPosition < 0) {
|
||||
rangeString = [NSString stringWithFormat:@"bytes=%lld-%lld", self.startPosition, self.endPosition];
|
||||
} else if (self.startPosition < 0) {
|
||||
rangeString = [NSString stringWithFormat:@"bytes=-%lld", self.endPosition];
|
||||
} else if (self.endPosition < 0) {
|
||||
rangeString = [NSString stringWithFormat:@"bytes=%lld-", self.startPosition];
|
||||
} else {
|
||||
rangeString = [NSString stringWithFormat:@"bytes=%lld-%lld", self.startPosition, self.endPosition];
|
||||
}
|
||||
|
||||
return rangeString;
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
#pragma mark request and result objects
|
||||
|
||||
@implementation OSSGetServiceRequest
|
||||
|
||||
- (NSDictionary *)requestParams {
|
||||
NSMutableDictionary * params = [NSMutableDictionary dictionary];
|
||||
[params oss_setObject:self.prefix forKey:@"prefix"];
|
||||
[params oss_setObject:self.marker forKey:@"marker"];
|
||||
if (self.maxKeys > 0) {
|
||||
[params oss_setObject:[@(self.maxKeys) stringValue] forKey:@"max-keys"];
|
||||
}
|
||||
return [params copy];
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSGetServiceResult
|
||||
@end
|
||||
|
||||
@implementation OSSCreateBucketRequest
|
||||
|
||||
- (instancetype)init
|
||||
{
|
||||
self = [super init];
|
||||
if (self) {
|
||||
_storageClass = OSSBucketStorageClassStandard;
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
- (NSString *)storageClassAsString {
|
||||
NSString *storageClassString = nil;
|
||||
switch (_storageClass) {
|
||||
case OSSBucketStorageClassStandard:
|
||||
storageClassString = @"Standard";
|
||||
break;
|
||||
case OSSBucketStorageClassIA:
|
||||
storageClassString = @"IA";
|
||||
break;
|
||||
case OSSBucketStorageClassArchive:
|
||||
storageClassString = @"Archive";
|
||||
break;
|
||||
default:
|
||||
storageClassString = @"Unknown";
|
||||
break;
|
||||
}
|
||||
return storageClassString;
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSCreateBucketResult
|
||||
@end
|
||||
|
||||
@implementation OSSDeleteBucketRequest
|
||||
@end
|
||||
|
||||
@implementation OSSDeleteBucketResult
|
||||
@end
|
||||
|
||||
@implementation OSSGetBucketRequest
|
||||
|
||||
- (NSDictionary *)requestParams {
|
||||
NSMutableDictionary * params = [NSMutableDictionary dictionary];
|
||||
[params oss_setObject:self.delimiter forKey:@"delimiter"];
|
||||
[params oss_setObject:self.prefix forKey:@"prefix"];
|
||||
[params oss_setObject:self.marker forKey:@"marker"];
|
||||
if (self.maxKeys > 0) {
|
||||
[params oss_setObject:[@(self.maxKeys) stringValue] forKey:@"max-keys"];
|
||||
}
|
||||
return [params copy];
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSListMultipartUploadsRequest
|
||||
- (NSDictionary *)requestParams {
|
||||
NSMutableDictionary * params = [NSMutableDictionary dictionary];
|
||||
[params oss_setObject:self.delimiter forKey:@"delimiter"];
|
||||
[params oss_setObject:self.prefix forKey:@"prefix"];
|
||||
[params oss_setObject:self.keyMarker forKey:@"key-marker"];
|
||||
[params oss_setObject:self.uploadIdMarker forKey:@"upload-id-marker"];
|
||||
[params oss_setObject:self.encodingType forKey:@"encoding-type"];
|
||||
|
||||
if (self.maxUploads > 0) {
|
||||
[params oss_setObject:[@(self.maxUploads) stringValue] forKey:@"max-uploads"];
|
||||
}
|
||||
|
||||
return [params copy];
|
||||
}
|
||||
@end
|
||||
|
||||
@implementation OSSListMultipartUploadsResult
|
||||
@end
|
||||
|
||||
@implementation OSSGetBucketResult
|
||||
@end
|
||||
|
||||
@implementation OSSGetBucketACLRequest
|
||||
|
||||
- (NSDictionary *)requestParams {
|
||||
return @{@"acl": @""};
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSGetBucketACLResult
|
||||
@end
|
||||
|
||||
@implementation OSSHeadObjectRequest
|
||||
@end
|
||||
|
||||
@implementation OSSHeadObjectResult
|
||||
@end
|
||||
|
||||
@implementation OSSGetObjectRequest
|
||||
@end
|
||||
|
||||
@implementation OSSGetObjectResult
|
||||
@end
|
||||
|
||||
@implementation OSSPutObjectACLRequest
|
||||
|
||||
- (instancetype)init
|
||||
{
|
||||
self = [super init];
|
||||
if (self) {
|
||||
_acl = @"default";
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSPutObjectACLResult
|
||||
@end
|
||||
|
||||
@implementation OSSPutObjectRequest
|
||||
|
||||
- (instancetype)init {
|
||||
if (self = [super init]) {
|
||||
self.objectMeta = [NSDictionary new];
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSPutObjectResult
|
||||
@end
|
||||
|
||||
@implementation OSSAppendObjectRequest
|
||||
|
||||
- (instancetype)init {
|
||||
if (self = [super init]) {
|
||||
self.objectMeta = [NSDictionary new];
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSAppendObjectResult
|
||||
@end
|
||||
|
||||
@implementation OSSDeleteObjectRequest
|
||||
@end
|
||||
|
||||
@implementation OSSDeleteObjectResult
|
||||
@end
|
||||
|
||||
@implementation OSSCopyObjectRequest
|
||||
|
||||
- (instancetype)init {
|
||||
if (self = [super init]) {
|
||||
self.objectMeta = [NSDictionary new];
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSCopyObjectResult
|
||||
@end
|
||||
|
||||
@implementation OSSInitMultipartUploadRequest
|
||||
|
||||
- (instancetype)init {
|
||||
if (self = [super init]) {
|
||||
self.objectMeta = [NSDictionary new];
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSInitMultipartUploadResult
|
||||
@end
|
||||
|
||||
@implementation OSSUploadPartRequest
|
||||
@end
|
||||
|
||||
@implementation OSSUploadPartResult
|
||||
@end
|
||||
|
||||
@implementation OSSPartInfo
|
||||
|
||||
+ (instancetype)partInfoWithPartNum:(int32_t)partNum
|
||||
eTag:(NSString *)eTag
|
||||
size:(int64_t)size {
|
||||
return [self partInfoWithPartNum:partNum
|
||||
eTag:eTag
|
||||
size:size
|
||||
crc64:0];
|
||||
}
|
||||
|
||||
+ (instancetype)partInfoWithPartNum:(int32_t)partNum eTag:(NSString *)eTag size:(int64_t)size crc64:(uint64_t)crc64
|
||||
{
|
||||
OSSPartInfo *parInfo = [OSSPartInfo new];
|
||||
parInfo.partNum = partNum;
|
||||
parInfo.eTag = eTag;
|
||||
parInfo.size = size;
|
||||
parInfo.crc64 = crc64;
|
||||
return parInfo;
|
||||
}
|
||||
|
||||
- (nonnull NSDictionary *)entityToDictionary
|
||||
{
|
||||
NSMutableDictionary *dict = [NSMutableDictionary dictionary];
|
||||
[dict setValue:@(_partNum) forKey:@"partNum"];
|
||||
if (_eTag)
|
||||
{
|
||||
[dict setValue:_eTag forKey:@"eTag"];
|
||||
}
|
||||
[dict setValue:@(_size) forKey:@"size"];
|
||||
[dict setValue:@(_crc64) forKey:@"crc64"];
|
||||
return [dict copy];
|
||||
}
|
||||
|
||||
- (NSString *)description
|
||||
{
|
||||
return [NSString stringWithFormat:@"OSSPartInfo<%p>:{partNum: %d,eTag: %@,partSize: %lld,crc64: %llu}",self,self.partNum,self.eTag,self.size,self.crc64];
|
||||
}
|
||||
|
||||
#pragma marks - Protocol Methods
|
||||
- (id)copyWithZone:(nullable NSZone *)zone
|
||||
{
|
||||
OSSPartInfo *instance = [[[self class] allocWithZone:zone] init];
|
||||
instance.partNum = self.partNum;
|
||||
instance.eTag = self.eTag;
|
||||
instance.size = self.size;
|
||||
instance.crc64 = self.crc64;
|
||||
return instance;
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSCompleteMultipartUploadRequest
|
||||
@end
|
||||
|
||||
@implementation OSSCompleteMultipartUploadResult
|
||||
@end
|
||||
|
||||
@implementation OSSAbortMultipartUploadRequest
|
||||
@end
|
||||
|
||||
@implementation OSSAbortMultipartUploadResult
|
||||
@end
|
||||
|
||||
@implementation OSSListPartsRequest
|
||||
@end
|
||||
|
||||
@implementation OSSListPartsResult
|
||||
@end
|
||||
|
||||
@implementation OSSMultipartUploadRequest
|
||||
|
||||
- (instancetype)init {
|
||||
if (self = [super init]) {
|
||||
self.partSize = 256 * 1024;
|
||||
self.threadNum = OSSDefaultThreadNum;
|
||||
self.terminationMode = OSSTerminationModeAll;
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
- (void)cancel {
|
||||
[super cancel];
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSResumableUploadRequest
|
||||
|
||||
- (instancetype)init {
|
||||
if (self = [super init]) {
|
||||
self.deleteUploadIdOnCancelling = YES;
|
||||
self.partSize = 256 * 1024;
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
- (void)cancel {
|
||||
[super cancel];
|
||||
if(_runningChildrenRequest){
|
||||
[_runningChildrenRequest cancel];
|
||||
}
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSResumableUploadResult
|
||||
@end
|
||||
|
||||
@implementation OSSCallBackRequest
|
||||
@end
|
||||
|
||||
@implementation OSSCallBackResult
|
||||
@end
|
||||
|
||||
@implementation OSSImagePersistRequest
|
||||
@end
|
||||
|
||||
@implementation OSSImagePersistResult
|
||||
@end
|
||||
49
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSNetworking.h
generated
Normal file
49
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSNetworking.h
generated
Normal file
@@ -0,0 +1,49 @@
|
||||
//
|
||||
// OSSNetworking.h
|
||||
// oss_ios_sdk
|
||||
//
|
||||
// Created by zhouzhuo on 8/16/15.
|
||||
// Copyright (c) 2015 aliyun.com. All rights reserved.
|
||||
//
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
#import "OSSModel.h"
|
||||
|
||||
@class OSSSyncMutableDictionary;
|
||||
@class OSSNetworkingRequestDelegate;
|
||||
@class OSSExecutor;
|
||||
|
||||
|
||||
|
||||
/**
|
||||
Network parameters
|
||||
*/
|
||||
@interface OSSNetworkingConfiguration : NSObject
|
||||
@property (nonatomic, assign) uint32_t maxRetryCount;
|
||||
@property (nonatomic, assign) uint32_t maxConcurrentRequestCount;
|
||||
@property (nonatomic, assign) BOOL enableBackgroundTransmitService;
|
||||
@property (nonatomic, strong) NSString * backgroundSessionIdentifier;
|
||||
@property (nonatomic, assign) NSTimeInterval timeoutIntervalForRequest;
|
||||
@property (nonatomic, assign) NSTimeInterval timeoutIntervalForResource;
|
||||
@property (nonatomic, strong) NSString * proxyHost;
|
||||
@property (nonatomic, strong) NSNumber * proxyPort;
|
||||
@property (nonatomic, assign) BOOL enableFollowRedirects;
|
||||
@property (nonatomic, assign) BOOL enableNetworkMetricInfo;
|
||||
@property (nonatomic, assign) uint32_t HTTPMaximumConnectionsPerHost;
|
||||
@property (nonatomic, assign) BOOL enableResetRetryCount;
|
||||
@end
|
||||
|
||||
|
||||
/**
|
||||
The network interface which OSSClient uses for network read and write operations.
|
||||
*/
|
||||
@interface OSSNetworking : NSObject <NSURLSessionDelegate, NSURLSessionDataDelegate>
|
||||
@property (nonatomic, strong) NSURLSession * session;
|
||||
@property (nonatomic, assign) BOOL isUsingBackgroundSession;
|
||||
@property (nonatomic, strong) OSSSyncMutableDictionary * sessionDelagateManager;
|
||||
@property (nonatomic, strong) OSSNetworkingConfiguration * configuration;
|
||||
@property (nonatomic, strong) OSSExecutor * taskExecutor;
|
||||
|
||||
- (instancetype)initWithConfiguration:(OSSNetworkingConfiguration *)configuration;
|
||||
- (OSSTask *)sendRequest:(OSSNetworkingRequestDelegate *)request;
|
||||
@end
|
||||
555
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSNetworking.m
generated
Normal file
555
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSNetworking.m
generated
Normal file
@@ -0,0 +1,555 @@
|
||||
//
|
||||
// OSSNetworking.m
|
||||
// oss_ios_sdk
|
||||
//
|
||||
// Created by zhouzhuo on 8/16/15.
|
||||
// Copyright (c) 2015 aliyun.com. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSDefine.h"
|
||||
#import "OSSNetworking.h"
|
||||
#import "OSSBolts.h"
|
||||
#import "OSSModel.h"
|
||||
#import "OSSUtil.h"
|
||||
#import "OSSLog.h"
|
||||
#import "OSSXMLDictionary.h"
|
||||
#import "OSSInputStreamHelper.h"
|
||||
#import "OSSNetworkingRequestDelegate.h"
|
||||
#import "OSSURLRequestRetryHandler.h"
|
||||
#import "OSSHttpResponseParser.h"
|
||||
|
||||
@implementation OSSNetworkingConfiguration
|
||||
@end
|
||||
|
||||
|
||||
@implementation OSSNetworking
|
||||
|
||||
- (instancetype)initWithConfiguration:(OSSNetworkingConfiguration *)configuration {
|
||||
if (self = [super init]) {
|
||||
self.configuration = configuration;
|
||||
NSURLSessionConfiguration * conf = nil;
|
||||
NSOperationQueue *delegateQueue = [NSOperationQueue new];
|
||||
|
||||
if (configuration.enableBackgroundTransmitService) {
|
||||
conf = [NSURLSessionConfiguration backgroundSessionConfigurationWithIdentifier:self.configuration.backgroundSessionIdentifier];
|
||||
} else {
|
||||
conf = [NSURLSessionConfiguration defaultSessionConfiguration];
|
||||
}
|
||||
conf.URLCache = nil;
|
||||
|
||||
if (configuration.timeoutIntervalForRequest > 0) {
|
||||
conf.timeoutIntervalForRequest = configuration.timeoutIntervalForRequest;
|
||||
}
|
||||
if (configuration.timeoutIntervalForResource > 0) {
|
||||
conf.timeoutIntervalForResource = configuration.timeoutIntervalForResource;
|
||||
}
|
||||
if (configuration.HTTPMaximumConnectionsPerHost > 0) {
|
||||
conf.HTTPMaximumConnectionsPerHost = configuration.HTTPMaximumConnectionsPerHost;
|
||||
}
|
||||
|
||||
if (configuration.proxyHost && configuration.proxyPort) {
|
||||
// Create an NSURLSessionConfiguration that uses the proxy
|
||||
NSDictionary *proxyDict = @{
|
||||
@"HTTPEnable" : [NSNumber numberWithInt:1],
|
||||
(NSString *)kCFStreamPropertyHTTPProxyHost : configuration.proxyHost,
|
||||
(NSString *)kCFStreamPropertyHTTPProxyPort : configuration.proxyPort,
|
||||
|
||||
@"HTTPSEnable" : [NSNumber numberWithInt:1],
|
||||
(NSString *)kCFStreamPropertyHTTPSProxyHost : configuration.proxyHost,
|
||||
(NSString *)kCFStreamPropertyHTTPSProxyPort : configuration.proxyPort,
|
||||
};
|
||||
conf.connectionProxyDictionary = proxyDict;
|
||||
}
|
||||
|
||||
_session = [NSURLSession sessionWithConfiguration:conf
|
||||
delegate:self
|
||||
delegateQueue:delegateQueue];
|
||||
|
||||
self.isUsingBackgroundSession = configuration.enableBackgroundTransmitService;
|
||||
_sessionDelagateManager = [OSSSyncMutableDictionary new];
|
||||
if (configuration.enableResetRetryCount) {
|
||||
[_sessionDelagateManager addObserverForResetCurrentRetryCount];
|
||||
}
|
||||
|
||||
NSOperationQueue * operationQueue = [NSOperationQueue new];
|
||||
if (configuration.maxConcurrentRequestCount > 0) {
|
||||
operationQueue.maxConcurrentOperationCount = configuration.maxConcurrentRequestCount;
|
||||
}
|
||||
self.taskExecutor = [OSSExecutor executorWithOperationQueue: operationQueue];
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
- (OSSTask *)sendRequest:(OSSNetworkingRequestDelegate *)request {
|
||||
OSSLogVerbose(@"send request --------");
|
||||
if (self.configuration.proxyHost && self.configuration.proxyPort) {
|
||||
request.isAccessViaProxy = YES;
|
||||
}
|
||||
|
||||
/* set maximum retry */
|
||||
request.retryHandler.maxRetryCount = self.configuration.maxRetryCount;
|
||||
|
||||
OSSTaskCompletionSource * taskCompletionSource = [OSSTaskCompletionSource taskCompletionSource];
|
||||
|
||||
__weak OSSNetworkingRequestDelegate *weakRequest= request;
|
||||
request.completionHandler = ^(id responseObject, NSError * error) {
|
||||
[weakRequest reset];
|
||||
|
||||
// 1.判断是否出错,如果出错的话,直接设置错误信息
|
||||
if (error)
|
||||
{
|
||||
if (weakRequest.metrics) {
|
||||
NSMutableDictionary *userInfo = error.userInfo ? [NSMutableDictionary dictionaryWithDictionary:error.userInfo] : [NSMutableDictionary dictionary];
|
||||
[userInfo oss_setObject:weakRequest.metrics forKey:OSSNetworkTaskMetrics];
|
||||
[taskCompletionSource setError:[NSError errorWithDomain:error.domain
|
||||
code:error.code
|
||||
userInfo:userInfo]];
|
||||
} else {
|
||||
[taskCompletionSource setError:error];
|
||||
}
|
||||
}else
|
||||
{
|
||||
[self checkForCrc64WithResult:responseObject
|
||||
requestDelegate:weakRequest
|
||||
taskCompletionSource:taskCompletionSource];
|
||||
}
|
||||
};
|
||||
[self dataTaskWithDelegate:request];
|
||||
return taskCompletionSource.task;
|
||||
}
|
||||
|
||||
- (void)checkForCrc64WithResult:(nonnull id)response requestDelegate:(OSSNetworkingRequestDelegate *)delegate taskCompletionSource:(OSSTaskCompletionSource *)source
|
||||
{
|
||||
OSSResult *result = (OSSResult *)response;
|
||||
BOOL hasRange = [delegate.internalRequest valueForHTTPHeaderField:@"Range"] != nil;
|
||||
NSURLComponents *urlComponents = [NSURLComponents componentsWithURL:delegate.internalRequest.URL resolvingAgainstBaseURL:YES];
|
||||
BOOL hasXOSSProcess = [urlComponents.query containsString:@"x-oss-process"];
|
||||
BOOL enableCRC = delegate.crc64Verifiable;
|
||||
// 3.判断如果未开启crc校验,或者headerFields里面有Range字段或者参数表中存在
|
||||
// x-oss-process字段,都将不进行crc校验
|
||||
if (!enableCRC || hasRange || hasXOSSProcess)
|
||||
{
|
||||
[source setResult:response];
|
||||
}
|
||||
else
|
||||
{
|
||||
OSSLogVerbose(@"--- checkForCrc64WithResult --- ");
|
||||
// 如果服务端未返回crc信息,默认是成功的
|
||||
OSSLogVerbose(@"result.remoteCRC64ecma : %@",result.remoteCRC64ecma);
|
||||
OSSLogVerbose(@"if result.localCRC64ecma : %@",result.localCRC64ecma);
|
||||
if (!result.remoteCRC64ecma.oss_isNotEmpty)
|
||||
{
|
||||
[source setResult:response];
|
||||
return;
|
||||
}
|
||||
// getObject 操作的crc数值会在delegate.responseParser consumeHttpResponseBody 进行计算。
|
||||
// upload & put 操作在上传成功后再计算。
|
||||
// 如果用户设置onReceiveData block。无法计算localCRC64ecma
|
||||
if (!result.localCRC64ecma.oss_isNotEmpty)
|
||||
{
|
||||
OSSLogVerbose(@"delegate.uploadingFileURL : %@",delegate.uploadingFileURL);
|
||||
if (delegate.uploadingFileURL)
|
||||
{
|
||||
OSSInputStreamHelper *helper = [[OSSInputStreamHelper alloc] initWithURL:delegate.uploadingFileURL];
|
||||
[helper syncReadBuffers];
|
||||
if (helper.crc64 != 0) {
|
||||
result.localCRC64ecma = [NSString stringWithFormat:@"%llu",helper.crc64];
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
result.localCRC64ecma = delegate.contentCRC;
|
||||
}
|
||||
OSSLogVerbose(@"finally result.localCRC64ecma : %@",result.localCRC64ecma);
|
||||
}
|
||||
|
||||
|
||||
// 针对append接口,需要多次计算crc值
|
||||
if ([delegate.lastCRC oss_isNotEmpty] && [result.localCRC64ecma oss_isNotEmpty])
|
||||
{
|
||||
uint64_t last_crc64,local_crc64;
|
||||
NSScanner *scanner = [NSScanner scannerWithString:delegate.lastCRC];
|
||||
[scanner scanUnsignedLongLong:&last_crc64];
|
||||
|
||||
scanner = [NSScanner scannerWithString:result.localCRC64ecma];
|
||||
[scanner scanUnsignedLongLong:&local_crc64];
|
||||
|
||||
NSURLComponents *urlComponents = [NSURLComponents componentsWithURL:delegate.internalRequest.URL resolvingAgainstBaseURL:YES];
|
||||
NSArray<NSString *> *params = [urlComponents.query componentsSeparatedByString:@"&"];
|
||||
|
||||
__block NSString *positionValue;
|
||||
[params enumerateObjectsUsingBlock:^(NSString *obj, NSUInteger idx, BOOL * _Nonnull stop) {
|
||||
if ([obj rangeOfString:@"position="].location == 0)
|
||||
{
|
||||
*stop = YES;
|
||||
positionValue = [obj substringFromIndex:9];
|
||||
}
|
||||
}];
|
||||
|
||||
uint64_t position = [positionValue longLongValue];
|
||||
NSString *next_append_position = [result.httpResponseHeaderFields objectForKey:@"x-oss-next-append-position"];
|
||||
uint64_t length = [next_append_position longLongValue] - position;
|
||||
|
||||
uint64_t crc_local = [OSSUtil crc64ForCombineCRC1:last_crc64 CRC2:local_crc64 length:(size_t)length];
|
||||
result.localCRC64ecma = [NSString stringWithFormat:@"%llu",crc_local];
|
||||
OSSLogVerbose(@"crc_local: %llu, crc_remote: %@,last_position: %llu,nextAppendPosition: %llu,length: %llu",crc_local,result.remoteCRC64ecma,position,[next_append_position longLongValue],length);
|
||||
}
|
||||
//如果服务器和本机计算的crc值不一致,则报crc校验失败;否则,认为上传任务执行成功
|
||||
if (result.remoteCRC64ecma.oss_isNotEmpty && result.localCRC64ecma.oss_isNotEmpty)
|
||||
{
|
||||
if ([result.remoteCRC64ecma isEqualToString:result.localCRC64ecma])
|
||||
{
|
||||
[source setResult:response];
|
||||
}else
|
||||
{
|
||||
NSString *errorMessage = [NSString stringWithFormat:@"crc validation fails(local_crc64ecma: %@,remote_crc64ecma: %@)",result.localCRC64ecma,result.remoteCRC64ecma];
|
||||
|
||||
NSError *crcError = [NSError errorWithDomain:OSSClientErrorDomain
|
||||
code:OSSClientErrorCodeInvalidCRC
|
||||
userInfo:@{OSSErrorMessageTOKEN:errorMessage}];
|
||||
[source setError:crcError];
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
[source setResult:response];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
- (void)dataTaskWithDelegate:(OSSNetworkingRequestDelegate *)requestDelegate {
|
||||
|
||||
[[[[[OSSTask taskWithResult:nil] continueWithExecutor:self.taskExecutor withSuccessBlock:^id(OSSTask *task) {
|
||||
OSSLogVerbose(@"start to intercept request");
|
||||
for (id<OSSRequestInterceptor> interceptor in requestDelegate.interceptors) {
|
||||
task = [interceptor interceptRequestMessage:requestDelegate.allNeededMessage];
|
||||
if (task.error) {
|
||||
return task;
|
||||
}
|
||||
}
|
||||
return task;
|
||||
}] continueWithSuccessBlock:^id(OSSTask *task) {
|
||||
return [requestDelegate buildInternalHttpRequest];
|
||||
}] continueWithSuccessBlock:^id(OSSTask *task) {
|
||||
NSURLSessionDataTask * sessionTask = nil;
|
||||
if (self.configuration.timeoutIntervalForRequest > 0) {
|
||||
requestDelegate.internalRequest.timeoutInterval = self.configuration.timeoutIntervalForRequest;
|
||||
}
|
||||
|
||||
if (requestDelegate.uploadingData) {
|
||||
[requestDelegate.internalRequest setHTTPBody:requestDelegate.uploadingData];
|
||||
sessionTask = [_session dataTaskWithRequest:requestDelegate.internalRequest];
|
||||
} else if (requestDelegate.uploadingFileURL) {
|
||||
sessionTask = [_session uploadTaskWithRequest:requestDelegate.internalRequest fromFile:requestDelegate.uploadingFileURL];
|
||||
|
||||
requestDelegate.isBackgroundUploadFileTask = self.isUsingBackgroundSession;
|
||||
} else { // not upload request
|
||||
sessionTask = [_session dataTaskWithRequest:requestDelegate.internalRequest];
|
||||
}
|
||||
|
||||
requestDelegate.currentSessionTask = sessionTask;
|
||||
requestDelegate.httpRequestNotSuccessResponseBody = [NSMutableData new];
|
||||
[self.sessionDelagateManager setObject:requestDelegate forKey:@(sessionTask.taskIdentifier)];
|
||||
if (requestDelegate.isRequestCancelled) {
|
||||
return [OSSTask taskWithError:[NSError errorWithDomain:OSSClientErrorDomain
|
||||
code:OSSClientErrorCodeTaskCancelled
|
||||
userInfo:nil]];
|
||||
}
|
||||
[sessionTask resume];
|
||||
|
||||
return task;
|
||||
}] continueWithBlock:^id(OSSTask *task) {
|
||||
|
||||
// if error occurs before created sessionTask
|
||||
if (task.error) {
|
||||
requestDelegate.completionHandler(nil, task.error);
|
||||
} else if (task.isFaulted) {
|
||||
requestDelegate.completionHandler(nil, [NSError errorWithDomain:OSSClientErrorDomain
|
||||
code:OSSClientErrorCodeExcpetionCatched
|
||||
userInfo:@{OSSErrorMessageTOKEN: [NSString stringWithFormat:@"Catch exception - %@", task.exception]}]);
|
||||
}
|
||||
return nil;
|
||||
}];
|
||||
}
|
||||
|
||||
#pragma mark - NSURLSessionTaskDelegate Methods
|
||||
|
||||
- (void)URLSession:(NSURLSession *)session task:(NSURLSessionTask *)sessionTask didCompleteWithError:(NSError *)error
|
||||
{
|
||||
if (error) {
|
||||
OSSLogError(@"%@,error: %@", NSStringFromSelector(_cmd), error);
|
||||
}
|
||||
|
||||
OSSNetworkingRequestDelegate * delegate = [self.sessionDelagateManager objectForKey:@(sessionTask.taskIdentifier)];
|
||||
[self.sessionDelagateManager removeObjectForKey:@(sessionTask.taskIdentifier)];
|
||||
|
||||
NSHTTPURLResponse * httpResponse = (NSHTTPURLResponse *)sessionTask.response;
|
||||
if (delegate == nil) {
|
||||
OSSLogVerbose(@"delegate: %@", delegate);
|
||||
/* if the background transfer service is enable, may recieve the previous task complete callback */
|
||||
/* for now, we ignore it */
|
||||
return ;
|
||||
}
|
||||
|
||||
/* background upload task will not call back didRecieveResponse */
|
||||
if (delegate.isBackgroundUploadFileTask) {
|
||||
OSSLogVerbose(@"backgroud upload task did recieve response: %@", httpResponse);
|
||||
if (httpResponse.statusCode >= 200 && httpResponse.statusCode < 300 && httpResponse.statusCode != 203) {
|
||||
[delegate.responseParser consumeHttpResponse:httpResponse];
|
||||
} else {
|
||||
delegate.isHttpRequestNotSuccessResponse = YES;
|
||||
}
|
||||
}
|
||||
|
||||
[[[[OSSTask taskWithResult:nil] continueWithSuccessBlock:^id(OSSTask * task) {
|
||||
if (!delegate.error) {
|
||||
delegate.error = error;
|
||||
}
|
||||
if (delegate.error) {
|
||||
OSSLogDebug(@"networking request completed with error: %@", error);
|
||||
if ([delegate.error.domain isEqualToString:NSURLErrorDomain] && delegate.error.code == NSURLErrorCancelled) {
|
||||
return [OSSTask taskWithError:[NSError errorWithDomain:OSSClientErrorDomain
|
||||
code:OSSClientErrorCodeTaskCancelled
|
||||
userInfo:[error userInfo]]];
|
||||
} else {
|
||||
NSMutableDictionary * userInfo = [NSMutableDictionary dictionaryWithDictionary:[error userInfo]];
|
||||
[userInfo setObject:[NSString stringWithFormat:@"%ld", (long)error.code] forKey:@"OriginErrorCode"];
|
||||
return [OSSTask taskWithError:[NSError errorWithDomain:OSSClientErrorDomain
|
||||
code:OSSClientErrorCodeNetworkError
|
||||
userInfo:userInfo]];
|
||||
}
|
||||
}
|
||||
return task;
|
||||
}] continueWithSuccessBlock:^id(OSSTask *task) {
|
||||
if (delegate.isHttpRequestNotSuccessResponse) {
|
||||
if (httpResponse.statusCode == 0) {
|
||||
return [OSSTask taskWithError:[NSError errorWithDomain:OSSClientErrorDomain
|
||||
code:OSSClientErrorCodeNetworkingFailWithResponseCode0
|
||||
userInfo:@{OSSErrorMessageTOKEN: @"Request failed, response code 0"}]];
|
||||
}
|
||||
NSString * notSuccessResponseBody = [[NSString alloc] initWithData:delegate.httpRequestNotSuccessResponseBody encoding:NSUTF8StringEncoding];
|
||||
OSSLogError(@"http error response: %@", notSuccessResponseBody);
|
||||
NSDictionary * dict = [NSDictionary oss_dictionaryWithXMLString:notSuccessResponseBody];
|
||||
|
||||
return [OSSTask taskWithError:[NSError errorWithDomain:OSSServerErrorDomain
|
||||
code:(-1 * httpResponse.statusCode)
|
||||
userInfo:dict]];
|
||||
}
|
||||
return task;
|
||||
}] continueWithBlock:^id(OSSTask *task) {
|
||||
if (task.error) {
|
||||
|
||||
|
||||
OSSNetworkingRetryType retryType = [delegate.retryHandler shouldRetry:delegate.currentRetryCount
|
||||
requestDelegate:delegate
|
||||
response:httpResponse
|
||||
error:task.error];
|
||||
OSSLogVerbose(@"current retry count: %u, retry type: %d", delegate.currentRetryCount, (int)retryType);
|
||||
|
||||
switch (retryType) {
|
||||
|
||||
case OSSNetworkingRetryTypeShouldNotRetry: {
|
||||
delegate.completionHandler(nil, task.error);
|
||||
return nil;
|
||||
}
|
||||
|
||||
case OSSNetworkingRetryTypeShouldCorrectClockSkewAndRetry: {
|
||||
/* correct clock skew */
|
||||
NSString * dateStr = [[httpResponse allHeaderFields] objectForKey:@"Date"];
|
||||
if ([dateStr length] > 0) {
|
||||
NSDate * serverTime = [NSDate oss_dateFromString:dateStr];
|
||||
NSDate * deviceTime = [NSDate date];
|
||||
NSTimeInterval skewTime = [deviceTime timeIntervalSinceDate:serverTime];
|
||||
[NSDate oss_setClockSkew:skewTime];
|
||||
} else if (!error) {
|
||||
// The response header does not have the 'Date' field.
|
||||
// This should not happen.
|
||||
OSSLogError(@"Date header does not exist, unable to fix the clock skew");
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
/* now, should retry */
|
||||
NSTimeInterval suspendTime = [delegate.retryHandler timeIntervalForRetry:delegate.currentRetryCount retryType:retryType];
|
||||
delegate.currentRetryCount++;
|
||||
[NSThread sleepForTimeInterval:suspendTime];
|
||||
|
||||
if(delegate.retryCallback){
|
||||
delegate.retryCallback();
|
||||
}
|
||||
|
||||
|
||||
/* retry recursively */
|
||||
[delegate reset];
|
||||
|
||||
[self dataTaskWithDelegate:delegate];
|
||||
} else {
|
||||
OSSResult *result = [delegate.responseParser constructResultObject];
|
||||
result.metrics = delegate.metrics;
|
||||
delegate.completionHandler(result, nil);
|
||||
}
|
||||
return nil;
|
||||
}];
|
||||
}
|
||||
|
||||
- (void)URLSession:(NSURLSession *)session task:(NSURLSessionTask *)task didSendBodyData:(int64_t)bytesSent totalBytesSent:(int64_t)totalBytesSent totalBytesExpectedToSend:(int64_t)totalBytesExpectedToSend
|
||||
{
|
||||
OSSNetworkingRequestDelegate * delegate = [self.sessionDelagateManager objectForKey:@(task.taskIdentifier)];
|
||||
if (delegate.uploadProgress)
|
||||
{
|
||||
delegate.uploadProgress(bytesSent, totalBytesSent, totalBytesExpectedToSend);
|
||||
}
|
||||
}
|
||||
|
||||
- (void)URLSession:(NSURLSession *)session task:(NSURLSessionTask *)task didReceiveChallenge:(NSURLAuthenticationChallenge *)challenge completionHandler:(void (^)(NSURLSessionAuthChallengeDisposition disposition, NSURLCredential * __nullable credential))completionHandler
|
||||
{
|
||||
if (!challenge) {
|
||||
return;
|
||||
}
|
||||
|
||||
NSURLSessionAuthChallengeDisposition disposition = NSURLSessionAuthChallengePerformDefaultHandling;
|
||||
NSURLCredential *credential = nil;
|
||||
|
||||
/*
|
||||
* Gets the host name
|
||||
*/
|
||||
|
||||
NSString * host = [[task.currentRequest allHTTPHeaderFields] objectForKey:@"Host"];
|
||||
if (!host) {
|
||||
host = task.currentRequest.URL.host;
|
||||
}
|
||||
|
||||
if ([challenge.protectionSpace.authenticationMethod isEqualToString:NSURLAuthenticationMethodServerTrust]) {
|
||||
if ([self evaluateServerTrust:challenge.protectionSpace.serverTrust forDomain:host]) {
|
||||
disposition = NSURLSessionAuthChallengeUseCredential;
|
||||
credential = [NSURLCredential credentialForTrust:challenge.protectionSpace.serverTrust];
|
||||
}
|
||||
} else {
|
||||
disposition = NSURLSessionAuthChallengePerformDefaultHandling;
|
||||
}
|
||||
// Uses the default evaluation for other challenges.
|
||||
completionHandler(disposition,credential);
|
||||
}
|
||||
|
||||
- (void)URLSessionDidFinishEventsForBackgroundURLSession:(NSURLSession *)session
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
- (void)URLSession:(NSURLSession *)session task:(NSURLSessionTask *)task
|
||||
willPerformHTTPRedirection:(NSHTTPURLResponse *)response
|
||||
newRequest:(NSURLRequest *)request
|
||||
completionHandler:(void (^)(NSURLRequest * _Nullable))completionHandler {
|
||||
if (self.configuration.enableFollowRedirects) {
|
||||
completionHandler(request);
|
||||
} else {
|
||||
completionHandler(nil);
|
||||
}
|
||||
}
|
||||
|
||||
- (void)URLSession:(NSURLSession *)session task:(NSURLSessionTask *)task didFinishCollectingMetrics:(NSURLSessionTaskMetrics *)metrics {
|
||||
if (self.configuration.enableNetworkMetricInfo) {
|
||||
OSSNetworkingRequestDelegate *delegate = [self.sessionDelagateManager objectForKey:@(task.taskIdentifier)];
|
||||
delegate.metrics = metrics;
|
||||
OSSLogDebug(@"%@", metrics);
|
||||
}
|
||||
}
|
||||
|
||||
#pragma mark - NSURLSessionDataDelegate Methods
|
||||
|
||||
- (void)URLSession:(NSURLSession *)session dataTask:(NSURLSessionDataTask *)dataTask didReceiveResponse:(NSURLResponse *)response completionHandler:(void (^)(NSURLSessionResponseDisposition))completionHandler
|
||||
{
|
||||
/* background upload task will not call back didRecieveResponse */
|
||||
OSSLogVerbose(@"%@,response: %@", NSStringFromSelector(_cmd), response);
|
||||
|
||||
OSSNetworkingRequestDelegate * delegate = [self.sessionDelagateManager objectForKey:@(dataTask.taskIdentifier)];
|
||||
NSHTTPURLResponse * httpResponse = (NSHTTPURLResponse *)response;
|
||||
if (httpResponse.statusCode >= 200 && httpResponse.statusCode < 300 && httpResponse.statusCode != 203) {
|
||||
[delegate.responseParser consumeHttpResponse:httpResponse];
|
||||
} else {
|
||||
delegate.isHttpRequestNotSuccessResponse = YES;
|
||||
}
|
||||
completionHandler(NSURLSessionResponseAllow);
|
||||
}
|
||||
|
||||
- (void)URLSession:(NSURLSession *)session dataTask:(NSURLSessionDataTask *)dataTask didReceiveData:(NSData *)data
|
||||
{
|
||||
OSSNetworkingRequestDelegate * delegate = [self.sessionDelagateManager objectForKey:@(dataTask.taskIdentifier)];
|
||||
|
||||
/* background upload task will not call back didRecieveResponse.
|
||||
so if we recieve response data after background uploading file,
|
||||
we consider it as error response message since a successful uploading request will not response any data */
|
||||
if (delegate.isBackgroundUploadFileTask)
|
||||
{
|
||||
//判断当前的statuscode是否成功
|
||||
NSHTTPURLResponse * httpResponse = (NSHTTPURLResponse *)dataTask.response;
|
||||
if (httpResponse.statusCode >= 200 && httpResponse.statusCode < 300 && httpResponse.statusCode != 203) {
|
||||
[delegate.responseParser consumeHttpResponse:httpResponse];
|
||||
delegate.isHttpRequestNotSuccessResponse = NO;
|
||||
}else
|
||||
{
|
||||
delegate.isHttpRequestNotSuccessResponse = YES;
|
||||
}
|
||||
}
|
||||
|
||||
if (delegate.isHttpRequestNotSuccessResponse) {
|
||||
[delegate.httpRequestNotSuccessResponseBody appendData:data];
|
||||
}
|
||||
else {
|
||||
if (delegate.onRecieveData) {
|
||||
delegate.onRecieveData(data);
|
||||
} else {
|
||||
OSSTask * consumeTask = [delegate.responseParser consumeHttpResponseBody:data];
|
||||
if (consumeTask.error) {
|
||||
OSSLogError(@"consume data error: %@", consumeTask.error);
|
||||
delegate.error = consumeTask.error;
|
||||
[dataTask cancel];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!delegate.isHttpRequestNotSuccessResponse && delegate.downloadProgress) {
|
||||
int64_t bytesWritten = [data length];
|
||||
delegate.payloadTotalBytesWritten += bytesWritten;
|
||||
int64_t totalBytesExpectedToWrite = dataTask.response.expectedContentLength;
|
||||
delegate.downloadProgress(bytesWritten, delegate.payloadTotalBytesWritten, totalBytesExpectedToWrite);
|
||||
}
|
||||
}
|
||||
|
||||
#pragma mark - Private Methods
|
||||
|
||||
- (BOOL)evaluateServerTrust:(SecTrustRef)serverTrust forDomain:(NSString *)domain {
|
||||
/*
|
||||
* Creates the policies for certificate verification.
|
||||
*/
|
||||
NSMutableArray *policies = [NSMutableArray array];
|
||||
if (domain) {
|
||||
[policies addObject:(__bridge_transfer id)SecPolicyCreateSSL(true, (__bridge CFStringRef)domain)];
|
||||
} else {
|
||||
[policies addObject:(__bridge_transfer id)SecPolicyCreateBasicX509()];
|
||||
}
|
||||
|
||||
/*
|
||||
* Sets the policies to server's certificate
|
||||
*/
|
||||
SecTrustSetPolicies(serverTrust, (__bridge CFArrayRef)policies);
|
||||
|
||||
|
||||
/*
|
||||
* Evaulates if the current serverTrust is trustable.
|
||||
* It's officially suggested that the serverTrust could be passed when result = kSecTrustResultUnspecified or kSecTrustResultProceed.
|
||||
* For more information checks out https://developer.apple.com/library/ios/technotes/tn2232/_index.html
|
||||
* For detail information about SecTrustResultType, checks out SecTrust.h
|
||||
*/
|
||||
SecTrustResultType result;
|
||||
SecTrustEvaluate(serverTrust, &result);
|
||||
|
||||
return (result == kSecTrustResultUnspecified || result == kSecTrustResultProceed);
|
||||
}
|
||||
|
||||
@end
|
||||
81
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSNetworkingRequestDelegate.h
generated
Normal file
81
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSNetworkingRequestDelegate.h
generated
Normal file
@@ -0,0 +1,81 @@
|
||||
//
|
||||
// OSSNetworkingRequestDelegate.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/1/22.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
#import "OSSConstants.h"
|
||||
#import "OSSTask.h"
|
||||
|
||||
@class OSSAllRequestNeededMessage;
|
||||
@class OSSURLRequestRetryHandler;
|
||||
@class OSSHttpResponseParser;
|
||||
|
||||
/**
|
||||
The proxy object class for each OSS request.
|
||||
*/
|
||||
@interface OSSNetworkingRequestDelegate : NSObject
|
||||
|
||||
@property (nonatomic, strong) NSMutableArray * interceptors;
|
||||
|
||||
@property (nonatomic, strong) NSMutableURLRequest *internalRequest;
|
||||
@property (nonatomic, assign) OSSOperationType operType;
|
||||
@property (nonatomic, assign) BOOL isAccessViaProxy;
|
||||
|
||||
@property (nonatomic, assign) BOOL isRequestCancelled;
|
||||
|
||||
@property (nonatomic, strong) OSSAllRequestNeededMessage *allNeededMessage;
|
||||
@property (nonatomic, strong) OSSURLRequestRetryHandler *retryHandler;
|
||||
@property (nonatomic, strong) OSSHttpResponseParser *responseParser;
|
||||
|
||||
@property (nonatomic, strong) NSData * uploadingData;
|
||||
@property (nonatomic, strong) NSURL * uploadingFileURL;
|
||||
|
||||
@property (nonatomic, assign) int64_t payloadTotalBytesWritten;
|
||||
|
||||
@property (nonatomic, assign) BOOL isBackgroundUploadFileTask;
|
||||
@property (nonatomic, assign) BOOL isHttpdnsEnable;
|
||||
|
||||
@property (nonatomic, assign) BOOL isPathStyleAccessEnable;
|
||||
@property (nonatomic, assign) BOOL isCustomPathPrefixEnable;
|
||||
@property (nonatomic, copy) NSArray * cnameExcludeList;
|
||||
|
||||
@property (nonatomic, assign) uint32_t currentRetryCount;
|
||||
@property (nonatomic, strong) NSError * error;
|
||||
@property (nonatomic, assign) BOOL isHttpRequestNotSuccessResponse;
|
||||
@property (nonatomic, strong) NSMutableData *httpRequestNotSuccessResponseBody;
|
||||
|
||||
@property (atomic, strong) NSURLSessionDataTask *currentSessionTask;
|
||||
|
||||
@property (nonatomic, strong) NSURLSessionTaskMetrics *metrics API_AVAILABLE(macos(10.12), ios(10.0));
|
||||
|
||||
@property (nonatomic, copy) OSSNetworkingUploadProgressBlock uploadProgress;
|
||||
@property (nonatomic, copy) OSSNetworkingDownloadProgressBlock downloadProgress;
|
||||
@property (nonatomic, copy) OSSNetworkingRetryBlock retryCallback;
|
||||
@property (nonatomic, copy) OSSNetworkingCompletionHandlerBlock completionHandler;
|
||||
@property (nonatomic, copy) OSSNetworkingOnRecieveDataBlock onRecieveData;
|
||||
|
||||
/**
|
||||
* when put object to server,client caculate crc64 code and assigns it to
|
||||
* this property.
|
||||
*/
|
||||
@property (nonatomic, copy) NSString *contentCRC;
|
||||
|
||||
/** last crc64 code */
|
||||
@property (nonatomic, copy) NSString *lastCRC;
|
||||
|
||||
/**
|
||||
* determine whether to verify crc64 code
|
||||
*/
|
||||
@property (nonatomic, assign) BOOL crc64Verifiable;
|
||||
|
||||
|
||||
|
||||
- (OSSTask *)buildInternalHttpRequest;
|
||||
- (void)reset;
|
||||
- (void)cancel;
|
||||
|
||||
@end
|
||||
186
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSNetworkingRequestDelegate.m
generated
Normal file
186
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSNetworkingRequestDelegate.m
generated
Normal file
@@ -0,0 +1,186 @@
|
||||
//
|
||||
// OSSNetworkingRequestDelegate.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/1/22.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSNetworkingRequestDelegate.h"
|
||||
|
||||
#import "OSSAllRequestNeededMessage.h"
|
||||
#import "OSSURLRequestRetryHandler.h"
|
||||
#import "OSSHttpResponseParser.h"
|
||||
#import "OSSDefine.h"
|
||||
#import "OSSUtil.h"
|
||||
#import "OSSLog.h"
|
||||
#import "OSSIPv6Adapter.h"
|
||||
|
||||
@implementation OSSNetworkingRequestDelegate
|
||||
|
||||
- (instancetype)init {
|
||||
if (self = [super init]) {
|
||||
self.retryHandler = [OSSURLRequestRetryHandler defaultRetryHandler];
|
||||
self.interceptors = [[NSMutableArray alloc] init];
|
||||
self.isHttpdnsEnable = YES;
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
- (void)reset {
|
||||
self.isHttpRequestNotSuccessResponse = NO;
|
||||
self.error = nil;
|
||||
self.payloadTotalBytesWritten = 0;
|
||||
self.isRequestCancelled = NO;
|
||||
[self.responseParser reset];
|
||||
}
|
||||
|
||||
- (void)cancel {
|
||||
self.isRequestCancelled = YES;
|
||||
if (self.currentSessionTask) {
|
||||
OSSLogDebug(@"this task is cancelled now!");
|
||||
[self.currentSessionTask cancel];
|
||||
}
|
||||
}
|
||||
|
||||
- (OSSTask *)validateRequestParams {
|
||||
NSString * errorMessage = nil;
|
||||
|
||||
if ((self.operType == OSSOperationTypeAppendObject || self.operType == OSSOperationTypePutObject || self.operType == OSSOperationTypeUploadPart)
|
||||
&& !self.uploadingData && !self.uploadingFileURL) {
|
||||
errorMessage = @"This operation need data or file to upload but none is set";
|
||||
}
|
||||
|
||||
if (self.uploadingFileURL && ![[NSFileManager defaultManager] fileExistsAtPath:[self.uploadingFileURL path]]) {
|
||||
errorMessage = @"File doesn't exist";
|
||||
}
|
||||
|
||||
if (errorMessage) {
|
||||
return [OSSTask taskWithError:[NSError errorWithDomain:OSSClientErrorDomain
|
||||
code:OSSClientErrorCodeInvalidArgument
|
||||
userInfo:@{OSSErrorMessageTOKEN: errorMessage}]];
|
||||
} else {
|
||||
return [self.allNeededMessage validateRequestParamsInOperationType:self.operType];
|
||||
}
|
||||
}
|
||||
|
||||
- (OSSTask *)buildInternalHttpRequest {
|
||||
|
||||
OSSTask * validateParam = [self validateRequestParams];
|
||||
if (validateParam.error) {
|
||||
return validateParam;
|
||||
}
|
||||
|
||||
#define URLENCODE(a) [OSSUtil encodeURL:(a)]
|
||||
OSSLogDebug(@"start to build request")
|
||||
// build base url string
|
||||
NSString *bucketName = self.allNeededMessage.bucketName;
|
||||
NSString *objectKey = self.allNeededMessage.objectKey;
|
||||
NSString *urlString = self.allNeededMessage.endpoint;
|
||||
NSURLComponents *urlComponents = [[NSURLComponents alloc] initWithString:urlString];
|
||||
NSString *headerHost = nil;
|
||||
BOOL isPathStyle = NO;
|
||||
|
||||
NSURLComponents *temComs = [NSURLComponents new];
|
||||
temComs.scheme = urlComponents.scheme;
|
||||
temComs.host = urlComponents.host;
|
||||
temComs.port = urlComponents.port;
|
||||
if (self.isCustomPathPrefixEnable) {
|
||||
temComs.path = urlComponents.path;
|
||||
}
|
||||
|
||||
if ([self.allNeededMessage.bucketName oss_isNotEmpty]) {
|
||||
OSSIPv6Adapter *ipAdapter = [OSSIPv6Adapter getInstance];
|
||||
if ([OSSUtil isOssOriginBucketHost:temComs.host]) {
|
||||
// eg. insert bucket to the begining of host.
|
||||
temComs.host = [NSString stringWithFormat:@"%@.%@", self.allNeededMessage.bucketName, temComs.host];
|
||||
headerHost = temComs.host;
|
||||
if ([temComs.scheme.lowercaseString isEqualToString:@"http"] && self.isHttpdnsEnable) {
|
||||
NSString *dnsResult = [OSSUtil getIpByHost: temComs.host];
|
||||
temComs.host = dnsResult;
|
||||
}
|
||||
} else if (self.allNeededMessage.isHostInCnameExcludeList) {
|
||||
if (self.isPathStyleAccessEnable) {
|
||||
isPathStyle = YES;
|
||||
} else {
|
||||
temComs.host = [NSString stringWithFormat:@"%@.%@", self.allNeededMessage.bucketName, temComs.host];
|
||||
}
|
||||
} else if ([ipAdapter isIPv4Address:temComs.host] || [ipAdapter isIPv6Address:temComs.host]) {
|
||||
isPathStyle = YES;
|
||||
}
|
||||
}
|
||||
|
||||
urlString = temComs.string;
|
||||
|
||||
if (isPathStyle) {
|
||||
urlString = [NSString stringWithFormat:@"%@/%@", urlString, bucketName];
|
||||
}
|
||||
// join object name
|
||||
if ([self.allNeededMessage.objectKey oss_isNotEmpty]) {
|
||||
urlString = [urlString oss_stringByAppendingPathComponentForURL:URLENCODE(self.allNeededMessage.objectKey)];
|
||||
}
|
||||
|
||||
// join query string
|
||||
if (self.allNeededMessage.params) {
|
||||
NSMutableArray * querys = [[NSMutableArray alloc] init];
|
||||
for (NSString * key in [self.allNeededMessage.params allKeys]) {
|
||||
NSString * value = [self.allNeededMessage.params objectForKey:key];
|
||||
if (value) {
|
||||
if ([value isEqualToString:@""]) {
|
||||
[querys addObject:URLENCODE(key)];
|
||||
} else {
|
||||
[querys addObject:[NSString stringWithFormat:@"%@=%@", URLENCODE(key), URLENCODE(value)]];
|
||||
}
|
||||
}
|
||||
}
|
||||
if (querys && [querys count]) {
|
||||
NSString * queryString = [querys componentsJoinedByString:@"&"];
|
||||
urlString = [NSString stringWithFormat:@"%@?%@", urlString, queryString];
|
||||
}
|
||||
}
|
||||
|
||||
OSSLogDebug(@"built full url: %@", urlString)
|
||||
|
||||
// generate internal request For NSURLSession
|
||||
self.internalRequest = [NSMutableURLRequest requestWithURL:[NSURL URLWithString:urlString]];
|
||||
|
||||
// set http method of request
|
||||
if (self.allNeededMessage.httpMethod) {
|
||||
[self.internalRequest setHTTPMethod:self.allNeededMessage.httpMethod];
|
||||
}
|
||||
|
||||
// set host of header fields
|
||||
if ([headerHost oss_isNotEmpty]) {
|
||||
[self.internalRequest setValue:headerHost forHTTPHeaderField:@"Host"];
|
||||
}
|
||||
|
||||
if (self.allNeededMessage.contentType) {
|
||||
[self.internalRequest setValue:self.allNeededMessage.contentType forHTTPHeaderField:@"Content-Type"];
|
||||
}
|
||||
if (self.allNeededMessage.contentMd5) {
|
||||
[self.internalRequest setValue:self.allNeededMessage.contentMd5 forHTTPHeaderField:@"Content-MD5"];
|
||||
}
|
||||
if (self.allNeededMessage.date) {
|
||||
[self.internalRequest setValue:self.allNeededMessage.date forHTTPHeaderField:@"Date"];
|
||||
}
|
||||
if (self.allNeededMessage.range) {
|
||||
[self.internalRequest setValue:self.allNeededMessage.range forHTTPHeaderField:@"Range"];
|
||||
}
|
||||
if (self.allNeededMessage.contentSHA1) {
|
||||
[self.internalRequest setValue:_allNeededMessage.contentSHA1 forHTTPHeaderField:@"x-oss-hash-sha1"];
|
||||
}
|
||||
if (self.allNeededMessage.headerParams) {
|
||||
for (NSString * key in [self.allNeededMessage.headerParams allKeys]) {
|
||||
[self.internalRequest setValue:[self.allNeededMessage.headerParams objectForKey:key] forHTTPHeaderField:key];
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
OSSLogVerbose(@"buidlInternalHttpRequest -\nmethod: %@\nurl: %@\nheader: %@", self.internalRequest.HTTPMethod,
|
||||
self.internalRequest.URL, self.internalRequest.allHTTPHeaderFields)
|
||||
|
||||
#undef URLENCODE//(a)
|
||||
return [OSSTask taskWithResult:nil];
|
||||
}
|
||||
|
||||
@end
|
||||
27
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSPutObjectTaggingRequest.h
generated
Normal file
27
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSPutObjectTaggingRequest.h
generated
Normal file
@@ -0,0 +1,27 @@
|
||||
//
|
||||
// OSSPutObjectTaggingRequest.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by ws on 2021/5/25.
|
||||
// Copyright © 2021 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSRequest.h"
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
@interface OSSPutObjectTaggingRequest : OSSRequest
|
||||
|
||||
/* bucket name */
|
||||
@property (nonatomic, copy) NSString *bucketName;
|
||||
|
||||
/* object name */
|
||||
@property (nonatomic, copy) NSString *objectKey;
|
||||
|
||||
@property (nonatomic, copy) NSDictionary *tags;
|
||||
|
||||
- (NSDictionary *)entityToDictionary;
|
||||
|
||||
@end
|
||||
|
||||
NS_ASSUME_NONNULL_END
|
||||
29
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSPutObjectTaggingRequest.m
generated
Normal file
29
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSPutObjectTaggingRequest.m
generated
Normal file
@@ -0,0 +1,29 @@
|
||||
//
|
||||
// OSSPutObjectTaggingRequest.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by ws on 2021/5/25.
|
||||
// Copyright © 2021 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSPutObjectTaggingRequest.h"
|
||||
|
||||
@implementation OSSPutObjectTaggingRequest
|
||||
|
||||
- (NSDictionary *)requestParams {
|
||||
return @{@"tagging": @""};
|
||||
}
|
||||
|
||||
- (NSDictionary *)entityToDictionary {
|
||||
NSMutableArray *tags = [NSMutableArray array];
|
||||
for (NSString *key in [self.tags allKeys]) {
|
||||
NSString *value = self.tags[key];
|
||||
NSDictionary *tag = @{@"Tag": @{@"Key":key,
|
||||
@"Value": value}};
|
||||
[tags addObject:tag];
|
||||
}
|
||||
NSDictionary *entity = @{@"Tagging": @{@"TagSet": tags}};
|
||||
return entity;
|
||||
}
|
||||
|
||||
@end
|
||||
17
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSPutObjectTaggingResult.h
generated
Normal file
17
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSPutObjectTaggingResult.h
generated
Normal file
@@ -0,0 +1,17 @@
|
||||
//
|
||||
// OSSPutObjectTaggingResult.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by ws on 2021/5/25.
|
||||
// Copyright © 2021 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSResult.h"
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
@interface OSSPutObjectTaggingResult : OSSResult
|
||||
|
||||
@end
|
||||
|
||||
NS_ASSUME_NONNULL_END
|
||||
13
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSPutObjectTaggingResult.m
generated
Normal file
13
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSPutObjectTaggingResult.m
generated
Normal file
@@ -0,0 +1,13 @@
|
||||
//
|
||||
// OSSPutObjectTaggingResult.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by ws on 2021/5/25.
|
||||
// Copyright © 2021 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSPutObjectTaggingResult.h"
|
||||
|
||||
@implementation OSSPutObjectTaggingResult
|
||||
|
||||
@end
|
||||
25
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSPutSymlinkRequest.h
generated
Normal file
25
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSPutSymlinkRequest.h
generated
Normal file
@@ -0,0 +1,25 @@
|
||||
//
|
||||
// OSSPutSymlinkRequest.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/8/1.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSRequest.h"
|
||||
|
||||
@interface OSSPutSymlinkRequest : OSSRequest
|
||||
|
||||
/* bucket name */
|
||||
@property (nonatomic, copy) NSString *bucketName;
|
||||
|
||||
/* object name */
|
||||
@property (nonatomic, copy) NSString *objectKey;
|
||||
|
||||
/* target object name */
|
||||
@property (nonatomic, copy) NSString *targetObjectName;
|
||||
|
||||
/* meta info in request header fields */
|
||||
@property (nonatomic, copy) NSDictionary *objectMeta;
|
||||
|
||||
@end
|
||||
17
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSPutSymlinkRequest.m
generated
Normal file
17
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSPutSymlinkRequest.m
generated
Normal file
@@ -0,0 +1,17 @@
|
||||
//
|
||||
// OSSPutSymlinkRequest.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/8/1.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSPutSymlinkRequest.h"
|
||||
|
||||
@implementation OSSPutSymlinkRequest
|
||||
|
||||
- (NSDictionary *)requestParams {
|
||||
return @{@"symlink": @""};
|
||||
}
|
||||
|
||||
@end
|
||||
13
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSPutSymlinkResult.h
generated
Normal file
13
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSPutSymlinkResult.h
generated
Normal file
@@ -0,0 +1,13 @@
|
||||
//
|
||||
// OSSPutSymlinkResult.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/8/1.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSResult.h"
|
||||
|
||||
@interface OSSPutSymlinkResult : OSSResult
|
||||
|
||||
@end
|
||||
13
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSPutSymlinkResult.m
generated
Normal file
13
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSPutSymlinkResult.m
generated
Normal file
@@ -0,0 +1,13 @@
|
||||
//
|
||||
// OSSPutSymlinkResult.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/8/1.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSPutSymlinkResult.h"
|
||||
|
||||
@implementation OSSPutSymlinkResult
|
||||
|
||||
@end
|
||||
41
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSRequest.h
generated
Normal file
41
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSRequest.h
generated
Normal file
@@ -0,0 +1,41 @@
|
||||
//
|
||||
// OSSRequest.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/1/22.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
#import "OSSConstants.h"
|
||||
|
||||
/**
|
||||
The base class of request to OSS.
|
||||
*/
|
||||
@interface OSSRequest : NSObject
|
||||
/**
|
||||
Flag of requiring authentication. It's per each request.
|
||||
*/
|
||||
@property (nonatomic, assign) BOOL isAuthenticationRequired;
|
||||
|
||||
/**
|
||||
the flag of request canceled.
|
||||
*/
|
||||
@property (atomic, assign) BOOL isCancelled;
|
||||
|
||||
/**
|
||||
the flag of verification about crc64
|
||||
*/
|
||||
@property (nonatomic, assign) OSSRequestCRCFlag crcFlag;
|
||||
|
||||
/**
|
||||
Cancels the request
|
||||
*/
|
||||
- (void)cancel;
|
||||
|
||||
/**
|
||||
Gets the query parameters' dictionary according to the properties.
|
||||
*/
|
||||
- (NSDictionary *)requestParams;
|
||||
|
||||
@end
|
||||
41
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSRequest.m
generated
Normal file
41
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSRequest.m
generated
Normal file
@@ -0,0 +1,41 @@
|
||||
//
|
||||
// OSSRequest.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/1/22.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSRequest.h"
|
||||
#import "OSSNetworkingRequestDelegate.h"
|
||||
|
||||
@interface OSSRequest ()
|
||||
|
||||
@property (nonatomic, strong) OSSNetworkingRequestDelegate *requestDelegate;
|
||||
|
||||
@end
|
||||
|
||||
|
||||
@implementation OSSRequest
|
||||
|
||||
- (instancetype)init {
|
||||
if (self = [super init]) {
|
||||
self.requestDelegate = [OSSNetworkingRequestDelegate new];
|
||||
self.isAuthenticationRequired = YES;
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
- (void)cancel {
|
||||
self.isCancelled = YES;
|
||||
|
||||
if (self.requestDelegate) {
|
||||
[self.requestDelegate cancel];
|
||||
}
|
||||
}
|
||||
|
||||
- (NSDictionary *)requestParams {
|
||||
return nil;
|
||||
}
|
||||
|
||||
@end
|
||||
17
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSRestoreObjectRequest.h
generated
Normal file
17
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSRestoreObjectRequest.h
generated
Normal file
@@ -0,0 +1,17 @@
|
||||
//
|
||||
// OSSRestoreObjectRequest.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/8/1.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSRequest.h"
|
||||
|
||||
@interface OSSRestoreObjectRequest : OSSRequest
|
||||
|
||||
@property (nonatomic, copy) NSString *bucketName;
|
||||
|
||||
@property (nonatomic, copy) NSString *objectKey;
|
||||
|
||||
@end
|
||||
17
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSRestoreObjectRequest.m
generated
Normal file
17
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSRestoreObjectRequest.m
generated
Normal file
@@ -0,0 +1,17 @@
|
||||
//
|
||||
// OSSRestoreObjectRequest.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/8/1.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSRestoreObjectRequest.h"
|
||||
|
||||
@implementation OSSRestoreObjectRequest
|
||||
|
||||
- (NSDictionary *)requestParams {
|
||||
return @{@"restore": @""};
|
||||
}
|
||||
|
||||
@end
|
||||
13
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSRestoreObjectResult.h
generated
Normal file
13
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSRestoreObjectResult.h
generated
Normal file
@@ -0,0 +1,13 @@
|
||||
//
|
||||
// OSSRestoreObjectResult.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/8/1.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSResult.h"
|
||||
|
||||
@interface OSSRestoreObjectResult : OSSResult
|
||||
|
||||
@end
|
||||
13
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSRestoreObjectResult.m
generated
Normal file
13
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSRestoreObjectResult.m
generated
Normal file
@@ -0,0 +1,13 @@
|
||||
//
|
||||
// OSSRestoreObjectResult.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/8/1.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSRestoreObjectResult.h"
|
||||
|
||||
@implementation OSSRestoreObjectResult
|
||||
|
||||
@end
|
||||
45
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSResult.h
generated
Normal file
45
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSResult.h
generated
Normal file
@@ -0,0 +1,45 @@
|
||||
//
|
||||
// OSSResult.h
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/1/26.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
|
||||
/**
|
||||
The base class of result from OSS.
|
||||
*/
|
||||
@interface OSSResult : NSObject
|
||||
|
||||
/**
|
||||
The http response code.
|
||||
*/
|
||||
@property (nonatomic, assign) NSInteger httpResponseCode;
|
||||
|
||||
/**
|
||||
The http headers, in the form of key value dictionary.
|
||||
*/
|
||||
@property (nonatomic, strong) NSDictionary * httpResponseHeaderFields;
|
||||
|
||||
/**
|
||||
The request Id. It's the value of header x-oss-request-id, which is created from OSS server.
|
||||
It's a unique Id represents this request. This is used for troubleshooting when you contact OSS support.
|
||||
*/
|
||||
@property (nonatomic, strong) NSString * requestId;
|
||||
|
||||
/**
|
||||
It's the value of header x-oss-hash-crc64ecma, which is created from OSS server.
|
||||
*/
|
||||
@property (nonatomic, copy) NSString *remoteCRC64ecma;
|
||||
|
||||
/**
|
||||
It's the value of local Data.
|
||||
*/
|
||||
@property (nonatomic, copy) NSString *localCRC64ecma;
|
||||
|
||||
/// statistics information for the task.
|
||||
@property (nonatomic, strong) NSURLSessionTaskMetrics *metrics API_AVAILABLE(macos(10.12), ios(10.0));
|
||||
|
||||
@end
|
||||
18
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSResult.m
generated
Normal file
18
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSResult.m
generated
Normal file
@@ -0,0 +1,18 @@
|
||||
//
|
||||
// OSSResult.m
|
||||
// AliyunOSSSDK
|
||||
//
|
||||
// Created by huaixu on 2018/1/26.
|
||||
// Copyright © 2018年 aliyun. All rights reserved.
|
||||
//
|
||||
|
||||
#import "OSSResult.h"
|
||||
|
||||
@implementation OSSResult
|
||||
|
||||
- (NSString *)description
|
||||
{
|
||||
return [NSString stringWithFormat:@"OSSResult<%p> : {httpResponseCode: %ld, requestId: %@, httpResponseHeaderFields: %@, local_crc64ecma: %@}",self,(long)self.httpResponseCode,self.requestId,self.httpResponseHeaderFields,self.localCRC64ecma];
|
||||
}
|
||||
|
||||
@end
|
||||
46
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSService.h
generated
Normal file
46
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSService.h
generated
Normal file
@@ -0,0 +1,46 @@
|
||||
//
|
||||
// OSSService.h
|
||||
// oss_ios_sdk
|
||||
//
|
||||
// Created by zhouzhuo on 8/20/15.
|
||||
// Copyright (c) 2015 aliyun.com. All rights reserved.
|
||||
//
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
|
||||
#define OSS_IOS_SDK_VERSION OSSSDKVersion
|
||||
|
||||
#import "OSSDefine.h"
|
||||
#import "OSSConstants.h"
|
||||
|
||||
#import "OSSNetworking.h"
|
||||
#import "OSSNetworkingRequestDelegate.h"
|
||||
#import "OSSAllRequestNeededMessage.h"
|
||||
#import "OSSURLRequestRetryHandler.h"
|
||||
#import "OSSHttpResponseParser.h"
|
||||
#import "OSSRequest.h"
|
||||
#import "OSSGetObjectACLRequest.h"
|
||||
#import "OSSGetObjectACLResult.h"
|
||||
#import "OSSDeleteMultipleObjectsRequest.h"
|
||||
#import "OSSDeleteMultipleObjectsResult.h"
|
||||
#import "OSSGetBucketInfoRequest.h"
|
||||
#import "OSSGetBucketInfoResult.h"
|
||||
#import "OSSPutSymlinkRequest.h"
|
||||
#import "OSSPutSymlinkResult.h"
|
||||
#import "OSSGetSymlinkRequest.h"
|
||||
#import "OSSGetSymlinkResult.h"
|
||||
#import "OSSRestoreObjectRequest.h"
|
||||
#import "OSSRestoreObjectResult.h"
|
||||
#import "OSSGetObjectTaggingRequest.h"
|
||||
#import "OSSGetObjectTaggingResult.h"
|
||||
#import "OSSPutObjectTaggingRequest.h"
|
||||
#import "OSSPutObjectTaggingResult.h"
|
||||
#import "OSSDeleteObjectTaggingRequest.h"
|
||||
#import "OSSDeleteObjectTaggingResult.h"
|
||||
|
||||
#import "OSSClient.h"
|
||||
#import "OSSModel.h"
|
||||
#import "OSSUtil.h"
|
||||
#import "OSSLog.h"
|
||||
|
||||
#import "OSSBolts.h"
|
||||
26
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSTask/OSSBolts.h
generated
Normal file
26
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSTask/OSSBolts.h
generated
Normal file
@@ -0,0 +1,26 @@
|
||||
/*
|
||||
* Copyright (c) 2014, Facebook, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* This source code is licensed under the BSD-style license found in the
|
||||
* LICENSE file in the root directory of this source tree. An additional grant
|
||||
* of patent rights can be found in the PATENTS file in the same directory.
|
||||
*
|
||||
*/
|
||||
|
||||
#import "OSSCancellationToken.h"
|
||||
#import "OSSCancellationTokenRegistration.h"
|
||||
#import "OSSCancellationTokenSource.h"
|
||||
#import "OSSExecutor.h"
|
||||
#import "OSSTask.h"
|
||||
#import "OSSTaskCompletionSource.h"
|
||||
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
/**
|
||||
A string containing the version of the Bolts Framework used by the current application.
|
||||
*/
|
||||
extern NSString *const OSSBoltsFrameworkVersionString;
|
||||
|
||||
NS_ASSUME_NONNULL_END
|
||||
17
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSTask/OSSBolts.m
generated
Normal file
17
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSTask/OSSBolts.m
generated
Normal file
@@ -0,0 +1,17 @@
|
||||
/*
|
||||
* Copyright (c) 2014, Facebook, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* This source code is licensed under the BSD-style license found in the
|
||||
* LICENSE file in the root directory of this source tree. An additional grant
|
||||
* of patent rights can be found in the PATENTS file in the same directory.
|
||||
*
|
||||
*/
|
||||
|
||||
#import "OSSBolts.h"
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
NSString *const OSSBoltsFrameworkVersionString = @"1.7.0";
|
||||
|
||||
NS_ASSUME_NONNULL_END
|
||||
42
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSTask/OSSCancellationToken.h
generated
Normal file
42
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSTask/OSSCancellationToken.h
generated
Normal file
@@ -0,0 +1,42 @@
|
||||
/*
|
||||
* Copyright (c) 2014, Facebook, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* This source code is licensed under the BSD-style license found in the
|
||||
* LICENSE file in the root directory of this source tree. An additional grant
|
||||
* of patent rights can be found in the PATENTS file in the same directory.
|
||||
*
|
||||
*/
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
|
||||
#import "OSSCancellationTokenRegistration.h"
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
/*!
|
||||
A block that will be called when a token is cancelled.
|
||||
*/
|
||||
typedef void(^OSSCancellationBlock)(void);
|
||||
|
||||
/*!
|
||||
The consumer view of a CancellationToken.
|
||||
Propagates notification that operations should be canceled.
|
||||
A OSSCancellationToken has methods to inspect whether the token has been cancelled.
|
||||
*/
|
||||
@interface OSSCancellationToken : NSObject
|
||||
|
||||
/*!
|
||||
Whether cancellation has been requested for this token source.
|
||||
*/
|
||||
@property (nonatomic, assign, readonly, getter=isCancellationRequested) BOOL cancellationRequested;
|
||||
|
||||
/*!
|
||||
Register a block to be notified when the token is cancelled.
|
||||
If the token is already cancelled the delegate will be notified immediately.
|
||||
*/
|
||||
- (OSSCancellationTokenRegistration *)registerCancellationObserverWithBlock:(OSSCancellationBlock)block;
|
||||
|
||||
@end
|
||||
|
||||
NS_ASSUME_NONNULL_END
|
||||
144
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSTask/OSSCancellationToken.m
generated
Normal file
144
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSTask/OSSCancellationToken.m
generated
Normal file
@@ -0,0 +1,144 @@
|
||||
/*
|
||||
* Copyright (c) 2014, Facebook, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* This source code is licensed under the BSD-style license found in the
|
||||
* LICENSE file in the root directory of this source tree. An additional grant
|
||||
* of patent rights can be found in the PATENTS file in the same directory.
|
||||
*
|
||||
*/
|
||||
|
||||
#import "OSSCancellationToken.h"
|
||||
#import "OSSCancellationTokenRegistration.h"
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
@interface OSSCancellationToken ()
|
||||
|
||||
@property (nullable, nonatomic, strong) NSMutableArray *registrations;
|
||||
@property (nonatomic, strong) NSObject *lock;
|
||||
@property (nonatomic) BOOL disposed;
|
||||
|
||||
@end
|
||||
|
||||
@interface OSSCancellationTokenRegistration (OSSCancellationToken)
|
||||
|
||||
+ (instancetype)registrationWithToken:(OSSCancellationToken *)token delegate:(OSSCancellationBlock)delegate;
|
||||
|
||||
- (void)notifyDelegate;
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSCancellationToken
|
||||
|
||||
@synthesize cancellationRequested = _cancellationRequested;
|
||||
|
||||
#pragma mark - Initializer
|
||||
|
||||
- (instancetype)init {
|
||||
self = [super init];
|
||||
if (!self) return self;
|
||||
|
||||
_registrations = [NSMutableArray array];
|
||||
_lock = [NSObject new];
|
||||
|
||||
return self;
|
||||
}
|
||||
|
||||
#pragma mark - Custom Setters/Getters
|
||||
|
||||
- (BOOL)isCancellationRequested {
|
||||
@synchronized(self.lock) {
|
||||
[self throwIfDisposed];
|
||||
return _cancellationRequested;
|
||||
}
|
||||
}
|
||||
|
||||
- (void)cancel {
|
||||
NSArray *registrations;
|
||||
@synchronized(self.lock) {
|
||||
[self throwIfDisposed];
|
||||
if (_cancellationRequested) {
|
||||
return;
|
||||
}
|
||||
[NSObject cancelPreviousPerformRequestsWithTarget:self selector:@selector(cancelPrivate) object:nil];
|
||||
_cancellationRequested = YES;
|
||||
registrations = [self.registrations copy];
|
||||
}
|
||||
|
||||
[self notifyCancellation:registrations];
|
||||
}
|
||||
|
||||
- (void)notifyCancellation:(NSArray *)registrations {
|
||||
for (OSSCancellationTokenRegistration *registration in registrations) {
|
||||
[registration notifyDelegate];
|
||||
}
|
||||
}
|
||||
|
||||
- (OSSCancellationTokenRegistration *)registerCancellationObserverWithBlock:(OSSCancellationBlock)block {
|
||||
@synchronized(self.lock) {
|
||||
OSSCancellationTokenRegistration *registration = [OSSCancellationTokenRegistration registrationWithToken:self delegate:[block copy]];
|
||||
[self.registrations addObject:registration];
|
||||
|
||||
return registration;
|
||||
}
|
||||
}
|
||||
|
||||
- (void)unregisterRegistration:(OSSCancellationTokenRegistration *)registration {
|
||||
@synchronized(self.lock) {
|
||||
[self throwIfDisposed];
|
||||
[self.registrations removeObject:registration];
|
||||
}
|
||||
}
|
||||
|
||||
// Delay on a non-public method to prevent interference with a user calling performSelector or
|
||||
// cancelPreviousPerformRequestsWithTarget on the public method
|
||||
- (void)cancelPrivate {
|
||||
[self cancel];
|
||||
}
|
||||
|
||||
- (void)cancelAfterDelay:(int)millis {
|
||||
[self throwIfDisposed];
|
||||
if (millis < -1) {
|
||||
[NSException raise:NSInvalidArgumentException format:@"Delay must be >= -1"];
|
||||
}
|
||||
|
||||
if (millis == 0) {
|
||||
[self cancel];
|
||||
return;
|
||||
}
|
||||
|
||||
@synchronized(self.lock) {
|
||||
[self throwIfDisposed];
|
||||
[NSObject cancelPreviousPerformRequestsWithTarget:self selector:@selector(cancelPrivate) object:nil];
|
||||
if (self.cancellationRequested) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (millis != -1) {
|
||||
double delay = (double)millis / 1000;
|
||||
[self performSelector:@selector(cancelPrivate) withObject:nil afterDelay:delay];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
- (void)dispose {
|
||||
@synchronized(self.lock) {
|
||||
if (self.disposed) {
|
||||
return;
|
||||
}
|
||||
[self.registrations makeObjectsPerformSelector:@selector(dispose)];
|
||||
self.registrations = nil;
|
||||
self.disposed = YES;
|
||||
}
|
||||
}
|
||||
|
||||
- (void)throwIfDisposed {
|
||||
if (self.disposed) {
|
||||
[NSException raise:NSInternalInconsistencyException format:@"Object already disposed"];
|
||||
}
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
NS_ASSUME_NONNULL_END
|
||||
29
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSTask/OSSCancellationTokenRegistration.h
generated
Normal file
29
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSTask/OSSCancellationTokenRegistration.h
generated
Normal file
@@ -0,0 +1,29 @@
|
||||
/*
|
||||
* Copyright (c) 2014, Facebook, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* This source code is licensed under the BSD-style license found in the
|
||||
* LICENSE file in the root directory of this source tree. An additional grant
|
||||
* of patent rights can be found in the PATENTS file in the same directory.
|
||||
*
|
||||
*/
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
/*!
|
||||
Represents the registration of a cancellation observer with a cancellation token.
|
||||
Can be used to unregister the observer at a later time.
|
||||
*/
|
||||
@interface OSSCancellationTokenRegistration : NSObject
|
||||
|
||||
/*!
|
||||
Removes the cancellation observer registered with the token
|
||||
and releases all resources associated with this registration.
|
||||
*/
|
||||
- (void)dispose;
|
||||
|
||||
@end
|
||||
|
||||
NS_ASSUME_NONNULL_END
|
||||
79
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSTask/OSSCancellationTokenRegistration.m
generated
Normal file
79
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSTask/OSSCancellationTokenRegistration.m
generated
Normal file
@@ -0,0 +1,79 @@
|
||||
/*
|
||||
* Copyright (c) 2014, Facebook, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* This source code is licensed under the BSD-style license found in the
|
||||
* LICENSE file in the root directory of this source tree. An additional grant
|
||||
* of patent rights can be found in the PATENTS file in the same directory.
|
||||
*
|
||||
*/
|
||||
|
||||
#import "OSSCancellationTokenRegistration.h"
|
||||
|
||||
#import "OSSCancellationToken.h"
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
@interface OSSCancellationTokenRegistration ()
|
||||
|
||||
@property (nonatomic, weak) OSSCancellationToken *token;
|
||||
@property (nullable, nonatomic, strong) OSSCancellationBlock cancellationObserverBlock;
|
||||
@property (nonatomic, strong) NSObject *lock;
|
||||
@property (nonatomic) BOOL disposed;
|
||||
|
||||
@end
|
||||
|
||||
@interface OSSCancellationToken (OSSCancellationTokenRegistration)
|
||||
|
||||
- (void)unregisterRegistration:(OSSCancellationTokenRegistration *)registration;
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSCancellationTokenRegistration
|
||||
|
||||
+ (instancetype)registrationWithToken:(OSSCancellationToken *)token delegate:(OSSCancellationBlock)delegate {
|
||||
OSSCancellationTokenRegistration *registration = [OSSCancellationTokenRegistration new];
|
||||
registration.token = token;
|
||||
registration.cancellationObserverBlock = delegate;
|
||||
return registration;
|
||||
}
|
||||
|
||||
- (instancetype)init {
|
||||
self = [super init];
|
||||
if (!self) return self;
|
||||
|
||||
_lock = [NSObject new];
|
||||
|
||||
return self;
|
||||
}
|
||||
|
||||
- (void)dispose {
|
||||
@synchronized(self.lock) {
|
||||
if (self.disposed) {
|
||||
return;
|
||||
}
|
||||
self.disposed = YES;
|
||||
}
|
||||
|
||||
OSSCancellationToken *token = self.token;
|
||||
if (token != nil) {
|
||||
[token unregisterRegistration:self];
|
||||
self.token = nil;
|
||||
}
|
||||
self.cancellationObserverBlock = nil;
|
||||
}
|
||||
|
||||
- (void)notifyDelegate {
|
||||
@synchronized(self.lock) {
|
||||
[self throwIfDisposed];
|
||||
self.cancellationObserverBlock();
|
||||
}
|
||||
}
|
||||
|
||||
- (void)throwIfDisposed {
|
||||
NSAssert(!self.disposed, @"Object already disposed");
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
NS_ASSUME_NONNULL_END
|
||||
60
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSTask/OSSCancellationTokenSource.h
generated
Normal file
60
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSTask/OSSCancellationTokenSource.h
generated
Normal file
@@ -0,0 +1,60 @@
|
||||
/*
|
||||
* Copyright (c) 2014, Facebook, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* This source code is licensed under the BSD-style license found in the
|
||||
* LICENSE file in the root directory of this source tree. An additional grant
|
||||
* of patent rights can be found in the PATENTS file in the same directory.
|
||||
*
|
||||
*/
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
@class OSSCancellationToken;
|
||||
|
||||
/*!
|
||||
OSSCancellationTokenSource represents the producer side of a CancellationToken.
|
||||
Signals to a CancellationToken that it should be canceled.
|
||||
It is a cancellation token that also has methods
|
||||
for changing the state of a token by cancelling it.
|
||||
*/
|
||||
@interface OSSCancellationTokenSource : NSObject
|
||||
|
||||
/*!
|
||||
Creates a new cancellation token source.
|
||||
*/
|
||||
+ (instancetype)cancellationTokenSource;
|
||||
|
||||
/*!
|
||||
The cancellation token associated with this CancellationTokenSource.
|
||||
*/
|
||||
@property (nonatomic, strong, readonly) OSSCancellationToken *token;
|
||||
|
||||
/*!
|
||||
Whether cancellation has been requested for this token source.
|
||||
*/
|
||||
@property (nonatomic, assign, readonly, getter=isCancellationRequested) BOOL cancellationRequested;
|
||||
|
||||
/*!
|
||||
Cancels the token if it has not already been cancelled.
|
||||
*/
|
||||
- (void)cancel;
|
||||
|
||||
/*!
|
||||
Schedules a cancel operation on this CancellationTokenSource after the specified number of milliseconds.
|
||||
@param millis The number of milliseconds to wait before completing the returned task.
|
||||
If delay is `0` the cancel is executed immediately. If delay is `-1` any scheduled cancellation is stopped.
|
||||
*/
|
||||
- (void)cancelAfterDelay:(int)millis;
|
||||
|
||||
/*!
|
||||
Releases all resources associated with this token source,
|
||||
including disposing of all registrations.
|
||||
*/
|
||||
- (void)dispose;
|
||||
|
||||
@end
|
||||
|
||||
NS_ASSUME_NONNULL_END
|
||||
64
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSTask/OSSCancellationTokenSource.m
generated
Normal file
64
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSTask/OSSCancellationTokenSource.m
generated
Normal file
@@ -0,0 +1,64 @@
|
||||
/*
|
||||
* Copyright (c) 2014, Facebook, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* This source code is licensed under the BSD-style license found in the
|
||||
* LICENSE file in the root directory of this source tree. An additional grant
|
||||
* of patent rights can be found in the PATENTS file in the same directory.
|
||||
*
|
||||
*/
|
||||
|
||||
#import "OSSCancellationTokenSource.h"
|
||||
|
||||
#import "OSSCancellationToken.h"
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
@interface OSSCancellationToken (OSSCancellationTokenSource)
|
||||
|
||||
- (void)cancel;
|
||||
- (void)cancelAfterDelay:(int)millis;
|
||||
|
||||
- (void)dispose;
|
||||
- (void)throwIfDisposed;
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSCancellationTokenSource
|
||||
|
||||
#pragma mark - Initializer
|
||||
|
||||
- (instancetype)init {
|
||||
self = [super init];
|
||||
if (!self) return self;
|
||||
|
||||
_token = [OSSCancellationToken new];
|
||||
|
||||
return self;
|
||||
}
|
||||
|
||||
+ (instancetype)cancellationTokenSource {
|
||||
return [OSSCancellationTokenSource new];
|
||||
}
|
||||
|
||||
#pragma mark - Custom Setters/Getters
|
||||
|
||||
- (BOOL)isCancellationRequested {
|
||||
return _token.isCancellationRequested;
|
||||
}
|
||||
|
||||
- (void)cancel {
|
||||
[_token cancel];
|
||||
}
|
||||
|
||||
- (void)cancelAfterDelay:(int)millis {
|
||||
[_token cancelAfterDelay:millis];
|
||||
}
|
||||
|
||||
- (void)dispose {
|
||||
[_token dispose];
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
NS_ASSUME_NONNULL_END
|
||||
62
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSTask/OSSExecutor.h
generated
Normal file
62
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSTask/OSSExecutor.h
generated
Normal file
@@ -0,0 +1,62 @@
|
||||
/*
|
||||
* Copyright (c) 2014, Facebook, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* This source code is licensed under the BSD-style license found in the
|
||||
* LICENSE file in the root directory of this source tree. An additional grant
|
||||
* of patent rights can be found in the PATENTS file in the same directory.
|
||||
*
|
||||
*/
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
/*!
|
||||
An object that can run a given block.
|
||||
*/
|
||||
@interface OSSExecutor : NSObject
|
||||
|
||||
/*!
|
||||
Returns a default executor, which runs continuations immediately until the call stack gets too
|
||||
deep, then dispatches to a new GCD queue.
|
||||
*/
|
||||
+ (instancetype)defaultExecutor;
|
||||
|
||||
/*!
|
||||
Returns an executor that runs continuations on the thread where the previous task was completed.
|
||||
*/
|
||||
+ (instancetype)immediateExecutor;
|
||||
|
||||
/*!
|
||||
Returns an executor that runs continuations on the main thread.
|
||||
*/
|
||||
+ (instancetype)mainThreadExecutor;
|
||||
|
||||
/*!
|
||||
Returns a new executor that uses the given block to execute continuations.
|
||||
@param block The block to use.
|
||||
*/
|
||||
+ (instancetype)executorWithBlock:(void(^)(void(^block)(void)))block;
|
||||
|
||||
/*!
|
||||
Returns a new executor that runs continuations on the given queue.
|
||||
@param queue The instance of `dispatch_queue_t` to dispatch all continuations onto.
|
||||
*/
|
||||
+ (instancetype)executorWithDispatchQueue:(dispatch_queue_t)queue;
|
||||
|
||||
/*!
|
||||
Returns a new executor that runs continuations on the given queue.
|
||||
@param queue The instance of `NSOperationQueue` to run all continuations on.
|
||||
*/
|
||||
+ (instancetype)executorWithOperationQueue:(NSOperationQueue *)queue;
|
||||
|
||||
/*!
|
||||
Runs the given block using this executor's particular strategy.
|
||||
@param block The block to execute.
|
||||
*/
|
||||
- (void)execute:(void(^)(void))block;
|
||||
|
||||
@end
|
||||
|
||||
NS_ASSUME_NONNULL_END
|
||||
136
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSTask/OSSExecutor.m
generated
Normal file
136
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSTask/OSSExecutor.m
generated
Normal file
@@ -0,0 +1,136 @@
|
||||
/*
|
||||
* Copyright (c) 2014, Facebook, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* This source code is licensed under the BSD-style license found in the
|
||||
* LICENSE file in the root directory of this source tree. An additional grant
|
||||
* of patent rights can be found in the PATENTS file in the same directory.
|
||||
*
|
||||
*/
|
||||
|
||||
#import "OSSExecutor.h"
|
||||
|
||||
#import <pthread.h>
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
/*!
|
||||
Get the remaining stack-size of the current thread.
|
||||
|
||||
@param totalSize The total stack size of the current thread.
|
||||
|
||||
@return The remaining size, in bytes, available to the current thread.
|
||||
|
||||
@note This function cannot be inlined, as otherwise the internal implementation could fail to report the proper
|
||||
remaining stack space.
|
||||
*/
|
||||
__attribute__((noinline)) static size_t remaining_stack_size(size_t *restrict totalSize) {
|
||||
pthread_t currentThread = pthread_self();
|
||||
|
||||
// NOTE: We must store stack pointers as uint8_t so that the pointer math is well-defined
|
||||
uint8_t *endStack = pthread_get_stackaddr_np(currentThread);
|
||||
*totalSize = pthread_get_stacksize_np(currentThread);
|
||||
|
||||
// NOTE: If the function is inlined, this value could be incorrect
|
||||
uint8_t *frameAddr = __builtin_frame_address(0);
|
||||
|
||||
return (*totalSize) - (endStack - frameAddr);
|
||||
}
|
||||
|
||||
@interface OSSExecutor ()
|
||||
|
||||
@property (nonatomic, copy) void(^block)(void(^block)(void));
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSExecutor
|
||||
|
||||
#pragma mark - Executor methods
|
||||
|
||||
+ (instancetype)defaultExecutor {
|
||||
static OSSExecutor *defaultExecutor = NULL;
|
||||
static dispatch_once_t onceToken;
|
||||
dispatch_once(&onceToken, ^{
|
||||
defaultExecutor = [self executorWithBlock:^void(void(^block)(void)) {
|
||||
// We prefer to run everything possible immediately, so that there is callstack information
|
||||
// when debugging. However, we don't want the stack to get too deep, so if the remaining stack space
|
||||
// is less than 10% of the total space, we dispatch to another GCD queue.
|
||||
size_t totalStackSize = 0;
|
||||
size_t remainingStackSize = remaining_stack_size(&totalStackSize);
|
||||
|
||||
if (remainingStackSize < (totalStackSize / 10)) {
|
||||
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), block);
|
||||
} else {
|
||||
@autoreleasepool {
|
||||
block();
|
||||
}
|
||||
}
|
||||
}];
|
||||
});
|
||||
return defaultExecutor;
|
||||
}
|
||||
|
||||
+ (instancetype)immediateExecutor {
|
||||
static OSSExecutor *immediateExecutor = NULL;
|
||||
static dispatch_once_t onceToken;
|
||||
dispatch_once(&onceToken, ^{
|
||||
immediateExecutor = [self executorWithBlock:^void(void(^block)(void)) {
|
||||
block();
|
||||
}];
|
||||
});
|
||||
return immediateExecutor;
|
||||
}
|
||||
|
||||
+ (instancetype)mainThreadExecutor {
|
||||
static OSSExecutor *mainThreadExecutor = NULL;
|
||||
static dispatch_once_t onceToken;
|
||||
dispatch_once(&onceToken, ^{
|
||||
mainThreadExecutor = [self executorWithBlock:^void(void(^block)(void)) {
|
||||
if (![NSThread isMainThread]) {
|
||||
dispatch_async(dispatch_get_main_queue(), block);
|
||||
} else {
|
||||
@autoreleasepool {
|
||||
block();
|
||||
}
|
||||
}
|
||||
}];
|
||||
});
|
||||
return mainThreadExecutor;
|
||||
}
|
||||
|
||||
+ (instancetype)executorWithBlock:(void(^)(void(^block)(void)))block {
|
||||
return [[self alloc] initWithBlock:block];
|
||||
}
|
||||
|
||||
+ (instancetype)executorWithDispatchQueue:(dispatch_queue_t)queue {
|
||||
return [self executorWithBlock:^void(void(^block)(void)) {
|
||||
dispatch_async(queue, block);
|
||||
}];
|
||||
}
|
||||
|
||||
+ (instancetype)executorWithOperationQueue:(NSOperationQueue *)queue {
|
||||
return [self executorWithBlock:^void(void(^block)(void)) {
|
||||
[queue addOperation:[NSBlockOperation blockOperationWithBlock:block]];
|
||||
}];
|
||||
}
|
||||
|
||||
#pragma mark - Initializer
|
||||
|
||||
- (instancetype)initWithBlock:(void(^)(void(^block)(void)))block {
|
||||
self = [super init];
|
||||
if (!self) return self;
|
||||
|
||||
_block = block;
|
||||
|
||||
return self;
|
||||
}
|
||||
|
||||
#pragma mark - Execution
|
||||
|
||||
- (void)execute:(void(^)(void))block {
|
||||
self.block(block);
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
NS_ASSUME_NONNULL_END
|
||||
295
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSTask/OSSTask.h
generated
Normal file
295
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSTask/OSSTask.h
generated
Normal file
@@ -0,0 +1,295 @@
|
||||
/*
|
||||
* Copyright (c) 2014, Facebook, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* This source code is licensed under the BSD-style license found in the
|
||||
* LICENSE file in the root directory of this source tree. An additional grant
|
||||
* of patent rights can be found in the PATENTS file in the same directory.
|
||||
*
|
||||
*/
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
|
||||
#import "OSSCancellationToken.h"
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
/*!
|
||||
Error domain used if there was multiple errors on <OSSTask taskForCompletionOfAllTasks:>.
|
||||
*/
|
||||
extern NSString *const OSSTaskErrorDomain;
|
||||
|
||||
/*!
|
||||
An error code used for <OSSTask taskForCompletionOfAllTasks:>, if there were multiple errors.
|
||||
*/
|
||||
extern NSInteger const kOSSMultipleErrorsError;
|
||||
|
||||
/*!
|
||||
An exception that is thrown if there was multiple exceptions on <OSSTask taskForCompletionOfAllTasks:>.
|
||||
*/
|
||||
extern NSString *const OSSTaskMultipleExceptionsException;
|
||||
|
||||
/*!
|
||||
An error userInfo key used if there were multiple errors on <OSSTask taskForCompletionOfAllTasks:>.
|
||||
Value type is `NSArray<NSError *> *`.
|
||||
*/
|
||||
extern NSString *const OSSTaskMultipleErrorsUserInfoKey;
|
||||
|
||||
/*!
|
||||
An error userInfo key used if there were multiple exceptions on <OSSTask taskForCompletionOfAllTasks:>.
|
||||
Value type is `NSArray<NSException *> *`.
|
||||
*/
|
||||
extern NSString *const OSSTaskMultipleExceptionsUserInfoKey;
|
||||
|
||||
@class OSSExecutor;
|
||||
@class OSSTask;
|
||||
|
||||
/*!
|
||||
The consumer view of a Task. A OSSTask has methods to
|
||||
inspect the state of the task, and to add continuations to
|
||||
be run once the task is complete.
|
||||
*/
|
||||
@interface OSSTask<__covariant ResultType> : NSObject
|
||||
|
||||
/*!
|
||||
A block that can act as a continuation for a task.
|
||||
*/
|
||||
typedef __nullable id(^OSSContinuationBlock)(OSSTask<ResultType> *task);
|
||||
|
||||
/*!
|
||||
Creates a task that is already completed with the given result.
|
||||
@param result The result for the task.
|
||||
*/
|
||||
+ (instancetype)taskWithResult:(_Nullable ResultType)result;
|
||||
|
||||
/*!
|
||||
Creates a task that is already completed with the given error.
|
||||
@param error The error for the task.
|
||||
*/
|
||||
+ (instancetype)taskWithError:(NSError *)error;
|
||||
|
||||
/*!
|
||||
Creates a task that is already completed with the given exception.
|
||||
@param exception The exception for the task.
|
||||
*/
|
||||
+ (instancetype)taskWithException:(NSException *)exception;
|
||||
|
||||
/*!
|
||||
Creates a task that is already cancelled.
|
||||
*/
|
||||
+ (instancetype)cancelledTask;
|
||||
|
||||
/*!
|
||||
Returns a task that will be completed (with result == nil) once
|
||||
all of the input tasks have completed.
|
||||
@param tasks An `NSArray` of the tasks to use as an input.
|
||||
*/
|
||||
+ (instancetype)taskForCompletionOfAllTasks:(nullable NSArray<OSSTask *> *)tasks;
|
||||
|
||||
/*!
|
||||
Returns a task that will be completed once all of the input tasks have completed.
|
||||
If all tasks complete successfully without being faulted or cancelled the result will be
|
||||
an `NSArray` of all task results in the order they were provided.
|
||||
@param tasks An `NSArray` of the tasks to use as an input.
|
||||
*/
|
||||
+ (instancetype)taskForCompletionOfAllTasksWithResults:(nullable NSArray<OSSTask *> *)tasks;
|
||||
|
||||
/*!
|
||||
Returns a task that will be completed once there is at least one successful task.
|
||||
The first task to successuly complete will set the result, all other tasks results are
|
||||
ignored.
|
||||
@param tasks An `NSArray` of the tasks to use as an input.
|
||||
*/
|
||||
+ (instancetype)taskForCompletionOfAnyTask:(nullable NSArray<OSSTask *> *)tasks;
|
||||
|
||||
/*!
|
||||
Returns a task that will be completed a certain amount of time in the future.
|
||||
@param millis The approximate number of milliseconds to wait before the
|
||||
task will be finished (with result == nil).
|
||||
*/
|
||||
+ (instancetype)taskWithDelay:(int)millis;
|
||||
|
||||
/*!
|
||||
Returns a task that will be completed a certain amount of time in the future.
|
||||
@param millis The approximate number of milliseconds to wait before the
|
||||
task will be finished (with result == nil).
|
||||
@param token The cancellation token (optional).
|
||||
*/
|
||||
+ (instancetype)taskWithDelay:(int)millis cancellationToken:(nullable OSSCancellationToken *)token;
|
||||
|
||||
/*!
|
||||
Returns a task that will be completed after the given block completes with
|
||||
the specified executor.
|
||||
@param executor A OSSExecutor responsible for determining how the
|
||||
continuation block will be run.
|
||||
@param block The block to immediately schedule to run with the given executor.
|
||||
@returns A task that will be completed after block has run.
|
||||
If block returns a OSSTask, then the task returned from
|
||||
this method will not be completed until that task is completed.
|
||||
*/
|
||||
+ (instancetype)taskFromExecutor:(OSSExecutor *)executor withBlock:(nullable id (^)(void))block;
|
||||
|
||||
// Properties that will be set on the task once it is completed.
|
||||
|
||||
/*!
|
||||
The result of a successful task.
|
||||
*/
|
||||
@property (nullable, nonatomic, strong, readonly) ResultType result;
|
||||
|
||||
/*!
|
||||
The error of a failed task.
|
||||
*/
|
||||
@property (nullable, nonatomic, strong, readonly) NSError *error;
|
||||
|
||||
/*!
|
||||
The exception of a failed task.
|
||||
*/
|
||||
@property (nullable, nonatomic, strong, readonly) NSException *exception;
|
||||
|
||||
/*!
|
||||
Whether this task has been cancelled.
|
||||
*/
|
||||
@property (nonatomic, assign, readonly, getter=isCancelled) BOOL cancelled;
|
||||
|
||||
/*!
|
||||
Whether this task has completed due to an error or exception.
|
||||
*/
|
||||
@property (nonatomic, assign, readonly, getter=isFaulted) BOOL faulted;
|
||||
|
||||
/*!
|
||||
Whether this task has completed.
|
||||
*/
|
||||
@property (nonatomic, assign, readonly, getter=isCompleted) BOOL completed;
|
||||
|
||||
/*!
|
||||
Enqueues the given block to be run once this task is complete.
|
||||
This method uses a default execution strategy. The block will be
|
||||
run on the thread where the previous task completes, unless the
|
||||
the stack depth is too deep, in which case it will be run on a
|
||||
dispatch queue with default priority.
|
||||
@param block The block to be run once this task is complete.
|
||||
@returns A task that will be completed after block has run.
|
||||
If block returns a OSSTask, then the task returned from
|
||||
this method will not be completed until that task is completed.
|
||||
*/
|
||||
- (OSSTask *)continueWithBlock:(OSSContinuationBlock)block;
|
||||
|
||||
/*!
|
||||
Enqueues the given block to be run once this task is complete.
|
||||
This method uses a default execution strategy. The block will be
|
||||
run on the thread where the previous task completes, unless the
|
||||
the stack depth is too deep, in which case it will be run on a
|
||||
dispatch queue with default priority.
|
||||
@param block The block to be run once this task is complete.
|
||||
@param cancellationToken The cancellation token (optional).
|
||||
@returns A task that will be completed after block has run.
|
||||
If block returns a OSSTask, then the task returned from
|
||||
this method will not be completed until that task is completed.
|
||||
*/
|
||||
- (OSSTask *)continueWithBlock:(OSSContinuationBlock)block cancellationToken:(nullable OSSCancellationToken *)cancellationToken;
|
||||
|
||||
/*!
|
||||
Enqueues the given block to be run once this task is complete.
|
||||
@param executor A OSSExecutor responsible for determining how the
|
||||
continuation block will be run.
|
||||
@param block The block to be run once this task is complete.
|
||||
@returns A task that will be completed after block has run.
|
||||
If block returns a OSSTask, then the task returned from
|
||||
this method will not be completed until that task is completed.
|
||||
*/
|
||||
- (OSSTask *)continueWithExecutor:(OSSExecutor *)executor withBlock:(OSSContinuationBlock)block;
|
||||
/*!
|
||||
Enqueues the given block to be run once this task is complete.
|
||||
@param executor A OSSExecutor responsible for determining how the
|
||||
continuation block will be run.
|
||||
@param block The block to be run once this task is complete.
|
||||
@param cancellationToken The cancellation token (optional).
|
||||
@returns A task that will be completed after block has run.
|
||||
If block returns a OSSTask, then the task returned from
|
||||
his method will not be completed until that task is completed.
|
||||
*/
|
||||
- (OSSTask *)continueWithExecutor:(OSSExecutor *)executor
|
||||
block:(OSSContinuationBlock)block
|
||||
cancellationToken:(nullable OSSCancellationToken *)cancellationToken;
|
||||
|
||||
/*!
|
||||
Identical to continueWithBlock:, except that the block is only run
|
||||
if this task did not produce a cancellation, error, or exception.
|
||||
If it did, then the failure will be propagated to the returned
|
||||
task.
|
||||
@param block The block to be run once this task is complete.
|
||||
@returns A task that will be completed after block has run.
|
||||
If block returns a OSSTask, then the task returned from
|
||||
this method will not be completed until that task is completed.
|
||||
*/
|
||||
- (OSSTask *)continueWithSuccessBlock:(OSSContinuationBlock)block;
|
||||
|
||||
/*!
|
||||
Identical to continueWithBlock:, except that the block is only run
|
||||
if this task did not produce a cancellation, error, or exception.
|
||||
If it did, then the failure will be propagated to the returned
|
||||
task.
|
||||
@param block The block to be run once this task is complete.
|
||||
@param cancellationToken The cancellation token (optional).
|
||||
@returns A task that will be completed after block has run.
|
||||
If block returns a OSSTask, then the task returned from
|
||||
this method will not be completed until that task is completed.
|
||||
*/
|
||||
- (OSSTask *)continueWithSuccessBlock:(OSSContinuationBlock)block cancellationToken:(nullable OSSCancellationToken *)cancellationToken;
|
||||
|
||||
/*!
|
||||
Identical to continueWithExecutor:withBlock:, except that the block
|
||||
is only run if this task did not produce a cancellation, error, or
|
||||
exception. If it did, then the failure will be propagated to the
|
||||
returned task.
|
||||
@param executor A OSSExecutor responsible for determining how the
|
||||
continuation block will be run.
|
||||
@param block The block to be run once this task is complete.
|
||||
@returns A task that will be completed after block has run.
|
||||
If block returns a OSSTask, then the task returned from
|
||||
this method will not be completed until that task is completed.
|
||||
*/
|
||||
- (OSSTask *)continueWithExecutor:(OSSExecutor *)executor withSuccessBlock:(OSSContinuationBlock)block;
|
||||
|
||||
/*!
|
||||
Identical to continueWithExecutor:withBlock:, except that the block
|
||||
is only run if this task did not produce a cancellation, error, or
|
||||
exception. If it did, then the failure will be propagated to the
|
||||
returned task.
|
||||
@param executor A OSSExecutor responsible for determining how the
|
||||
continuation block will be run.
|
||||
@param block The block to be run once this task is complete.
|
||||
@param cancellationToken The cancellation token (optional).
|
||||
@returns A task that will be completed after block has run.
|
||||
If block returns a OSSTask, then the task returned from
|
||||
this method will not be completed until that task is completed.
|
||||
*/
|
||||
- (OSSTask *)continueWithExecutor:(OSSExecutor *)executor
|
||||
successBlock:(OSSContinuationBlock)block
|
||||
cancellationToken:(nullable OSSCancellationToken *)cancellationToken;
|
||||
|
||||
/*!
|
||||
Waits until this operation is completed.
|
||||
This method is inefficient and consumes a thread resource while
|
||||
it's running. It should be avoided. This method logs a warning
|
||||
message if it is used on the main thread.
|
||||
*/
|
||||
- (void)waitUntilFinished;
|
||||
|
||||
@end
|
||||
|
||||
@class OSSResult;
|
||||
|
||||
@interface OSSTask(OSS)
|
||||
|
||||
typedef void(^OSSCompleteBlock)(BOOL isSuccess, NSError * _Nullable error, OSSResult * _Nullable result);
|
||||
|
||||
- (BOOL)isSuccessful;
|
||||
|
||||
- (NSError *)toError;
|
||||
|
||||
- (OSSTask *)completed:(OSSCompleteBlock)block;
|
||||
|
||||
@end
|
||||
|
||||
NS_ASSUME_NONNULL_END
|
||||
584
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSTask/OSSTask.m
generated
Normal file
584
Pods/AliyunOSSiOS/AliyunOSSSDK/OSSTask/OSSTask.m
generated
Normal file
@@ -0,0 +1,584 @@
|
||||
/*
|
||||
* Copyright (c) 2014, Facebook, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* This source code is licensed under the BSD-style license found in the
|
||||
* LICENSE file in the root directory of this source tree. An additional grant
|
||||
* of patent rights can be found in the PATENTS file in the same directory.
|
||||
*
|
||||
*/
|
||||
|
||||
#import "OSSTask.h"
|
||||
#import "OSSLog.h"
|
||||
#import "OSSConstants.h"
|
||||
#import "OSSDefine.h"
|
||||
|
||||
#import <libkern/OSAtomic.h>
|
||||
|
||||
#import "OSSBolts.h"
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
__attribute__ ((noinline)) void ossWarnBlockingOperationOnMainThread() {
|
||||
NSLog(@"Warning: A long-running operation is being executed on the main thread. \n"
|
||||
" Break on warnBlockingOperationOnMainThread() to debug.");
|
||||
}
|
||||
|
||||
NSString *const OSSTaskErrorDomain = @"bolts";
|
||||
NSInteger const kOSSMultipleErrorsError = 80175001;
|
||||
NSString *const OSSTaskMultipleExceptionsException = @"OSSMultipleExceptionsException";
|
||||
|
||||
NSString *const OSSTaskMultipleErrorsUserInfoKey = @"errors";
|
||||
NSString *const OSSTaskMultipleExceptionsUserInfoKey = @"exceptions";
|
||||
|
||||
@interface OSSTask () {
|
||||
id _result;
|
||||
NSError *_error;
|
||||
NSException *_exception;
|
||||
}
|
||||
|
||||
@property (nonatomic, assign, readwrite, getter=isCancelled) BOOL cancelled;
|
||||
@property (nonatomic, assign, readwrite, getter=isFaulted) BOOL faulted;
|
||||
@property (nonatomic, assign, readwrite, getter=isCompleted) BOOL completed;
|
||||
|
||||
@property (nonatomic, strong) NSObject *lock;
|
||||
@property (nonatomic, strong) NSCondition *condition;
|
||||
@property (nonatomic, strong) NSMutableArray *callbacks;
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSTask
|
||||
|
||||
#pragma mark - Initializer
|
||||
|
||||
- (instancetype)init {
|
||||
self = [super init];
|
||||
if (!self) return self;
|
||||
|
||||
_lock = [[NSObject alloc] init];
|
||||
_condition = [[NSCondition alloc] init];
|
||||
_callbacks = [NSMutableArray array];
|
||||
|
||||
return self;
|
||||
}
|
||||
|
||||
- (instancetype)initWithResult:(_Nullable id)result {
|
||||
self = [super init];
|
||||
if (self) {
|
||||
[self trySetResult:result];
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
- (instancetype)initWithError:(NSError *)error {
|
||||
self = [super init];
|
||||
if (!self) return self;
|
||||
|
||||
[self trySetError:error];
|
||||
|
||||
return self;
|
||||
}
|
||||
|
||||
- (instancetype)initWithException:(NSException *)exception {
|
||||
self = [super init];
|
||||
if (!self) return self;
|
||||
|
||||
[self trySetException:exception];
|
||||
|
||||
return self;
|
||||
}
|
||||
|
||||
- (instancetype)initCancelled {
|
||||
self = [super init];
|
||||
if (!self) return self;
|
||||
|
||||
[self trySetCancelled];
|
||||
|
||||
return self;
|
||||
}
|
||||
|
||||
#pragma mark - Task Class methods
|
||||
|
||||
+ (instancetype)taskWithResult:(_Nullable id)result {
|
||||
return [[self alloc] initWithResult:result];
|
||||
}
|
||||
|
||||
+ (instancetype)taskWithError:(NSError *)error {
|
||||
return [[self alloc] initWithError:error];
|
||||
}
|
||||
|
||||
+ (instancetype)taskWithException:(NSException *)exception {
|
||||
return [[self alloc] initWithException:exception];
|
||||
}
|
||||
|
||||
+ (instancetype)cancelledTask {
|
||||
return [[self alloc] initCancelled];
|
||||
}
|
||||
|
||||
+ (instancetype)taskForCompletionOfAllTasks:(nullable NSArray<OSSTask *> *)tasks {
|
||||
__block int32_t total = (int32_t)tasks.count;
|
||||
if (total == 0) {
|
||||
return [self taskWithResult:nil];
|
||||
}
|
||||
|
||||
__block int32_t cancelled = 0;
|
||||
NSObject *lock = [[NSObject alloc] init];
|
||||
NSMutableArray *errors = [NSMutableArray array];
|
||||
NSMutableArray *exceptions = [NSMutableArray array];
|
||||
|
||||
OSSTaskCompletionSource *tcs = [OSSTaskCompletionSource taskCompletionSource];
|
||||
for (OSSTask *task in tasks) {
|
||||
[task continueWithBlock:^id(OSSTask *task) {
|
||||
if (task.exception) {
|
||||
@synchronized (lock) {
|
||||
[exceptions addObject:task.exception];
|
||||
}
|
||||
} else if (task.error) {
|
||||
@synchronized (lock) {
|
||||
[errors addObject:task.error];
|
||||
}
|
||||
} else if (task.cancelled) {
|
||||
OSAtomicIncrement32Barrier(&cancelled);
|
||||
}
|
||||
|
||||
if (OSAtomicDecrement32Barrier(&total) == 0) {
|
||||
if (exceptions.count > 0) {
|
||||
if (exceptions.count == 1) {
|
||||
tcs.exception = [exceptions firstObject];
|
||||
} else {
|
||||
NSException *exception =
|
||||
[NSException exceptionWithName:OSSTaskMultipleExceptionsException
|
||||
reason:@"There were multiple exceptions."
|
||||
userInfo:@{ OSSTaskMultipleExceptionsUserInfoKey: exceptions }];
|
||||
tcs.exception = exception;
|
||||
}
|
||||
} else if (errors.count > 0) {
|
||||
if (errors.count == 1) {
|
||||
tcs.error = [errors firstObject];
|
||||
} else {
|
||||
NSError *error = [NSError errorWithDomain:OSSTaskErrorDomain
|
||||
code:kOSSMultipleErrorsError
|
||||
userInfo:@{ OSSTaskMultipleErrorsUserInfoKey: errors }];
|
||||
tcs.error = error;
|
||||
}
|
||||
} else if (cancelled > 0) {
|
||||
[tcs cancel];
|
||||
} else {
|
||||
tcs.result = nil;
|
||||
}
|
||||
}
|
||||
return nil;
|
||||
}];
|
||||
}
|
||||
return tcs.task;
|
||||
}
|
||||
|
||||
+ (instancetype)taskForCompletionOfAllTasksWithResults:(nullable NSArray<OSSTask *> *)tasks {
|
||||
return [[self taskForCompletionOfAllTasks:tasks] continueWithSuccessBlock:^id(OSSTask *task) {
|
||||
return [tasks valueForKey:@"result"];
|
||||
}];
|
||||
}
|
||||
|
||||
+ (instancetype)taskForCompletionOfAnyTask:(nullable NSArray<OSSTask *> *)tasks
|
||||
{
|
||||
__block int32_t total = (int32_t)tasks.count;
|
||||
if (total == 0) {
|
||||
return [self taskWithResult:nil];
|
||||
}
|
||||
|
||||
__block int completed = 0;
|
||||
__block int32_t cancelled = 0;
|
||||
|
||||
NSObject *lock = [NSObject new];
|
||||
NSMutableArray<NSError *> *errors = [NSMutableArray new];
|
||||
NSMutableArray<NSException *> *exceptions = [NSMutableArray new];
|
||||
|
||||
OSSTaskCompletionSource *source = [OSSTaskCompletionSource taskCompletionSource];
|
||||
for (OSSTask *task in tasks) {
|
||||
[task continueWithBlock:^id(OSSTask *task) {
|
||||
if (task.exception != nil) {
|
||||
@synchronized(lock) {
|
||||
[exceptions addObject:task.exception];
|
||||
}
|
||||
} else if (task.error != nil) {
|
||||
@synchronized(lock) {
|
||||
[errors addObject:task.error];
|
||||
}
|
||||
} else if (task.cancelled) {
|
||||
OSAtomicIncrement32Barrier(&cancelled);
|
||||
} else {
|
||||
if(OSAtomicCompareAndSwap32Barrier(0, 1, &completed)) {
|
||||
[source setResult:task.result];
|
||||
}
|
||||
}
|
||||
|
||||
if (OSAtomicDecrement32Barrier(&total) == 0 &&
|
||||
OSAtomicCompareAndSwap32Barrier(0, 1, &completed)) {
|
||||
if (cancelled > 0) {
|
||||
[source cancel];
|
||||
} else if (exceptions.count > 0) {
|
||||
if (exceptions.count == 1) {
|
||||
source.exception = exceptions.firstObject;
|
||||
} else {
|
||||
NSException *exception =
|
||||
[NSException exceptionWithName:OSSTaskMultipleExceptionsException
|
||||
reason:@"There were multiple exceptions."
|
||||
userInfo:@{ @"exceptions": exceptions }];
|
||||
source.exception = exception;
|
||||
}
|
||||
} else if (errors.count > 0) {
|
||||
if (errors.count == 1) {
|
||||
source.error = errors.firstObject;
|
||||
} else {
|
||||
NSError *error = [NSError errorWithDomain:OSSTaskErrorDomain
|
||||
code:kOSSMultipleErrorsError
|
||||
userInfo:@{ @"errors": errors }];
|
||||
source.error = error;
|
||||
}
|
||||
}
|
||||
}
|
||||
// Abort execution of per tasks continuations
|
||||
return nil;
|
||||
}];
|
||||
}
|
||||
return source.task;
|
||||
}
|
||||
|
||||
|
||||
+ (instancetype)taskWithDelay:(int)millis {
|
||||
OSSTaskCompletionSource *tcs = [OSSTaskCompletionSource taskCompletionSource];
|
||||
dispatch_time_t popTime = dispatch_time(DISPATCH_TIME_NOW, millis * NSEC_PER_MSEC);
|
||||
dispatch_after(popTime, dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^(void){
|
||||
tcs.result = nil;
|
||||
});
|
||||
return tcs.task;
|
||||
}
|
||||
|
||||
+ (instancetype)taskWithDelay:(int)millis cancellationToken:(nullable OSSCancellationToken *)token {
|
||||
if (token.cancellationRequested) {
|
||||
return [OSSTask cancelledTask];
|
||||
}
|
||||
|
||||
OSSTaskCompletionSource *tcs = [OSSTaskCompletionSource taskCompletionSource];
|
||||
dispatch_time_t popTime = dispatch_time(DISPATCH_TIME_NOW, millis * NSEC_PER_MSEC);
|
||||
dispatch_after(popTime, dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^(void){
|
||||
if (token.cancellationRequested) {
|
||||
[tcs cancel];
|
||||
return;
|
||||
}
|
||||
tcs.result = nil;
|
||||
});
|
||||
return tcs.task;
|
||||
}
|
||||
|
||||
+ (instancetype)taskFromExecutor:(OSSExecutor *)executor withBlock:(nullable id (^)(void))block {
|
||||
return [[self taskWithResult:nil] continueWithExecutor:executor withBlock:^id(OSSTask *task) {
|
||||
return block();
|
||||
}];
|
||||
}
|
||||
|
||||
#pragma mark - Custom Setters/Getters
|
||||
|
||||
- (nullable id)result {
|
||||
@synchronized(self.lock) {
|
||||
return _result;
|
||||
}
|
||||
}
|
||||
|
||||
- (BOOL)trySetResult:(nullable id)result {
|
||||
@synchronized(self.lock) {
|
||||
if (self.completed) {
|
||||
return NO;
|
||||
}
|
||||
self.completed = YES;
|
||||
_result = result;
|
||||
[self runContinuations];
|
||||
return YES;
|
||||
}
|
||||
}
|
||||
|
||||
- (nullable NSError *)error {
|
||||
@synchronized(self.lock) {
|
||||
return _error;
|
||||
}
|
||||
}
|
||||
|
||||
- (BOOL)trySetError:(NSError *)error {
|
||||
@synchronized(self.lock) {
|
||||
if (self.completed) {
|
||||
return NO;
|
||||
}
|
||||
self.completed = YES;
|
||||
self.faulted = YES;
|
||||
_error = error;
|
||||
[self runContinuations];
|
||||
return YES;
|
||||
}
|
||||
}
|
||||
|
||||
- (nullable NSException *)exception {
|
||||
@synchronized(self.lock) {
|
||||
return _exception;
|
||||
}
|
||||
}
|
||||
|
||||
- (BOOL)trySetException:(NSException *)exception {
|
||||
@synchronized(self.lock) {
|
||||
if (self.completed) {
|
||||
return NO;
|
||||
}
|
||||
self.completed = YES;
|
||||
self.faulted = YES;
|
||||
_exception = exception;
|
||||
[self runContinuations];
|
||||
return YES;
|
||||
}
|
||||
}
|
||||
|
||||
- (BOOL)isCancelled {
|
||||
@synchronized(self.lock) {
|
||||
return _cancelled;
|
||||
}
|
||||
}
|
||||
|
||||
- (BOOL)isFaulted {
|
||||
@synchronized(self.lock) {
|
||||
return _faulted;
|
||||
}
|
||||
}
|
||||
|
||||
- (BOOL)trySetCancelled {
|
||||
@synchronized(self.lock) {
|
||||
if (self.completed) {
|
||||
return NO;
|
||||
}
|
||||
self.completed = YES;
|
||||
self.cancelled = YES;
|
||||
[self runContinuations];
|
||||
return YES;
|
||||
}
|
||||
}
|
||||
|
||||
- (BOOL)isCompleted {
|
||||
@synchronized(self.lock) {
|
||||
return _completed;
|
||||
}
|
||||
}
|
||||
|
||||
- (void)runContinuations {
|
||||
@synchronized(self.lock) {
|
||||
[self.condition lock];
|
||||
[self.condition broadcast];
|
||||
[self.condition unlock];
|
||||
for (void (^callback)(void) in self.callbacks) {
|
||||
callback();
|
||||
}
|
||||
[self.callbacks removeAllObjects];
|
||||
}
|
||||
}
|
||||
|
||||
#pragma mark - Chaining methods
|
||||
|
||||
- (OSSTask *)continueWithExecutor:(OSSExecutor *)executor withBlock:(OSSContinuationBlock)block {
|
||||
return [self continueWithExecutor:executor block:block cancellationToken:nil];
|
||||
}
|
||||
|
||||
- (OSSTask *)continueWithExecutor:(OSSExecutor *)executor
|
||||
block:(OSSContinuationBlock)block
|
||||
cancellationToken:(nullable OSSCancellationToken *)cancellationToken {
|
||||
OSSTaskCompletionSource *tcs = [OSSTaskCompletionSource taskCompletionSource];
|
||||
|
||||
// Capture all of the state that needs to used when the continuation is complete.
|
||||
dispatch_block_t executionBlock = ^{
|
||||
if (cancellationToken.cancellationRequested) {
|
||||
[tcs cancel];
|
||||
return;
|
||||
}
|
||||
|
||||
id result = nil;
|
||||
@try {
|
||||
result = block(self);
|
||||
} @catch (NSException *exception) {
|
||||
NSError *error = [NSError errorWithDomain:OSSClientErrorDomain
|
||||
code:OSSClientErrorCodeExcpetionCatched
|
||||
userInfo:@{OSSErrorMessageTOKEN: [NSString stringWithFormat:@"Catch exception - %@", exception]}];
|
||||
tcs.error = error;
|
||||
OSSLogError(@"exception name: %@",[exception name]);
|
||||
OSSLogError(@"exception reason: %@",[exception reason]);
|
||||
return;
|
||||
}
|
||||
|
||||
if ([result isKindOfClass:[OSSTask class]]) {
|
||||
|
||||
id (^setupWithTask) (OSSTask *) = ^id(OSSTask *task) {
|
||||
if (cancellationToken.cancellationRequested || task.cancelled) {
|
||||
[tcs cancel];
|
||||
} else if (task.exception) {
|
||||
NSError *error = [NSError errorWithDomain:OSSClientErrorDomain
|
||||
code:OSSClientErrorCodeExcpetionCatched
|
||||
userInfo:@{OSSErrorMessageTOKEN: [NSString stringWithFormat:@"Catch exception - %@", task.exception]}];
|
||||
tcs.error = error;
|
||||
} else if (task.error) {
|
||||
tcs.error = task.error;
|
||||
} else {
|
||||
tcs.result = task.result;
|
||||
}
|
||||
return nil;
|
||||
};
|
||||
|
||||
OSSTask *resultTask = (OSSTask *)result;
|
||||
|
||||
if (resultTask.completed) {
|
||||
setupWithTask(resultTask);
|
||||
} else {
|
||||
[resultTask continueWithBlock:setupWithTask];
|
||||
}
|
||||
|
||||
} else {
|
||||
tcs.result = result;
|
||||
}
|
||||
};
|
||||
|
||||
BOOL completed;
|
||||
@synchronized(self.lock) {
|
||||
completed = self.completed;
|
||||
if (!completed) {
|
||||
[self.callbacks addObject:[^{
|
||||
[executor execute:executionBlock];
|
||||
} copy]];
|
||||
}
|
||||
}
|
||||
if (completed) {
|
||||
[executor execute:executionBlock];
|
||||
}
|
||||
|
||||
return tcs.task;
|
||||
}
|
||||
|
||||
- (OSSTask *)continueWithBlock:(OSSContinuationBlock)block {
|
||||
return [self continueWithExecutor:[OSSExecutor defaultExecutor] block:block cancellationToken:nil];
|
||||
}
|
||||
|
||||
- (OSSTask *)continueWithBlock:(OSSContinuationBlock)block cancellationToken:(nullable OSSCancellationToken *)cancellationToken {
|
||||
return [self continueWithExecutor:[OSSExecutor defaultExecutor] block:block cancellationToken:cancellationToken];
|
||||
}
|
||||
|
||||
- (OSSTask *)continueWithExecutor:(OSSExecutor *)executor
|
||||
withSuccessBlock:(OSSContinuationBlock)block {
|
||||
return [self continueWithExecutor:executor successBlock:block cancellationToken:nil];
|
||||
}
|
||||
|
||||
- (OSSTask *)continueWithExecutor:(OSSExecutor *)executor
|
||||
successBlock:(OSSContinuationBlock)block
|
||||
cancellationToken:(nullable OSSCancellationToken *)cancellationToken {
|
||||
if (cancellationToken.cancellationRequested) {
|
||||
return [OSSTask cancelledTask];
|
||||
}
|
||||
|
||||
return [self continueWithExecutor:executor block:^id(OSSTask *task) {
|
||||
if (task.faulted || task.cancelled) {
|
||||
return task;
|
||||
} else {
|
||||
return block(task);
|
||||
}
|
||||
} cancellationToken:cancellationToken];
|
||||
}
|
||||
|
||||
- (OSSTask *)continueWithSuccessBlock:(OSSContinuationBlock)block {
|
||||
return [self continueWithExecutor:[OSSExecutor defaultExecutor] successBlock:block cancellationToken:nil];
|
||||
}
|
||||
|
||||
- (OSSTask *)continueWithSuccessBlock:(OSSContinuationBlock)block cancellationToken:(nullable OSSCancellationToken *)cancellationToken {
|
||||
return [self continueWithExecutor:[OSSExecutor defaultExecutor] successBlock:block cancellationToken:cancellationToken];
|
||||
}
|
||||
|
||||
#pragma mark - Syncing Task (Avoid it)
|
||||
|
||||
- (void)warnOperationOnMainThread {
|
||||
ossWarnBlockingOperationOnMainThread();
|
||||
}
|
||||
|
||||
- (void)waitUntilFinished {
|
||||
if ([NSThread isMainThread]) {
|
||||
[self warnOperationOnMainThread];
|
||||
}
|
||||
|
||||
@synchronized(self.lock) {
|
||||
if (self.completed) {
|
||||
return;
|
||||
}
|
||||
[self.condition lock];
|
||||
}
|
||||
while (!self.completed) {
|
||||
[self.condition wait];
|
||||
}
|
||||
[self.condition unlock];
|
||||
}
|
||||
|
||||
#pragma mark - NSObject
|
||||
|
||||
- (NSString *)description {
|
||||
// Acquire the data from the locked properties
|
||||
BOOL completed;
|
||||
BOOL cancelled;
|
||||
BOOL faulted;
|
||||
NSString *resultDescription = nil;
|
||||
|
||||
@synchronized(self.lock) {
|
||||
completed = self.completed;
|
||||
cancelled = self.cancelled;
|
||||
faulted = self.faulted;
|
||||
resultDescription = completed ? [NSString stringWithFormat:@" result = %@", self.result] : @"";
|
||||
}
|
||||
|
||||
// Description string includes status information and, if available, the
|
||||
// result since in some ways this is what a promise actually "is".
|
||||
return [NSString stringWithFormat:@"<%@: %p; completed = %@; cancelled = %@; faulted = %@;%@>",
|
||||
NSStringFromClass([self class]),
|
||||
self,
|
||||
completed ? @"YES" : @"NO",
|
||||
cancelled ? @"YES" : @"NO",
|
||||
faulted ? @"YES" : @"NO",
|
||||
resultDescription];
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@implementation OSSTask(OSS)
|
||||
|
||||
- (BOOL)isSuccessful {
|
||||
if (self.cancelled || self.faulted) {
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
- (NSError *)toError {
|
||||
if (self.cancelled) {
|
||||
return [NSError errorWithDomain:OSSClientErrorDomain
|
||||
code:OSSClientErrorCodeTaskCancelled
|
||||
userInfo:@{OSSErrorMessageTOKEN: @"This task is cancelled"}];
|
||||
} else if (self.error) {
|
||||
return self.error;
|
||||
} else if (self.exception) {
|
||||
return [NSError errorWithDomain:OSSClientErrorDomain
|
||||
code:OSSClientErrorCodeExcpetionCatched
|
||||
userInfo:@{OSSErrorMessageTOKEN: [NSString stringWithFormat:@"Catch exception - %@", self.exception]}];
|
||||
}
|
||||
return nil;
|
||||
}
|
||||
|
||||
- (OSSTask *)completed:(OSSCompleteBlock)block {
|
||||
return [self continueWithBlock:^id _Nullable(OSSTask * _Nonnull task) {
|
||||
if ([task isSuccessful]) {
|
||||
block(YES, nil, task.result);
|
||||
} else {
|
||||
block(NO, [task toError], nil);
|
||||
}
|
||||
return nil;
|
||||
}];
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
NS_ASSUME_NONNULL_END
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user