summaryrefslogtreecommitdiff
path: root/StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking
diff options
context:
space:
mode:
authorJules Laplace <julescarbon@gmail.com>2020-08-31 23:07:20 +0200
committerJules Laplace <julescarbon@gmail.com>2020-08-31 23:07:20 +0200
commit22721a013bdd10d5eb395ba18453585f5f3f1f7f (patch)
tree5a920e31d6026ed5dc55265e5fd057febccc50e3 /StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking
parentd22d51a1ae49680015326857360eb699f31efced (diff)
rebuild the ios platform and the plugins
Diffstat (limited to 'StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking')
-rw-r--r--StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSFABNetworkClient.h56
-rw-r--r--StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSFABNetworkClient.m280
-rw-r--r--StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSMultipartMimeStreamEncoder.h88
-rw-r--r--StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSMultipartMimeStreamEncoder.m208
-rw-r--r--StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSNetworkResponseHandler.h87
-rw-r--r--StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSNetworkResponseHandler.m290
-rw-r--r--StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSURLBuilder.h44
-rw-r--r--StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSURLBuilder.m103
8 files changed, 1156 insertions, 0 deletions
diff --git a/StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSFABNetworkClient.h b/StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSFABNetworkClient.h
new file mode 100644
index 00000000..ebbd26c9
--- /dev/null
+++ b/StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSFABNetworkClient.h
@@ -0,0 +1,56 @@
+// Copyright 2019 Google
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import <Foundation/Foundation.h>
+
+OBJC_EXTERN const NSUInteger FIRCLSNetworkMaximumRetryCount;
+
+NS_ASSUME_NONNULL_BEGIN
+
+typedef void (^FIRCLSNetworkDataTaskCompletionHandlerBlock)(NSData *__nullable data,
+ NSURLResponse *__nullable response,
+ NSError *__nullable error);
+typedef void (^FIRCLSNetworkDownloadTaskCompletionHandlerBlock)(NSURL *__nullable location,
+ NSURLResponse *__nullable response,
+ NSError *__nullable error);
+
+@interface FIRCLSFABNetworkClient : NSObject
+
+- (instancetype)init;
+- (instancetype)initWithQueue:(nullable NSOperationQueue *)operationQueue;
+- (instancetype)initWithSessionConfiguration:(NSURLSessionConfiguration *)config
+ queue:(nullable NSOperationQueue *)operationQueue
+ NS_DESIGNATED_INITIALIZER;
+
+- (void)startDataTaskWithRequest:(NSURLRequest *)request
+ retryLimit:(NSUInteger)retryLimit
+ completionHandler:(FIRCLSNetworkDataTaskCompletionHandlerBlock)completionHandler;
+- (void)startDownloadTaskWithRequest:(NSURLRequest *)request
+ retryLimit:(NSUInteger)retryLimit
+ completionHandler:
+ (FIRCLSNetworkDownloadTaskCompletionHandlerBlock)completionHandler;
+
+- (void)invalidateAndCancel;
+
+// Backwards compatibility (we cannot change an interface in Fabric Base that other kits rely on,
+// since we have no control of versioning dependencies)
+- (void)startDataTaskWithRequest:(NSURLRequest *)request
+ completionHandler:(FIRCLSNetworkDataTaskCompletionHandlerBlock)completionHandler;
+- (void)startDownloadTaskWithRequest:(NSURLRequest *)request
+ completionHandler:
+ (FIRCLSNetworkDownloadTaskCompletionHandlerBlock)completionHandler;
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSFABNetworkClient.m b/StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSFABNetworkClient.m
new file mode 100644
index 00000000..39630bae
--- /dev/null
+++ b/StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSFABNetworkClient.m
@@ -0,0 +1,280 @@
+// Copyright 2019 Google
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "Crashlytics/Shared/FIRCLSNetworking/FIRCLSFABNetworkClient.h"
+
+#if FIRCLSURLSESSION_REQUIRED
+#import "Crashlytics/Crashlytics/FIRCLSURLSession/FIRCLSURLSession.h"
+#endif
+
+#import "Crashlytics/Shared/FIRCLSNetworking/FIRCLSNetworkResponseHandler.h"
+
+static const float FIRCLSNetworkMinimumRetryJitter = 0.90f;
+static const float FIRCLSNetworkMaximumRetryJitter = 1.10f;
+const NSUInteger FIRCLSNetworkMaximumRetryCount = 10;
+
+@interface FIRCLSFABNetworkClient () <NSURLSessionDelegate, NSURLSessionTaskDelegate>
+
+@property(nonatomic, strong, readonly) NSURLSession *session;
+
+@end
+
+@implementation FIRCLSFABNetworkClient
+
+- (instancetype)init {
+ return [self initWithQueue:nil];
+}
+
+- (instancetype)initWithQueue:(nullable NSOperationQueue *)operationQueue {
+#if !FIRCLSURLSESSION_REQUIRED
+ NSURLSessionConfiguration *config = [NSURLSessionConfiguration defaultSessionConfiguration];
+#else
+ NSURLSessionConfiguration *config = [FIRCLSURLSessionConfiguration defaultSessionConfiguration];
+#endif
+ return [self initWithSessionConfiguration:config queue:operationQueue];
+}
+
+- (instancetype)initWithSessionConfiguration:(NSURLSessionConfiguration *)config
+ queue:(nullable NSOperationQueue *)operationQueue {
+ self = [super init];
+ if (!self) {
+ return nil;
+ }
+
+#if !FIRCLSURLSESSION_REQUIRED
+ _session = [NSURLSession sessionWithConfiguration:config
+ delegate:self
+ delegateQueue:operationQueue];
+#else
+ _session = [FIRCLSURLSession sessionWithConfiguration:config
+ delegate:self
+ delegateQueue:operationQueue];
+#endif
+ if (!_session) {
+ return nil;
+ }
+
+ return self;
+}
+
+- (void)dealloc {
+ [_session finishTasksAndInvalidate];
+}
+
+#pragma mark - Delay Handling
+- (double)randomDoubleWithMin:(double)min max:(double)max {
+ return min + ((max - min) * drand48());
+}
+
+- (double)generateRandomJitter {
+ return [self randomDoubleWithMin:FIRCLSNetworkMinimumRetryJitter
+ max:FIRCLSNetworkMaximumRetryJitter];
+}
+
+- (NSTimeInterval)computeDelayForResponse:(NSURLResponse *)response
+ withRetryCount:(NSUInteger)count {
+ NSTimeInterval initialValue = [FIRCLSNetworkResponseHandler retryValueForResponse:response];
+
+ // make sure count is > 0
+ count = MAX(count, 1);
+ // make sure initialValue is >2 for exponential backoff to work reasonably with low count numbers
+ initialValue = MAX(initialValue, 2.0);
+
+ const double jitter = [self generateRandomJitter];
+
+ return pow(initialValue, count) * jitter; // exponential backoff
+}
+
+- (void)runAfterRetryValueFromResponse:(NSURLResponse *)response
+ attempts:(NSUInteger)count
+ onQueue:(dispatch_queue_t)queue
+ block:(void (^)(void))block {
+ const NSTimeInterval delay = [self computeDelayForResponse:response withRetryCount:count];
+
+ dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (uint64_t)(delay * NSEC_PER_SEC)), queue, block);
+}
+
+- (void)runAfterRetryValueFromResponse:(NSURLResponse *)response
+ attempts:(NSUInteger)count
+ block:(void (^)(void))block {
+ dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
+
+ [self runAfterRetryValueFromResponse:response attempts:count onQueue:queue block:block];
+}
+
+#pragma mark - Tasks
+
+- (void)startDataTaskWithRequest:(NSURLRequest *)request
+ retryLimit:(NSUInteger)retryLimit
+ tries:(NSUInteger)tries
+ completionHandler:(FIRCLSNetworkDataTaskCompletionHandlerBlock)completionHandler {
+ NSURLSessionTask *task = [self.session
+ dataTaskWithRequest:request
+ completionHandler:^(NSData *data, NSURLResponse *response, NSError *taskError) {
+ [FIRCLSNetworkResponseHandler
+ handleCompletedResponse:response
+ forOriginalRequest:request
+ error:taskError
+ block:^(BOOL retry, NSError *error) {
+ if (!retry) {
+ completionHandler(data, response, error);
+ return;
+ }
+
+ if (tries >= retryLimit) {
+ NSDictionary *userInfo = @{
+ @"retryLimit" : @(retryLimit),
+ NSURLErrorFailingURLStringErrorKey : request.URL
+ };
+ completionHandler(
+ nil, nil,
+ [NSError
+ errorWithDomain:FIRCLSNetworkErrorDomain
+ code:FIRCLSNetworkErrorMaximumAttemptsReached
+ userInfo:userInfo]);
+ return;
+ }
+
+ [self
+ runAfterRetryValueFromResponse:response
+ attempts:tries
+ block:^{
+ [self
+ startDataTaskWithRequest:
+ request
+ retryLimit:
+ retryLimit
+ tries:
+ (tries +
+ 1)
+ completionHandler:
+ completionHandler];
+ }];
+ }];
+ }];
+
+ [task resume];
+
+ if (!task) {
+ completionHandler(nil, nil,
+ [NSError errorWithDomain:FIRCLSNetworkErrorDomain
+ code:FIRCLSNetworkErrorFailedToStartOperation
+ userInfo:nil]);
+ }
+}
+
+- (void)startDataTaskWithRequest:(NSURLRequest *)request
+ retryLimit:(NSUInteger)retryLimit
+ completionHandler:(FIRCLSNetworkDataTaskCompletionHandlerBlock)completionHandler {
+ [self startDataTaskWithRequest:request
+ retryLimit:retryLimit
+ tries:0
+ completionHandler:completionHandler];
+}
+
+- (void)startDataTaskWithRequest:(NSURLRequest *)request
+ completionHandler:(FIRCLSNetworkDataTaskCompletionHandlerBlock)completionHandler {
+ [self startDataTaskWithRequest:request
+ retryLimit:FIRCLSNetworkMaximumRetryCount
+ completionHandler:completionHandler];
+}
+
+- (void)startDownloadTaskWithRequest:(NSURLRequest *)request
+ retryLimit:(NSUInteger)retryLimit
+ tries:(NSUInteger)tries
+ completionHandler:
+ (FIRCLSNetworkDownloadTaskCompletionHandlerBlock)completionHandler {
+ NSURLSessionTask *task = [self.session
+ downloadTaskWithRequest:request
+ completionHandler:^(NSURL *location, NSURLResponse *response, NSError *taskError) {
+ [FIRCLSNetworkResponseHandler
+ handleCompletedResponse:response
+ forOriginalRequest:request
+ error:taskError
+ block:^(BOOL retry, NSError *error) {
+ if (!retry) {
+ completionHandler(location, response, error);
+ return;
+ }
+
+ if (tries >= retryLimit) {
+ NSDictionary *userInfo = @{
+ @"retryLimit" : @(retryLimit),
+ NSURLErrorFailingURLStringErrorKey : request.URL
+ };
+ completionHandler(
+ nil, nil,
+ [NSError
+ errorWithDomain:FIRCLSNetworkErrorDomain
+ code:
+ FIRCLSNetworkErrorMaximumAttemptsReached
+ userInfo:userInfo]);
+ return;
+ }
+
+ [self
+ runAfterRetryValueFromResponse:response
+ attempts:tries
+ block:^{
+ [self
+ startDownloadTaskWithRequest:
+ request
+ retryLimit:
+ retryLimit
+ tries:
+ (tries +
+ 1)
+ completionHandler:
+ completionHandler];
+ }];
+ }];
+ }];
+
+ [task resume];
+
+ if (!task) {
+ completionHandler(nil, nil,
+ [NSError errorWithDomain:FIRCLSNetworkErrorDomain
+ code:FIRCLSNetworkErrorFailedToStartOperation
+ userInfo:nil]);
+ }
+}
+
+- (void)startDownloadTaskWithRequest:(NSURLRequest *)request
+ retryLimit:(NSUInteger)retryLimit
+ completionHandler:
+ (FIRCLSNetworkDownloadTaskCompletionHandlerBlock)completionHandler {
+ [self startDownloadTaskWithRequest:request
+ retryLimit:retryLimit
+ tries:0
+ completionHandler:completionHandler];
+}
+
+- (void)startDownloadTaskWithRequest:(NSURLRequest *)request
+ completionHandler:
+ (FIRCLSNetworkDownloadTaskCompletionHandlerBlock)completionHandler {
+ [self startDownloadTaskWithRequest:request
+ retryLimit:FIRCLSNetworkMaximumRetryCount
+ completionHandler:completionHandler];
+}
+
+- (void)invalidateAndCancel {
+ [self.session invalidateAndCancel];
+}
+
+#pragma mark - NSURLSession Delegate
+- (void)URLSession:(NSURLSession *)session didBecomeInvalidWithError:(NSError *)error {
+}
+
+@end
diff --git a/StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSMultipartMimeStreamEncoder.h b/StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSMultipartMimeStreamEncoder.h
new file mode 100644
index 00000000..c3630a5b
--- /dev/null
+++ b/StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSMultipartMimeStreamEncoder.h
@@ -0,0 +1,88 @@
+// Copyright 2019 Google
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import <Foundation/Foundation.h>
+
+/**
+ * This class is a helper class for generating Multipart requests, as described in
+ * http://www.w3.org/Protocols/rfc1341/7_2_Multipart.html. In the case of multiple part messages, in
+ * which one or more different sets of data are combined in a single body, a "multipart"
+ * Content-Type field must appear in the entity's header. The body must then contain one or more
+ * "body parts," each preceded by an encapsulation boundary, and the last one followed by a closing
+ * boundary. Each part starts with an encapsulation boundary, and then contains a body part
+ * consisting of header area, a blank line, and a body area.
+ */
+@interface FIRCLSMultipartMimeStreamEncoder : NSObject
+
+/**
+ * Convenience class method to populate a NSMutableURLRequest with data from a block that takes an
+ * instance of this class as input.
+ */
++ (void)populateRequest:(NSMutableURLRequest *)request
+ withDataFromEncoder:(void (^)(FIRCLSMultipartMimeStreamEncoder *encoder))block;
+
+/**
+ * Returns a NSString instance with multipart/form-data appended to the boundary.
+ */
++ (NSString *)contentTypeHTTPHeaderValueWithBoundary:(NSString *)boundary;
+/**
+ * Convenience class method that returns an instance of this class
+ */
++ (instancetype)encoderWithStream:(NSOutputStream *)stream andBoundary:(NSString *)boundary;
+/**
+ * Returns a unique boundary string.
+ */
++ (NSString *)generateBoundary;
+/**
+ * Designated initializer
+ * @param stream NSOutputStream associated with the Multipart request
+ * @param boundary the unique Boundary string to be used
+ */
+- (instancetype)initWithStream:(NSOutputStream *)stream
+ andBoundary:(NSString *)boundary NS_DESIGNATED_INITIALIZER;
+- (instancetype)init NS_UNAVAILABLE;
++ (instancetype)new NS_UNAVAILABLE;
+/**
+ * Encodes this block within the boundary on the output stream
+ */
+- (void)encode:(void (^)(void))block;
+/**
+ * Adds the contents of the file data with given Mime type anf fileName within the boundary in
+ * stream
+ */
+- (void)addFileData:(NSData *)data
+ fileName:(NSString *)fileName
+ mimeType:(NSString *)mimeType
+ fieldName:(NSString *)name;
+/**
+ * Convenience method for the method above. Converts fileURL to data and calls the above method.
+ */
+- (void)addFile:(NSURL *)fileURL
+ fileName:(NSString *)fileName
+ mimeType:(NSString *)mimeType
+ fieldName:(NSString *)name;
+/**
+ * Adds this field and value in the stream
+ */
+- (void)addValue:(id)value fieldName:(NSString *)name;
+/**
+ * String referring to the multipart MIME type with boundary
+ */
+@property(nonatomic, copy, readonly) NSString *contentTypeHTTPHeaderValue;
+/**
+ * Length of the data written to stream
+ */
+@property(nonatomic, copy, readonly) NSString *contentLengthHTTPHeaderValue;
+
+@end
diff --git a/StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSMultipartMimeStreamEncoder.m b/StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSMultipartMimeStreamEncoder.m
new file mode 100644
index 00000000..927087da
--- /dev/null
+++ b/StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSMultipartMimeStreamEncoder.m
@@ -0,0 +1,208 @@
+// Copyright 2019 Google
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "Crashlytics/Shared/FIRCLSNetworking/FIRCLSMultipartMimeStreamEncoder.h"
+
+#import "Crashlytics/Crashlytics/Helpers/FIRCLSLogger.h"
+#import "Crashlytics/Shared/FIRCLSByteUtility.h"
+#import "Crashlytics/Shared/FIRCLSUUID.h"
+
+@interface FIRCLSMultipartMimeStreamEncoder () <NSStreamDelegate>
+
+@property(nonatomic) NSUInteger length;
+@property(nonatomic, copy) NSString *boundary;
+@property(nonatomic, copy, readonly) NSData *headerData;
+@property(nonatomic, copy, readonly) NSData *footerData;
+@property(nonatomic, strong) NSOutputStream *outputStream;
+
+@end
+
+@implementation FIRCLSMultipartMimeStreamEncoder
+
++ (void)populateRequest:(NSMutableURLRequest *)request
+ withDataFromEncoder:(void (^)(FIRCLSMultipartMimeStreamEncoder *encoder))block {
+ NSString *boundary = [self generateBoundary];
+
+ NSOutputStream *stream = [NSOutputStream outputStreamToMemory];
+
+ FIRCLSMultipartMimeStreamEncoder *encoder =
+ [[FIRCLSMultipartMimeStreamEncoder alloc] initWithStream:stream andBoundary:boundary];
+
+ [encoder encode:^{
+ block(encoder);
+ }];
+
+ [request setValue:encoder.contentTypeHTTPHeaderValue forHTTPHeaderField:@"Content-Type"];
+ [request setValue:encoder.contentLengthHTTPHeaderValue forHTTPHeaderField:@"Content-Length"];
+
+ NSData *data = [stream propertyForKey:NSStreamDataWrittenToMemoryStreamKey];
+ request.HTTPBody = data;
+}
+
++ (NSString *)contentTypeHTTPHeaderValueWithBoundary:(NSString *)boundary {
+ return [NSString stringWithFormat:@"multipart/form-data; boundary=%@", boundary];
+}
+
++ (instancetype)encoderWithStream:(NSOutputStream *)stream andBoundary:(NSString *)boundary {
+ return [[self alloc] initWithStream:stream andBoundary:boundary];
+}
+
++ (NSString *)generateBoundary {
+ return FIRCLSGenerateUUID();
+}
+
+- (instancetype)initWithStream:(NSOutputStream *)stream andBoundary:(NSString *)boundary {
+ self = [super init];
+ if (!self) {
+ return nil;
+ }
+
+ self.outputStream = stream;
+
+ if (!boundary) {
+ boundary = [FIRCLSMultipartMimeStreamEncoder generateBoundary];
+ }
+
+ _boundary = boundary;
+
+ return self;
+}
+
+- (void)encode:(void (^)(void))block {
+ [self beginEncoding];
+
+ block();
+
+ [self endEncoding];
+}
+
+- (NSString *)contentTypeHTTPHeaderValue {
+ return [[self class] contentTypeHTTPHeaderValueWithBoundary:self.boundary];
+}
+
+- (NSString *)contentLengthHTTPHeaderValue {
+ return [NSString stringWithFormat:@"%lu", (unsigned long)_length];
+}
+
+#pragma - mark MIME part API
+- (void)beginEncoding {
+ _length = 0;
+
+ [self.outputStream open];
+
+ [self writeData:self.headerData];
+}
+
+- (void)endEncoding {
+ [self writeData:self.footerData];
+
+ [self.outputStream close];
+}
+
+- (NSData *)headerData {
+ return [@"MIME-Version: 1.0\r\n" dataUsingEncoding:NSUTF8StringEncoding];
+}
+
+- (NSData *)footerData {
+ return [[NSString stringWithFormat:@"--%@--\r\n", self.boundary]
+ dataUsingEncoding:NSUTF8StringEncoding];
+}
+
+- (void)addFileData:(NSData *)data
+ fileName:(NSString *)fileName
+ mimeType:(NSString *)mimeType
+ fieldName:(NSString *)name {
+ if ([data length] == 0) {
+ FIRCLSErrorLog(@"Unable to MIME encode data with zero length (%@)", name);
+ return;
+ }
+
+ if ([name length] == 0 || [fileName length] == 0) {
+ FIRCLSErrorLog(@"name (%@) or fieldname (%@) is invalid", name, fileName);
+ return;
+ }
+
+ NSMutableString *string;
+
+ string = [NSMutableString
+ stringWithFormat:@"--%@\r\nContent-Disposition: form-data; name=\"%@\"; filename=\"%@\"\r\n",
+ self.boundary, name, fileName];
+
+ if (mimeType) {
+ [string appendFormat:@"Content-Type: %@\r\n", mimeType];
+ [string appendString:@"Content-Transfer-Encoding: binary\r\n\r\n"];
+ } else {
+ [string appendString:@"Content-Type: application/octet-stream\r\n\r\n"];
+ }
+
+ [self writeData:[string dataUsingEncoding:NSUTF8StringEncoding]];
+
+ [self writeData:data];
+
+ [self writeData:[@"\r\n" dataUsingEncoding:NSUTF8StringEncoding]];
+}
+
+- (void)addValue:(id)value fieldName:(NSString *)name {
+ if ([name length] == 0 || !value || value == NSNull.null) {
+ FIRCLSErrorLog(@"name (%@) or value (%@) is invalid", name, value);
+ return;
+ }
+
+ NSMutableString *string;
+
+ string =
+ [NSMutableString stringWithFormat:@"--%@\r\nContent-Disposition: form-data; name=\"%@\"\r\n",
+ self.boundary, name];
+ [string appendString:@"Content-Type: text/plain\r\n\r\n"];
+ [string appendFormat:@"%@\r\n", value];
+
+ [self writeData:[string dataUsingEncoding:NSUTF8StringEncoding]];
+}
+
+- (void)addFile:(NSURL *)fileURL
+ fileName:(NSString *)fileName
+ mimeType:(NSString *)mimeType
+ fieldName:(NSString *)name {
+ NSData *data = [NSData dataWithContentsOfURL:fileURL];
+
+ [self addFileData:data fileName:fileName mimeType:mimeType fieldName:name];
+}
+
+- (BOOL)writeBytes:(const void *)bytes ofLength:(NSUInteger)length {
+ if ([self.outputStream write:bytes maxLength:length] != length) {
+ FIRCLSErrorLog(@"Failed to write bytes to stream");
+ return NO;
+ }
+
+ _length += length;
+
+ return YES;
+}
+
+- (void)writeData:(NSData *)data {
+ FIRCLSEnumerateByteRangesOfNSDataUsingBlock(
+ data, ^(const void *bytes, NSRange byteRange, BOOL *stop) {
+ NSUInteger length = byteRange.length;
+
+ if ([self.outputStream write:bytes maxLength:length] != length) {
+ FIRCLSErrorLog(@"Failed to write data to stream");
+ *stop = YES;
+ return;
+ }
+
+ self->_length += length;
+ });
+}
+
+@end
diff --git a/StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSNetworkResponseHandler.h b/StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSNetworkResponseHandler.h
new file mode 100644
index 00000000..42f0bb49
--- /dev/null
+++ b/StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSNetworkResponseHandler.h
@@ -0,0 +1,87 @@
+// Copyright 2019 Google
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import <Foundation/Foundation.h>
+
+/**
+ * Type to indicate response status
+ */
+typedef NS_ENUM(NSInteger, FIRCLSNetworkClientResponseType) {
+ FIRCLSNetworkClientResponseSuccess,
+ FIRCLSNetworkClientResponseInvalid,
+ FIRCLSNetworkClientResponseFailure,
+ FIRCLSNetworkClientResponseRetry,
+ FIRCLSNetworkClientResponseBackOff
+};
+
+typedef NS_ENUM(NSInteger, FIRCLSNetworkErrorType) {
+ FIRCLSNetworkErrorUnknown = -1,
+ FIRCLSNetworkErrorFailedToStartOperation = -3,
+ FIRCLSNetworkErrorResponseInvalid = -4,
+ FIRCLSNetworkErrorRequestFailed = -5,
+ FIRCLSNetworkErrorMaximumAttemptsReached = -6,
+};
+
+extern NSInteger const FIRCLSNetworkErrorUnknownURLCancelReason;
+
+/**
+ * This block is an input parameter to handleCompletedResponse: and handleCompletedTask: methods of
+ * this class.
+ * @param retryMightSucceed is YES if the request should be retried.
+ * @param error is the error received back in response.
+ */
+typedef void (^FIRCLSNetworkResponseCompletionHandlerBlock)(BOOL retryMightSucceed, NSError *error);
+
+/**
+ * Error domain for Crashlytics network errors
+ */
+extern NSString *const FIRCLSNetworkErrorDomain;
+/**
+ * This class handles network responses.
+ */
+@interface FIRCLSNetworkResponseHandler : NSObject
+/**
+ * Returns the header in the given NSURLResponse with name as key
+ */
++ (NSString *)headerForResponse:(NSURLResponse *)response withKey:(NSString *)key;
+/**
+ * Returns Retry-After header value in response, and if absent returns a default retry value
+ */
++ (NSTimeInterval)retryValueForResponse:(NSURLResponse *)response;
+/**
+ * Checks if the content type for response matches the request
+ */
++ (BOOL)contentTypeForResponse:(NSURLResponse *)response matchesRequest:(NSURLRequest *)request;
+
++ (NSInteger)cancelReasonFromURLError:(NSError *)error;
+
++ (BOOL)retryableURLError:(NSError *)error;
+
+/**
+ * Convenience method that calls back the input block with FIRCLSNetworkClientResponseType after
+ * checking the response code in response
+ */
++ (void)clientResponseType:(NSURLResponse *)response
+ handler:(void (^)(FIRCLSNetworkClientResponseType type,
+ NSInteger statusCode))responseTypeAndStatusCodeHandlerBlock;
+/**
+ * Handles a completed response for request and calls back input block. Populates error even if
+ * error was nil, but response code indicated an error.
+ */
++ (void)handleCompletedResponse:(NSURLResponse *)response
+ forOriginalRequest:(NSURLRequest *)originalRequest
+ error:(NSError *)error
+ block:(FIRCLSNetworkResponseCompletionHandlerBlock)completionHandlerBlock;
+
+@end
diff --git a/StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSNetworkResponseHandler.m b/StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSNetworkResponseHandler.m
new file mode 100644
index 00000000..c46f6ec7
--- /dev/null
+++ b/StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSNetworkResponseHandler.m
@@ -0,0 +1,290 @@
+// Copyright 2019 Google
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "Crashlytics/Shared/FIRCLSNetworking/FIRCLSNetworkResponseHandler.h"
+
+@implementation FIRCLSNetworkResponseHandler
+
+static const NSTimeInterval kFIRCLSNetworkResponseHandlerDefaultRetryInterval = 2.0;
+static NSString *const kFIRCLSNetworkResponseHandlerContentType = @"Content-Type";
+NSString *const FIRCLSNetworkErrorDomain = @"FIRCLSNetworkError";
+
+NSInteger const FIRCLSNetworkErrorUnknownURLCancelReason = -1;
+
+#pragma mark - Header Handling
++ (NSString *)headerForResponse:(NSURLResponse *)response withKey:(NSString *)key {
+ if (![response respondsToSelector:@selector(allHeaderFields)]) {
+ return nil;
+ }
+
+ return [((NSHTTPURLResponse *)response).allHeaderFields objectForKey:key];
+}
+
++ (NSTimeInterval)retryValueForResponse:(NSURLResponse *)response {
+ NSString *retryValueString = [self headerForResponse:response withKey:@"Retry-After"];
+ if (!retryValueString) {
+ return kFIRCLSNetworkResponseHandlerDefaultRetryInterval;
+ }
+
+ NSTimeInterval value = retryValueString.doubleValue;
+ if (value < 0.0) {
+ return kFIRCLSNetworkResponseHandlerDefaultRetryInterval;
+ }
+
+ return value;
+}
+
++ (NSString *)requestIdForResponse:(NSURLResponse *)response {
+ return [self headerForResponse:response withKey:@"X-Request-Id"];
+}
+
++ (BOOL)contentTypeForResponse:(NSURLResponse *)response matchesRequest:(NSURLRequest *)request {
+ NSString *accept = [request.allHTTPHeaderFields objectForKey:@"Accept"];
+ if (!accept) {
+ // An omitted accept header is defined to match everything
+ return YES;
+ }
+
+ NSString *contentHeader = [self.class headerForResponse:response
+ withKey:kFIRCLSNetworkResponseHandlerContentType];
+ if (!contentHeader) {
+ // FIRCLSDeveloperLog("Network", @"Content-Type not present in response");
+ return NO;
+ }
+
+ NSString *acceptCharset = request.allHTTPHeaderFields[@"Accept-Charset"];
+
+ NSArray *parts = [contentHeader componentsSeparatedByString:@"; charset="];
+ if (!parts) {
+ parts = @[ contentHeader ];
+ }
+
+ if ([[parts objectAtIndex:0] caseInsensitiveCompare:accept] != NSOrderedSame) {
+ // FIRCLSDeveloperLog("Network", @"Content-Type does not match Accept");
+ return NO;
+ }
+
+ if (!acceptCharset) {
+ return YES;
+ }
+
+ if (parts.count < 2) {
+ return YES;
+ }
+
+ return [[parts objectAtIndex:1] caseInsensitiveCompare:acceptCharset] == NSOrderedSame;
+}
+
++ (NSInteger)cancelReasonFromURLError:(NSError *)error {
+ if (![[error domain] isEqualToString:NSURLErrorDomain]) {
+ return FIRCLSNetworkErrorUnknownURLCancelReason;
+ }
+
+ if ([error code] != NSURLErrorCancelled) {
+ return FIRCLSNetworkErrorUnknownURLCancelReason;
+ }
+
+ NSNumber *reason = [[error userInfo] objectForKey:NSURLErrorBackgroundTaskCancelledReasonKey];
+ if (reason == nil) {
+ return FIRCLSNetworkErrorUnknownURLCancelReason;
+ }
+
+ return [reason integerValue];
+}
+
++ (BOOL)retryableURLError:(NSError *)error {
+ // So far, the only task errors seen are NSURLErrorDomain. For others, we're not
+ // sure what to do.
+ if (![[error domain] isEqualToString:NSURLErrorDomain]) {
+ return NO;
+ }
+
+ // cases that we know are definitely not retryable
+ switch ([error code]) {
+ case NSURLErrorBadURL:
+ case NSURLErrorUnsupportedURL:
+ case NSURLErrorHTTPTooManyRedirects:
+ case NSURLErrorRedirectToNonExistentLocation:
+ case NSURLErrorUserCancelledAuthentication:
+ case NSURLErrorUserAuthenticationRequired:
+ case NSURLErrorAppTransportSecurityRequiresSecureConnection:
+ case NSURLErrorFileDoesNotExist:
+ case NSURLErrorFileIsDirectory:
+ case NSURLErrorDataLengthExceedsMaximum:
+ case NSURLErrorSecureConnectionFailed:
+ case NSURLErrorServerCertificateHasBadDate:
+ case NSURLErrorServerCertificateUntrusted:
+ case NSURLErrorServerCertificateHasUnknownRoot:
+ case NSURLErrorServerCertificateNotYetValid:
+ case NSURLErrorClientCertificateRejected:
+ case NSURLErrorClientCertificateRequired:
+ case NSURLErrorBackgroundSessionRequiresSharedContainer:
+ return NO;
+ }
+
+ // All other errors, as far as I can tell, are things that could clear up
+ // without action on the part of the client.
+
+ // NSURLErrorCancelled is a potential special-case. I believe there are
+ // situations where a cancelled request cannot be successfully restarted. But,
+ // until I can prove it, we'll retry. There are defnitely many cases where
+ // a cancelled request definitely can be restarted and will work.
+
+ return YES;
+}
+
+#pragma mark - Error Creation
++ (NSError *)errorForCode:(NSInteger)code userInfo:(NSDictionary *)userInfo {
+ return [NSError errorWithDomain:FIRCLSNetworkErrorDomain code:code userInfo:userInfo];
+}
+
++ (NSError *)errorForResponse:(NSURLResponse *)response
+ ofType:(FIRCLSNetworkClientResponseType)type
+ status:(NSInteger)status {
+ if (type == FIRCLSNetworkClientResponseSuccess) {
+ return nil;
+ }
+
+ NSString *requestId = [self requestIdForResponse:response];
+ NSString *contentType = [self headerForResponse:response
+ withKey:kFIRCLSNetworkResponseHandlerContentType];
+
+ // this could be nil, so be careful
+ requestId = requestId ? requestId : @"";
+ contentType = contentType ? contentType : @"";
+
+ NSDictionary *userInfo = @{
+ @"type" : @(type),
+ @"status_code" : @(status),
+ @"request_id" : requestId,
+ @"content_type" : contentType
+ };
+
+ // compute a reasonable error code type
+ NSInteger errorCode = FIRCLSNetworkErrorUnknown;
+ switch (type) {
+ case FIRCLSNetworkClientResponseFailure:
+ errorCode = FIRCLSNetworkErrorRequestFailed;
+ break;
+ case FIRCLSNetworkClientResponseInvalid:
+ errorCode = FIRCLSNetworkErrorResponseInvalid;
+ break;
+ default:
+ break;
+ }
+
+ return [self errorForCode:errorCode userInfo:userInfo];
+}
+
++ (void)clientResponseType:(NSURLResponse *)response
+ handler:(void (^)(FIRCLSNetworkClientResponseType type,
+ NSInteger statusCode))responseTypeAndStatusCodeHandlerBlock {
+ if (![response respondsToSelector:@selector(statusCode)]) {
+ responseTypeAndStatusCodeHandlerBlock(FIRCLSNetworkClientResponseInvalid, 0);
+ return;
+ }
+
+ NSInteger code = ((NSHTTPURLResponse *)response).statusCode;
+
+ switch (code) {
+ case 200:
+ case 201:
+ case 202:
+ case 204:
+ case 304:
+ responseTypeAndStatusCodeHandlerBlock(FIRCLSNetworkClientResponseSuccess, code);
+ return;
+ case 420:
+ case 429:
+ responseTypeAndStatusCodeHandlerBlock(FIRCLSNetworkClientResponseBackOff, code);
+ return;
+ case 408:
+ responseTypeAndStatusCodeHandlerBlock(FIRCLSNetworkClientResponseRetry, code);
+ return;
+ case 400:
+ case 401:
+ case 403:
+ case 404:
+ case 406:
+ case 410:
+ case 411:
+ case 413:
+ case 419:
+ case 422:
+ case 431:
+ responseTypeAndStatusCodeHandlerBlock(FIRCLSNetworkClientResponseFailure, code);
+ return;
+ }
+
+ // check for a 5xx
+ if (code >= 500 && code <= 599) {
+ responseTypeAndStatusCodeHandlerBlock(FIRCLSNetworkClientResponseRetry, code);
+ return;
+ }
+
+ responseTypeAndStatusCodeHandlerBlock(FIRCLSNetworkClientResponseInvalid, code);
+}
+
++ (void)handleCompletedResponse:(NSURLResponse *)response
+ forOriginalRequest:(NSURLRequest *)originalRequest
+ error:(NSError *)originalError
+ block:
+ (FIRCLSNetworkResponseCompletionHandlerBlock)completionHandlerBlock {
+ // if we have an error, we can just continue
+ if (originalError) {
+ BOOL retryable = [self retryableURLError:originalError];
+
+ completionHandlerBlock(retryable, originalError);
+ return;
+ }
+
+ [self.class clientResponseType:response
+ handler:^(FIRCLSNetworkClientResponseType type, NSInteger statusCode) {
+ NSError *error = nil;
+
+ switch (type) {
+ case FIRCLSNetworkClientResponseInvalid:
+ error = [self errorForResponse:response
+ ofType:type
+ status:statusCode];
+ break;
+ case FIRCLSNetworkClientResponseBackOff:
+ case FIRCLSNetworkClientResponseRetry:
+ error = [self errorForResponse:response
+ ofType:type
+ status:statusCode];
+ completionHandlerBlock(YES, error);
+ return;
+ case FIRCLSNetworkClientResponseFailure:
+ error = [self errorForResponse:response
+ ofType:type
+ status:statusCode];
+ break;
+ case FIRCLSNetworkClientResponseSuccess:
+ if (![self contentTypeForResponse:response
+ matchesRequest:originalRequest]) {
+ error = [self errorForResponse:response
+ ofType:FIRCLSNetworkClientResponseInvalid
+ status:statusCode];
+ break;
+ }
+
+ break;
+ }
+
+ completionHandlerBlock(NO, error);
+ }];
+}
+
+@end
diff --git a/StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSURLBuilder.h b/StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSURLBuilder.h
new file mode 100644
index 00000000..c8fbaa94
--- /dev/null
+++ b/StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSURLBuilder.h
@@ -0,0 +1,44 @@
+// Copyright 2019 Google
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import <Foundation/Foundation.h>
+
+/**
+ * This is a convenience class to ease constructing NSURLs.
+ */
+@interface FIRCLSURLBuilder : NSObject
+
+/**
+ * Convenience method that returns a FIRCLSURLBuilder instance with the input base URL appended to
+ * it.
+ */
++ (instancetype)URLWithBase:(NSString *)base;
+/**
+ * Appends the component to the URL being built by FIRCLSURLBuilder instance
+ */
+- (void)appendComponent:(NSString *)component;
+/**
+ * Escapes and appends the component to the URL being built by FIRCLSURLBuilder instance
+ */
+- (void)escapeAndAppendComponent:(NSString *)component;
+/**
+ * Adds a query and value to the URL being built
+ */
+- (void)appendValue:(id)value forQueryParam:(NSString *)param;
+/**
+ * Returns the built URL
+ */
+- (NSURL *)URL;
+
+@end
diff --git a/StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSURLBuilder.m b/StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSURLBuilder.m
new file mode 100644
index 00000000..a027e4f1
--- /dev/null
+++ b/StoneIsland/platforms/ios/Pods/FirebaseCrashlytics/Crashlytics/Shared/FIRCLSNetworking/FIRCLSURLBuilder.m
@@ -0,0 +1,103 @@
+// Copyright 2019 Google
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "Crashlytics/Shared/FIRCLSNetworking/FIRCLSURLBuilder.h"
+
+#import "Crashlytics/Crashlytics/Helpers/FIRCLSLogger.h"
+
+@interface FIRCLSURLBuilder ()
+
+@property(nonatomic) NSMutableString *URLString;
+@property(nonatomic) NSUInteger queryParams;
+
+- (NSString *)escapeString:(NSString *)string;
+
+@end
+
+@implementation FIRCLSURLBuilder
+
++ (instancetype)URLWithBase:(NSString *)base {
+ FIRCLSURLBuilder *url = [[FIRCLSURLBuilder alloc] init];
+
+ [url appendComponent:base];
+
+ return url;
+}
+
+- (instancetype)init {
+ self = [super init];
+ if (!self) {
+ return nil;
+ }
+
+ _URLString = [[NSMutableString alloc] init];
+ _queryParams = 0;
+
+ return self;
+}
+
+- (NSString *)escapeString:(NSString *)string {
+#if TARGET_OS_WATCH
+ // TODO: Question - Why does watchOS use a different encoding from the other platforms and the
+ // Android SDK?
+ return
+ [string stringByAddingPercentEncodingWithAllowedCharacters:[NSCharacterSet
+ URLPathAllowedCharacterSet]];
+#else
+ return
+ [string stringByAddingPercentEncodingWithAllowedCharacters:NSCharacterSet
+ .URLQueryAllowedCharacterSet];
+#endif
+}
+
+- (void)appendComponent:(NSString *)component {
+ if (component.length == 0) {
+ FIRCLSErrorLog(@"URLBuilder parameter component must not be empty");
+ return;
+ }
+
+ [self.URLString appendString:component];
+}
+
+- (void)escapeAndAppendComponent:(NSString *)component {
+ [self appendComponent:[self escapeString:component]];
+}
+
+- (void)appendValue:(id)value forQueryParam:(NSString *)param {
+ if (!value) {
+ return;
+ }
+
+ if (self.queryParams == 0) {
+ [self appendComponent:@"?"];
+ } else {
+ [self appendComponent:@"&"];
+ }
+
+ self.queryParams += 1;
+
+ [self appendComponent:param];
+ [self appendComponent:@"="];
+ if ([value isKindOfClass:NSString.class]) {
+ [self escapeAndAppendComponent:value];
+ } else {
+ [self escapeAndAppendComponent:[value description]];
+ }
+}
+
+- (NSURL *)URL {
+ return [NSURL URLWithString:self.URLString];
+}
+
+@end