1. 程式人生 > >iOS 網路請求優化之取消請求

iOS 網路請求優化之取消請求

在這裡插入圖片描述

  • 頁面返回的時候,將網路請求取消
  • 同一個請求多次請求時,短時間忽略相同的請求
  • 同一個請求多次請求時,取消之前發出的請求
  • 傳送的請求,多次嘗試並確保成功

最近發現很多網路請求都有可以優化的地方,雖然開發和測試都沒有發現問題,但是可以讓程式碼更加的優雅。想到了有四個方面可以優化,親測有效。

1. 頁面返回的時候取消網路請求

在一個介面進行多個請求的時候,而有可能使用者馬上點選了返回按鈕,那麼如果是使用了AFNetworking的情況,此時ViewController不會馬上銷燬,需要等到網路請求返回並執行完畢block後才會銷燬此ViewController。
那麼會存在2個問題:

  • 網路請求返回的資料沒有使用,浪費流量。
  • ViewController銷燬延遲,記憶體不能及時釋放。
1.1 記錄所有的請求

將頁面中進行的所有請求記錄,包括controller和view中發起的請求,當然設計為不是強制的,而是通過根據業務選擇新增。採用BaseViewController的方式,每一個ViewController都需要繼承BaseViewController,然後新增新增請求和取消請求的方法。

當網路請求完成後,主動將請求從記錄中移除,減少返回時的迴圈遍歷操作。

#pragma mark - Cancel Task

/** 記錄將需要在退出VC取消的請求。
 *  在記錄的時候,清理已經請求完成的task
 *  如果請求需要有取消功能,那麼在failure的block中,需要新增對取消的失敗不做任務處理的實現。
 */
- (void)addSessionDataTask:(NSURLSessionDataTask *)task;

/** 移除已經請求成功的請求
 * 在請求完成的block中,新增移除的操作
 */
- (void)removeSessionDataTask:(NSURLSessionDataTask *)task;

/** 取消所有的請求 */
- (void)cancelAllSessionDataTask;

BaseViewController.m的實現為:

@property (nonatomic, strong) NSMutableArray<NSURLSessionDataTask *> *sessionDataTaskMArr;

#pragma mark - Cancel Task

/** 將需要在退出VC取消的請求,記錄。
 *  在記錄的時候,清理已經請求完成的task
 */
- (void)addSessionDataTask:(NSURLSessionDataTask *)task
{
    if (nil == task) {
        return;
    }

    [self.sessionDataTaskMArr addObject:task];
}

/** 移除已經請求成功的請求 */
- (void)removeSessionDataTask:(NSURLSessionDataTask *)task
{
    [self.sessionDataTaskMArr removeObject:task];
}

/** 取消所有的請求 */
- (void)cancelAllSessionDataTask
{
    if (0 >= [self.sessionDataTaskMArr count]) {
        return;
    }

    for (NSURLSessionDataTask *dataTask in self.sessionDataTaskMArr) {
        if (NSURLSessionTaskStateRunning == dataTask.state
            || NSURLSessionTaskStateSuspended == dataTask.state) {
            [dataTask cancel];
        }
    }

    [self.sessionDataTaskMArr removeAllObjects];
}

- (NSMutableArray *)sessionDataTaskMArr
{
    if (nil == _sessionDataTaskMArr) {
        _sessionDataTaskMArr = [[NSMutableArray alloc] initWithCapacity:5];
    }

    return _sessionDataTaskMArr;
}
1.2 ViewController新增請求

在ViewController發起的請求,那麼直接將請求返回的NSURLSessionDataTask,呼叫BaseViewController方法記錄:

- (void)addSessionDataTask:(NSURLSessionDataTask *)task;
1.3 View的新增請求

如果是在View中發起的請求,那麼需要根據View來獲取所在的ViewController。建立BaseView,讓發起請求的View繼承BaseView,在BaseView中實現新增記錄請求的方法。實現如下:

#pragma mark - Cancel Task

