123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182 |
- //
- // RNFetchBlobNetwork.m
- // RNFetchBlob
- //
- // Created by wkh237 on 2016/6/6.
- // Copyright © 2016 wkh237. All rights reserved.
- //
-
-
- #import <Foundation/Foundation.h>
- #import "RNFetchBlobNetwork.h"
-
- #import "RNFetchBlob.h"
- #import "RNFetchBlobConst.h"
- #import "RNFetchBlobProgress.h"
-
- #if __has_include(<React/RCTAssert.h>)
- #import <React/RCTRootView.h>
- #import <React/RCTLog.h>
- #import <React/RCTEventDispatcher.h>
- #import <React/RCTBridge.h>
- #else
- #import "RCTRootView.h"
- #import "RCTLog.h"
- #import "RCTEventDispatcher.h"
- #import "RCTBridge.h"
- #endif
-
- ////////////////////////////////////////
- //
- // HTTP request handler
- //
- ////////////////////////////////////////
-
- NSMapTable * expirationTable;
-
- __attribute__((constructor))
- static void initialize_tables() {
- if (expirationTable == nil) {
- expirationTable = [[NSMapTable alloc] init];
- }
- }
-
-
- @implementation RNFetchBlobNetwork
-
-
- - (id)init {
- self = [super init];
- if (self) {
- self.requestsTable = [NSMapTable mapTableWithKeyOptions:NSMapTableStrongMemory valueOptions:NSMapTableWeakMemory];
-
- self.taskQueue = [[NSOperationQueue alloc] init];
- self.taskQueue.qualityOfService = NSQualityOfServiceUtility;
- self.taskQueue.maxConcurrentOperationCount = 10;
- self.rebindProgressDict = [NSMutableDictionary dictionary];
- self.rebindUploadProgressDict = [NSMutableDictionary dictionary];
- }
-
- return self;
- }
-
- + (RNFetchBlobNetwork* _Nullable)sharedInstance {
- static id _sharedInstance = nil;
- static dispatch_once_t onceToken;
-
- dispatch_once(&onceToken, ^{
- _sharedInstance = [[self alloc] init];
- });
-
- return _sharedInstance;
- }
-
- - (void) sendRequest:(__weak NSDictionary * _Nullable )options
- contentLength:(long) contentLength
- bridge:(RCTBridge * _Nullable)bridgeRef
- taskId:(NSString * _Nullable)taskId
- withRequest:(__weak NSURLRequest * _Nullable)req
- callback:(_Nullable RCTResponseSenderBlock) callback
- {
- RNFetchBlobRequest *request = [[RNFetchBlobRequest alloc] init];
- [request sendRequest:options
- contentLength:contentLength
- bridge:bridgeRef
- taskId:taskId
- withRequest:req
- taskOperationQueue:self.taskQueue
- callback:callback];
-
- @synchronized([RNFetchBlobNetwork class]) {
- [self.requestsTable setObject:request forKey:taskId];
- [self checkProgressConfig];
- }
- }
-
- - (void) checkProgressConfig {
- //reconfig progress
- [self.rebindProgressDict enumerateKeysAndObjectsUsingBlock:^(NSString * _Nonnull key, RNFetchBlobProgress * _Nonnull config, BOOL * _Nonnull stop) {
- [self enableProgressReport:key config:config];
- }];
- [self.rebindProgressDict removeAllObjects];
-
- //reconfig uploadProgress
- [self.rebindUploadProgressDict enumerateKeysAndObjectsUsingBlock:^(NSString * _Nonnull key, RNFetchBlobProgress * _Nonnull config, BOOL * _Nonnull stop) {
- [self enableUploadProgress:key config:config];
- }];
- [self.rebindUploadProgressDict removeAllObjects];
- }
-
- - (void) enableProgressReport:(NSString *) taskId config:(RNFetchBlobProgress *)config
- {
- if (config) {
- @synchronized ([RNFetchBlobNetwork class]) {
- if (![self.requestsTable objectForKey:taskId]) {
- [self.rebindProgressDict setValue:config forKey:taskId];
- } else {
- [self.requestsTable objectForKey:taskId].progressConfig = config;
- }
- }
- }
- }
-
- - (void) enableUploadProgress:(NSString *) taskId config:(RNFetchBlobProgress *)config
- {
- if (config) {
- @synchronized ([RNFetchBlobNetwork class]) {
- if (![self.requestsTable objectForKey:taskId]) {
- [self.rebindUploadProgressDict setValue:config forKey:taskId];
- } else {
- [self.requestsTable objectForKey:taskId].uploadProgressConfig = config;
- }
- }
- }
- }
-
- - (void) cancelRequest:(NSString *)taskId
- {
- NSURLSessionDataTask * task;
-
- @synchronized ([RNFetchBlobNetwork class]) {
- task = [self.requestsTable objectForKey:taskId].task;
- }
-
- if (task && task.state == NSURLSessionTaskStateRunning) {
- [task cancel];
- }
- }
-
- // removing case from headers
- + (NSMutableDictionary *) normalizeHeaders:(NSDictionary *)headers
- {
- NSMutableDictionary * mheaders = [[NSMutableDictionary alloc]init];
- for (NSString * key in headers) {
- [mheaders setValue:[headers valueForKey:key] forKey:[key lowercaseString]];
- }
-
- return mheaders;
- }
-
- // #115 Invoke fetch.expire event on those expired requests so that the expired event can be handled
- + (void) emitExpiredTasks
- {
- @synchronized ([RNFetchBlobNetwork class]){
- NSEnumerator * emu = [expirationTable keyEnumerator];
- NSString * key;
-
- while ((key = [emu nextObject]))
- {
- RCTBridge * bridge = [RNFetchBlob getRCTBridge];
- id args = @{ @"taskId": key };
- [bridge.eventDispatcher sendDeviceEventWithName:EVENT_EXPIRE body:args];
-
- }
-
- // clear expired task entries
- [expirationTable removeAllObjects];
- expirationTable = [[NSMapTable alloc] init];
- }
- }
-
- @end
|