/** 記錄將需要在退出VC取消的請求。
 *  在記錄的時候,清理已經請求完成的task
 *  如果請求需要有取消功能,那麼在failure的block中,需要新增對取消的失敗不做任務處理的實現。
 */
- (void)addSessionDataTask:(NSURLSessionDataTask *)task;

/** 移除已經請求成功的請求
 * 在請求完成的block中,新增移除的操作
 */
- (void)removeSessionDataTask:(NSURLSessionDataTask *)task;

BaseView.m的實現為:

@property (nonatomic, strong) UIViewController *rootViewController;

#pragma mark - Cancel Task

/** 將需要在退出VC取消的請求,記錄。
 *  在記錄的時候,清理已經請求完成的task
 */
- (void)addSessionDataTask:(NSURLSessionDataTask *)task
{
    UIViewController *currentVC = self.rootViewController;

    if ([currentVC isKindOfClass:[HQBaseViewController class]]) {
        [(HQBaseViewController *)currentVC addSessionDataTask:task];
    }
}

/** 移除已經請求成功的請求
 * 在請求完成的block中,新增移除的操作
 */
- (void)removeSessionDataTask:(NSURLSessionDataTask *)task
{
    UIViewController *currentVC = self.rootViewController;

    if ([currentVC isKindOfClass:[HQBaseViewController class]]) {
        [(HQBaseViewController *)currentVC removeSessionDataTask:task];
    }
}


#pragma mark - Private

- (UIViewController *)rootViewController
{
    if (nil == _rootViewController) {
        for (UIView *next = [self superview]; next; next = next.superview) {
            UIResponder *nextResponder = [next nextResponder];
            if ([nextResponder isKindOfClass:[UIViewController class]]) {
                _rootViewController = (UIViewController *)nextResponder;

                return _rootViewController;
            }
        }
    }

    return _rootViewController;
}
1.4 取消所有請求

viewController的消失,分為dismiss和pop兩種情況,所以在BaseViewController中,新增取消請求:

#pragma mark - Override Methods

- (void)dismissViewControllerAnimated: (BOOL)flag completion: (void (^ __nullable)(void))completion NS_AVAILABLE_IOS(5_0)
{
    [self cancelAllSessionDataTask];

    [super dismissViewControllerAnimated:flag completion:completion];
}

然後需要實現一個BaseNavigationController來過載pop的3個方法,並對所有的viewController進行取消請求,如下:

- (nullable UIViewController *)popViewControllerAnimated:(BOOL)animated
{
    // 取消請求
    UIViewController *viewController = [super popViewControllerAnimated:animated];
    if ([viewController isKindOfClass:[HQBaseViewController class]]) {
        [(HQBaseViewController *)viewController cancelAllSessionDataTask];
    }

    return viewController;
}
- (nullable NSArray<__kindof UIViewController *> *)popToViewController:(UIViewController *)viewController animated:(BOOL)animated
{
    NSArray *viewControllerVCs = [super popToViewController:viewController animated:animated];

    for (UIViewController *vc in viewControllerVCs) {
        if ([vc isKindOfClass:[HQBaseViewController class]]) {
            [(HQBaseViewController *)vc cancelAllSessionDataTask];
        }
    }

    return viewControllerVCs;
}
- (nullable NSArray<__kindof UIViewController *> *)popToRootViewControllerAnimated:(BOOL)animated
{
    NSArray *viewControllerVCs = [super popToRootViewControllerAnimated:animated];

    for (UIViewController *vc in viewControllerVCs) {
        if ([vc isKindOfClass:[HQBaseViewController class]]) {
            [(HQBaseViewController *)vc cancelAllSessionDataTask];
        }
    }

    return viewControllerVCs;
}

Done,取消網路請求搞定。使用這樣的實現方式是為了避免修改之前的程式碼,可以做到零侵入。可以對需要新增的ViewController進行新增。
注意:取消請求的返回需要進行特殊處理。

2. 同一個請求多次請求時,短時間忽略相同的請求

當進行重新整理操作時,如果在請求還沒有返回之前,一直在重新整理操作,不管是狂點還是亂點。那麼第一個請求發出後,短時間內可以不進行重複請求。
程式碼實現見下面的BaseViewModel。

3. 同一個請求多次請求時,取消之前發出的請求

如果是在搜尋操作,那麼每次輸入關鍵字的時候,之前發出的請求可以取消,僅僅顯示最後的請求結果。
採用的方法為建立一個BaseViewModel,所有的請求操作繼承BaseViewModel,在發起請求之前進行一次判斷。程式碼如下:

#pragma mark - 忽略請求

/** 忽略請求,當請求的url和引數都是一樣的時候,在短時間內不發起再次請求, 預設3秒 */
- (BOOL)ignoreRequestWithUrl:(NSString *)url params:(NSDictionary *)params;

/** 忽略請求,當請求的url和引數都是一樣的時候,在短時間內不發起再次請求 */
- (BOOL)ignoreRequestWithUrl:(NSString *)url params:(NSDictionary *)params timeInterval:(NSTimeInterval)timeInterval;


#pragma mark - 取消之前的請求

/** 取消之前的同一個url的網路請求
 *  在failure分支中,判斷如果是取消操作,那麼不做任何處理
 *  在success和failure分支中,都要呼叫clearTaskSessionWithUrl:方法,進行記憶體釋放
 */
- (void)cancelLastTaskSessionWithUrl:(NSString *)url currentTaskSession:(NSURLSessionTask *)task;

/** 清除url繫結的sessionTask */
- (void)clearTaskSessionWithUrl:(NSString *)url;

BaseViewModel.m的實現:

@property (nonatomic, strong) NSMutableDictionary *requestTimeMDic;
@property (nonatomic, strong) NSMutableDictionary *cancelTaskMDic;

- (BOOL)ignoreRequestWithUrl:(NSString *)url params:(NSDictionary *)params
{
    return [self ignoreRequestWithUrl:url params:params timeInterval:kRequestTimeInterval];
}

- (BOOL)ignoreRequestWithUrl:(NSString *)url params:(NSDictionary *)params timeInterval:(NSTimeInterval)timeInterval
{
    NSString *requestStr = [NSString stringWithFormat:@"%@%@", url, [params uq_URLQueryString]];
    NSString *requestMD5 = [NSString md5:requestStr];
    NSTimeInterval nowTime = [[NSDate date] timeIntervalSince1970];
    NSNumber *lastTimeNum = [self.requestTimeMDic objectForKey:requestMD5];

    WS(weakSelf);
    dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(timeInterval * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
        // 超過忽略時間後,將值清空
        [weakSelf.requestTimeMDic removeObjectForKey:requestMD5];
    });


    if (timeInterval < (nowTime - [lastTimeNum doubleValue])) {
        if (0.01 > [lastTimeNum doubleValue]) {
            [self.requestTimeMDic setObject:@(nowTime) forKey:requestMD5];
        }

        return NO;
    } else {
        return YES;
    }
}

- (void)cancelLastTaskSessionWithUrl:(NSString *)url currentTaskSession:(NSURLSessionTask *)task
{
    NSURLSessionTask *lastSessionTask = [self.cancelTaskMDic objectForKey:url];

    if (nil == lastSessionTask) {
        [self.cancelTaskMDic setObject:task forKey:url];

        return;
    }

    [lastSessionTask cancel];
}

- (void)clearTaskSessionWithUrl:(NSString *)url
{
    [self.cancelTaskMDic removeObjectForKey:url];
}




#pragma mark - Remove Unused Things


#pragma mark - Private Methods


#pragma mark - Getter Methods

- (NSMutableDictionary *)requestTimeMDic
{
    if (nil == _requestTimeMDic) {
        _requestTimeMDic = [[NSMutableDictionary alloc] initWithCapacity:5];
    }

    return _requestTimeMDic;
}

- (NSMutableDictionary *)cancelTaskMDic
{
    if (nil == _cancelTaskMDic) {
        _cancelTaskMDic = [[NSMutableDictionary alloc] initWithCapacity:5];
    }

    return _cancelTaskMDic;
}

思路很簡單,將請求的url和引數進行一次MD5記錄,然後將時間作為值。

4. 傳送的請求,多次嘗試並確保成功

需要確保請求成功,並且有可能頁面已經摧毀。那麼請求需要加入到單例中,在單例中進行多次請求。新增一個網路是否可用的判斷,當網路不能使用時,暫停嘗試。
設計的再完美一點,就是(1)做本地化快取.(2)新增一個成功後的反饋這個看業務需求吧。
先建立一個Model類,用來記錄申請的請求引數。

@interface HXWebServiceRequestModel : HXBaseJSONModel

/** 重試的剩餘次數 */
@property (nonatomic, assign) NSInteger times;

/** 請求型別 */
@property (nonatomic, assign) RequestType requestType;

/** 請求url */
@property (nonatomic, strong) NSString *urlStr;

/** 請求引數 */
@property (nonatomic, strong) NSDictionary *params;

/** upload時的陣列 */
@property (nonatomic, strong) NSArray *formDataArray;

/** 是否在請求 */
@property (nonatomic, assign) BOOL isRequesting;

@end

@implementation HXWebServiceRequestModel

@end

WebServiceManager程式碼如下:

/** 重試的次數,預設為3次 */
@property (nonatomic, assign) NSUInteger maxRetryTimes;

/** 建立單例,可以在介面消失後,繼續執行 */
+ (instancetype)shareInstace;

/** 將執行的請求儲存,進行多次重試,指導成功 */
- (void)requestWithType:(RequestType)type url:(NSString *)url params:(NSDictionary *)param formDataArray:(NSArray *)formDataArray;

WebServicemanager.m的實現:

static NSTimeInterval kTimeInterval = 3.0;

@property (nonatomic, strong) NSTimer *timer;

@property (nonatomic, strong) NSMutableArray<HXWebServiceRequestModel *> *requestMArr;


+ (instancetype)shareInstace
{
    static HXWebServiceManager *webServiceManager = nil;
    static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        webServiceManager = [[HXWebServiceManager alloc] init];

        webServiceManager.maxRetryTimes = 3;

        [webServiceManager initialNetwork];
    });

    return webServiceManager;
}

- (void)requestWithType:(RequestType)type url:(NSString *)url params:(NSDictionary *)param formDataArray:(NSArray *)formDataArray
{
    HXWebServiceRequestModel *model = [[HXWebServiceRequestModel alloc] init];
    model.times = self.maxRetryTimes;
    model.requestType = type;
    model.urlStr = url;
    model.params = param;
    model.formDataArray = formDataArray;
    model.isRequesting = NO;

    [self.requestMArr addObject:model];

    if (![self.timer isValid]) {
        [self.timer fire];
    }
}



#pragma mark - Initial Methods

- (void)initialNetwork
{
    [[NSNotificationCenter defaultCenter] addObserver:self
                                             selector:@selector(networkChanged:)
                                                 name:AFNetworkingReachabilityDidChangeNotification
                                               object:nil];
}

- (void)networkChanged:(NSNotification *)notification
{
    NSNumber *status = [notification.userInfo objectForKey:AFNetworkingReachabilityNotificationStatusItem];

    if (AFNetworkReachabilityStatusNotReachable == [status integerValue]) {
        if (self.timer.isValid) {
            self.timer.fireDate = [NSDate distantFuture];
        }
    } else {
        if (![self.timer isValid]) {
            [self.timer fire];
        } else {
            self.timer.fireDate = [NSDate date];
        }
    }
}


#pragma mark - Target Methods

- (void)requestNetwork
{
    if (0 >= [self.requestMArr count]
        || ![[AFNetworkReachabilityManager sharedManager] isReachable]) {
        [self.timer invalidate];
        self.timer = nil;

        return;
    }

    for (HXWebServiceRequestModel *model in self.requestMArr) {
        [self requestWithModel:model];
    }
}

- (void)requestWithModel:(HXWebServiceRequestModel *)model
{
    if (model.isRequesting) {
        return;
    }

    WS(weakSelf);
    switch (model.requestType) {
        case kRequestTypeGet:
        {
            [HXQWebService getRequest:model.urlStr
                           parameters:model.params
                             progress:nil
                              success:^(ErrorCode status, NSString *msg, NSDictionary *data) {
                                  model.isRequesting = NO;

                                  if (status == kNoError
                                      || 0 >= model.times) {
                                      [weakSelf.requestMArr removeObject:model];
                                  }

                              } failure:^(ErrorCode status, NSString *msg, NSDictionary *data) {
                                  model.isRequesting = NO;
                              }];
        }
            break;

        case kRequestTypePut:
        {
            [HXQWebService putRequest:model.urlStr
                           parameters:model.params
                              success:^(ErrorCode status, NSString *msg, NSDictionary *data) {
                                  model.isRequesting = NO;

                                  if (status == kNoError
                                      || 0 >= model.times) {
                                      [weakSelf.requestMArr removeObject:model];
                                  }
                              } failure:^(ErrorCode status, NSString *msg, NSDictionary *data) {
                                  model.isRequesting = NO;
                              }];
        }
            break;

        case kRequestTypePost:
        {
            [HXQWebService postRequest:model.urlStr
                            parameters:model.params
                              progress:nil
                               success:^(ErrorCode status, NSString *msg, NSDictionary *data) {
                                   model.isRequesting = NO;

                                   if (status == kNoError
                                       || 0 >= model.times) {
                                       [weakSelf.requestMArr removeObject:model];
                                   }
                               } failure:^(ErrorCode status, NSString *msg, NSDictionary *data) {
                                   model.isRequesting = NO;
                               }];
        }
            break;

        case kRequestTypeUpload:
        {
            [HXQWebService uploadRequest:model.urlStr
                              parameters:model.params
                           formDataArray:model.formDataArray
                                progress:nil
                                 success:^(ErrorCode status, NSString *msg, NSDictionary *data) {
                                     model.isRequesting = NO;

                                     if (status == kNoError
                                         || 0 >= model.times) {
                                         [weakSelf.requestMArr removeObject:model];
                                     }
                                 } failure:^(ErrorCode status, NSString *msg, NSDictionary *data) {
                                     model.isRequesting = NO;
                                 }];
        }
            break;

        case kRequestTypeDelete:
        {
            [HXQWebService deleteRequest:model.urlStr
                              parameters:model.params
                                 success:^(ErrorCode status, NSString *msg, NSDictionary *data) {
                                     model.isRequesting = NO;

                                     if (status == kNoError
                                         || 0 >= model.times) {
                                         [weakSelf.requestMArr removeObject:model];
                                     }
                                 } failure:^(ErrorCode status, NSString *msg, NSDictionary *data) {
                                     model.isRequesting = NO;
                                 }];
        }
            break;

        default:
            break;
    }

    model.isRequesting = YES;
    model.times = (0 < model.times--) ?:0;
}



#pragma mark - Getter Methods

- (NSTimer *)timer
{
    if (nil == _timer) {
        _timer = [NSTimer scheduledTimerWithTimeInterval:kTimeInterval target:self selector:@selector(requestNetwork) userInfo:nil repeats:YES];

        [[NSRunLoop currentRunLoop] addTimer:_timer forMode:NSRunLoopCommonModes];
    }

    return _timer;
}

- (NSMutableArray *)requestMArr
{
    if (nil == _requestMArr) {
        _requestMArr = [[NSMutableArray alloc] initWithCapacity:5];
    }

    return _requestMArr;
}

用到的HTTP巨集定義:

typedef NS_ENUM(NSInteger, RequestType) {
    kRequestTypeGet         = 0,
    kRequestTypePost        = 1,
    kRequestTypeUpload      = 2,
    kRequestTypePut         = 3,
    kRequestTypeDelete      = 4,
};

需要保證請求成功,那麼直接呼叫這個方法就可以,並且直接返回成功。

PS: 程式碼中用到了很多專案封裝的類,後續發出自己的封裝類,也可以看看我的Github

相關推薦

iOS 網路請求優化取消請求

頁面返回的時候,將網路請求取消 同一個請求多次請求時,短時間忽略相同的請求 同一個請求多次請求時,取消之前發出的請求 傳送的請求,多次嘗試並確保成功 最近發現很多網路請求都有可以優化的地方,雖然開發和測試都沒有發現問題,但是可以讓程式碼更加的優雅。想到

前端效能優化http請求的過程

前端效能優化之http請求的過程 在前端面試中,經常會被問到“一個頁面從輸入URL到頁面載入顯示完成,這個過程都發生了什麼”,這是前端的經典面試題之一。這個過程涉及的東西很多,區分度很高。 大致分為這幾個過程: 1.DNS解析 2.TCP連線 3.傳送HTTP請求 4.伺服器

tomcat優化Http請求壓縮

HTTP 壓縮可以大大提高瀏覽網站的速度,它的原理是,在客戶端請求網頁後,從伺服器端將網頁檔案壓縮,再下載到客戶端,由客戶端的瀏覽器負責解壓縮並瀏覽。相對於普通的瀏覽過程HTML ,CSS,Javascript , Text ,它可以節省40%左右的流量。更為重要的是,它可以

iOS網路開發基礎--傳送HTTP請求

一、一個HTTP請求的基本要素 1.請求URL:客戶端通過哪個路徑找到伺服器 2.請求引數:客戶端傳送給伺服器的資料 如登入時需要傳送的使用者名稱和密碼 3.返回結果:伺服器返回給客戶端

iOS性能優化Leaks動態分析

反向輸出 ges 合並 性能優化 recursion 問題 details auto 14. iOS性能優化之Leaks動態分析 Instruments-Leaks有很多跟蹤模塊可以動態分析和跟蹤內存, CPU 和文件系統(因為是動態分析 所以必須運行才能打開)。 具體

IOS網路圖片快取SDWebImage

載入網路圖片可以說是網路應用中必備的。如果單純的去下載圖片,而不去做多執行緒、快取等技術去優化,載入圖片時的效果與使用者體驗就會很差。 處理網路圖片快取步驟: 1、根據圖片URL查詢記憶體是否有這張圖片,有則返回圖片,沒有則進入下一步。 2、查詢本地磁碟儲存是否有這張圖片,有則返回圖片,

[SEO]wordpress優化取消gravatar重定向

以前一直使用的是cnzz 的統計,發現它的確只是個統計而已,比起google或者百度的分析差了很多,Google Analytics或者百度統計中都有網站效能,頁面優化,SEO優化等等都會有建議的,特別是網站速度診斷等工具,都是非常好的,Google Analytics也用過一段時間,裡面的很多東西都略顯專業

iOS開發記憶體優化自動檢測記憶體洩露,檢查是否有迴圈引用,檢查記憶體為何如此大,Block迴圈引用的檢查

手機裝置的記憶體是一個共享資源。應用程式可能會不當的耗盡記憶體、崩潰,或者遭遇大幅度的效能降低。 Facebook iOS客戶端有很多功能,並且它們共享同一塊記憶體空間。如果任何特定的功能消耗過多的記憶體,就會影響到整個應用程式。這是可能發生的,比如,這個功能導致了記

iOS App記憶體優化 解決UIImagePickerController的圖片物件佔用RAM過高問題

這個坑會在特定的情況下特別明顯: 類似朋友圈的新增多張本地選擇\拍照 的圖片 並在介面上做一個預覽功能 由於沒有特別的相機\相簿需求,則直接使用系統自帶的UIImagePickerController 最簡單的方法-> UIImagePickerController 選擇圖片 -> 代理返回圖

iOS學習筆記(八)——iOS網路通訊httpNSURLConnection

      移動網際網路時代,網路通訊已是手機終端必不可少的功能。我們的應用中也必不可少的使用了網路通訊,增強客戶端與伺服器互動。這一篇提供了使用NSURLConnection實現http通訊的方式。          NSURLConnection提供了非同步請求、同步請求

iOS網路請求太頻繁 處理之前傳送的http請求(取消)

搜尋功能在APP中非常的常見,搜尋功能伴隨的往往是實時搜尋結果,極大的方便了使用者的查詢與實時資料的更新,但是也有極大的問題,當我們搜尋框的文字改變的時候,就會進行網路請求,如果輸入特別快的時候,網路請求也會特頻繁,對伺服器的壓力也就更大。 解決方法:在進行新的網路請求的時

微信小程式wx.request:fail錯誤,真機預覽請求無效問題解決,安卓,ios網路預覽異常

問題描述:域名已經備案,我全部都有,也在後臺配置了,但是手機預覽,還是請求失敗, PC端是可以請求資料出來的 新版開發者工具增加了https檢查功能;可使用此功能直接檢查排查ssl協議版本問題:可能原因:0:後臺域名沒有配置0.1:域名不支援https1:沒有重啟工具;2:

知識鞏固——性能優化減少http請求

做成 coord 性能優化 base .... ase ... 轉碼 樣式表 1、css 雪碧圖 sprites 其實更高深的應該是把圖標做成字體文件直接引用 2、圖片地圖 類似上,area標簽的coords屬性 3、合並腳本和樣式表,js和css 4、使用base64碼減

網路請求測試HttpUrlConnection【Android】

使用HttpConnection 1.URL:包含請求地址的類 url(path):包含請求路徑的構造方法 openConnection():得到連線物件 2.HttpURLConnection:代表與伺服器連線的類 setMethod("GET/POST"):設定請

iOS網路請求框架:MKNetWorkKit的使用

2014-07-11 MKNetWorkKit是由一個印度小夥子寫的,是用於網路請求的庫,支援ARC,程式碼的網址這裡給出。 作者原始碼地址(MugunthKumar):MKNetworkKit 作者類庫介紹中文翻譯地址(翻譯作者,csdn博主kmyhy,楊巨集焱):csdn博

[聊聊架構] 日請求量過億,談陌陌的 Feed 服務優化

場景和架構介紹     先從產品層⾯面介紹一下Feed業務。Feed本⾝身就是一段簡短文字加一張圖片,帶有位置資訊,釋出之後可以被好友和附近的人看到,通過點贊評論的方式互動。類似微博和朋友圈。     陌陌上季度的MAU為6980萬,Feed作為主要的社交業務,從201

iOS 網路請求劫持

1、概述: NSURLProtocol是URL loading system 中的一個重要的組成部分,它允許我們對全域性的網路請求(基於使用URLRequest)做攔截,可攔截的請求型別有NSURLConnection、NSURLSession 和 UIWebView中的請

網路請求框架Retrofit2.0基本講解

Retrofit2.0簡介   Retrofit是一套RESTful架構的Android(Java)客戶端實現,基於註解,提供JSON to POJO(Plain Ordinary Java Object,簡單Java物件),POJO to JSON,網路請求

ios網路請求框架,基於AFNetworking封裝,其中快取模組依賴TMCache,JSON解析模組依賴MJExtension,使用更加簡單方便

LazyNetForIOS 由於本人不太會寫文章,有寫得不好得地方請見諒 專案介紹 專案地址 介紹: 非常感謝這三個作品得作者,個人也熱衷與開源,以後有覺得好的東西都會熱於與大家分享

通用網路請求實現HttpURLConnection和OkHttp

  網路請求是一個耗時操作,所以我們需要開啟一個子執行緒來發起網路請求,同時,由於耗時邏輯都是在子執行緒裡進行的,那麼伺服器響應的資料就無法返回,這時我們應該考慮使用Java的回撥機制。 public interface HttpCallbackListene