最近項目中碰到一個需求司光,有七個網(wǎng)絡請求,執(zhí)行順序如下圖
這時候基本有以下兩種解決方案:
1悉患,嵌套飘庄,在網(wǎng)絡請求成功block里面調用下一個請求
2,通過GCD中的group與semaphore組合购撼,需要寫大量__block 變量來接受網(wǎng)絡數(shù)據(jù)
上面兩種解決方法都不是很優(yōu)雅,代碼維護也不容易谴仙,就想著有什么方法可以不用嵌套迂求,不用加鎖,參數(shù)還可以非常方便的傳遞晃跺。
所以就封裝了這個網(wǎng)絡工具揩局,可以非常方便的解決網(wǎng)絡串行執(zhí)行、并行執(zhí)行掀虎,還支持串行與并行任意組合凌盯,
網(wǎng)絡工具包含RequestItem(單個網(wǎng)絡請求)、BatchRequest(并行網(wǎng)絡請求)烹玉、ChainRequest(串行網(wǎng)絡請求)三個類和一個簡單的NetTool(網(wǎng)絡請求工具驰怎,支持替換成自己封裝的網(wǎng)絡工具)
使用示例
//創(chuàng)建單個網(wǎng)絡請求
- (SQCombineRequestItem *)createItemWithKey:(NSString *)key {
//創(chuàng)建網(wǎng)絡請求
SQCombineRequestItem *item = [[SQCombineRequestItem alloc] init];
//將要開始
item.requestWillStart = ^(SQCombineRequestItem *requestItem) {
NSLog(@"will start %@", key);
};
//獲取網(wǎng)絡請求參數(shù)
item.requestParam = ^NSDictionary *(NSDictionary *data){
//data為前面的網(wǎng)絡請求成功之后傳遞過來的數(shù)據(jù)
NSLog(@"getParam %@ %@",key, data);
return @{@"q": @"北京"};
};
//網(wǎng)絡的url
item.url = @"https://dict.youdao.com/jsonapi";
//網(wǎng)絡請求方式
item.method = SQCRNetMethodGet;
//成功回調
item.successBlock = ^(id data, SQCombineRequestResult *result) {
//傳遞給下一個網(wǎng)絡請求的數(shù)據(jù)
result.dataToNextRequest = @{key: key};
//如果校驗數(shù)據(jù)不符合要求,要停止網(wǎng)絡請求,執(zhí)行下面即可
//result.stop = YES;
NSLog(@"success %@", key);
};
//失敗回調
item.failBlock = ^(id error) {
NSLog(@"fail %@", key);
};
return item;
}
1二打、單個網(wǎng)絡請求
//創(chuàng)建網(wǎng)絡請求
SQCombineRequestItem *item = [self createItemWithKey:@"single"];
//開始請求
[item start];
結果
2021-08-31 19:33:18.736320+0800 SQCombineRequestDemo[20020:93993] will start single
2021-08-31 19:33:18.736533+0800 SQCombineRequestDemo[20020:93993] getParam single (null)
2021-08-31 19:33:19.122764+0800 SQCombineRequestDemo[20020:93993] success single
2021-08-31 19:33:19.123052+0800 SQCombineRequestDemo[20020:93993] dealloc SQCombineRequestItem
2县忌、串行網(wǎng)絡請求
//創(chuàng)建串行網(wǎng)絡
self.chainRequest = [[SQCombineChainRequest alloc] init];
//串行網(wǎng)絡所有請求執(zhí)行成功
self.chainRequest.successBlock = ^(id data, SQCombineRequestResult *result) {
NSLog(@"chainRequest success");
};
//任何網(wǎng)絡請求執(zhí)行失敗,或者任何一個網(wǎng)絡成功回調里面stop傳YES,都會走到這里
self.chainRequest.failBlock = ^(id error) {
NSLog(@"chainRequest fail");
};
for (int i = 0; i < 3; i++) {
//創(chuàng)建網(wǎng)絡請求
SQCombineRequestItem *item = [self createItemWithKey:[NSString stringWithFormat:@"%d", i]];
[self.chainRequest addRequest:item];
}
[self.chainRequest start];
結果
2021-08-31 19:34:44.030914+0800 SQCombineRequestDemo[20020:93993] will start 0
2021-08-31 19:34:44.031103+0800 SQCombineRequestDemo[20020:93993] getParam 0 (null)
2021-08-31 19:34:44.310259+0800 SQCombineRequestDemo[20020:93993] success 0
2021-08-31 19:34:44.310585+0800 SQCombineRequestDemo[20020:93993] will start 1
2021-08-31 19:34:44.310916+0800 SQCombineRequestDemo[20020:93993] getParam 1 {
0 = 0;
}
2021-08-31 19:34:44.617736+0800 SQCombineRequestDemo[20020:93993] success 1
2021-08-31 19:34:44.618036+0800 SQCombineRequestDemo[20020:93993] will start 2
2021-08-31 19:34:44.618327+0800 SQCombineRequestDemo[20020:93993] getParam 2 {
0 = 0;
1 = 1;
}
2021-08-31 19:34:44.874603+0800 SQCombineRequestDemo[20020:93993] success 2
2021-08-31 19:34:44.874899+0800 SQCombineRequestDemo[20020:93993] chainRequest success
3、并行網(wǎng)絡請求
//創(chuàng)建并行網(wǎng)絡
self.batchRequest = [[SQCombineBatchRequest alloc] init];
//串行網(wǎng)絡所有請求執(zhí)行成功
self.batchRequest.successBlock = ^(id data, SQCombineRequestResult *result) {
NSLog(@"batchRequest success");
};
//任何網(wǎng)絡請求執(zhí)行失敗,或者任何一個網(wǎng)絡成功回調里面stop傳YES,都會走到這里
self.batchRequest.failBlock = ^(id error) {
NSLog(@"batchRequest fail");
};
NSMutableArray *items = [NSMutableArray arrayWithCapacity:3];
for (int i = 0; i < 3; i++) {
//創(chuàng)建網(wǎng)絡請求
SQCombineRequestItem *item = [self createItemWithKey:[NSString stringWithFormat:@"%d",i]];
item.successBlock = ^(id data, SQCombineRequestResult *result) {
NSLog(@"success %d",i);
};
[items addObject:item];
}
[self.batchRequest addRequests:items];
[self.batchRequest start];
結果
2021-08-31 19:36:08.543819+0800 SQCombineRequestDemo[20020:93993] will start 0
2021-08-31 19:36:08.544094+0800 SQCombineRequestDemo[20020:93993] getParam 0 (null)
2021-08-31 19:36:08.545526+0800 SQCombineRequestDemo[20020:93993] will start 1
2021-08-31 19:36:08.545700+0800 SQCombineRequestDemo[20020:93993] getParam 1 (null)
2021-08-31 19:36:08.547276+0800 SQCombineRequestDemo[20020:93993] will start 2
2021-08-31 19:36:08.547774+0800 SQCombineRequestDemo[20020:93993] getParam 2 (null)
2021-08-31 19:36:09.025486+0800 SQCombineRequestDemo[20020:93993] success 2
2021-08-31 19:36:09.027692+0800 SQCombineRequestDemo[20020:93993] success 0
2021-08-31 19:36:09.061978+0800 SQCombineRequestDemo[20020:93993] success 1
2021-08-31 19:36:09.062164+0800 SQCombineRequestDemo[20020:93993] batchRequest success
4、組合使用
圖中b c d作為item添加到上面灰色串行網(wǎng)絡中症杏,e f g作為item添加到下面灰色串行網(wǎng)絡中装获, 兩個灰色又作為item加入到黃色的并行網(wǎng)絡中。綠色跟黃色又作為item加入到藍色串行網(wǎng)絡中厉颤。
//組合使用代碼
//創(chuàng)建請求a
SQCombineRequestItem *a = [self createItemWithKey:@"a"];
//創(chuàng)建bcd串行請求
SQCombineChainRequest *bcd = [[SQCombineChainRequest alloc] init];
for (NSString *key in @[@"b", @"c", @"d"]) {
//分別添加b c d網(wǎng)絡添加到bcd串行網(wǎng)絡中
[bcd addRequest:[self createItemWithKey:key]];
}
//b c d成功
bcd.successBlock = ^(id data, SQCombineRequestResult *result) {
NSLog(@"bcd success");
};
//創(chuàng)建efg串行網(wǎng)絡
SQCombineChainRequest *efg = [[SQCombineChainRequest alloc] init];
for (NSString *key in @[@"e", @"f", @"g"]) {
//分別將e f g網(wǎng)絡添加到efg串行網(wǎng)絡中
[efg addRequest:[self createItemWithKey:key]];
}
//e f g 成功
efg.successBlock = ^(id data, SQCombineRequestResult *result) {
NSLog(@"efg success");
};
//創(chuàng)建bcd穴豫、efg并行的網(wǎng)絡請求
SQCombineBatchRequest *batch = [[SQCombineBatchRequest alloc] init];
//并行網(wǎng)絡請求添加bcd efg
[batch addRequests:@[bcd, efg]];
//創(chuàng)建最終的串行網(wǎng)路請求
self.chainRequest = [[SQCombineChainRequest alloc] init];
//串行網(wǎng)絡請求添加請求a
[self.chainRequest addRequest:a];
// 串行網(wǎng)絡添加并行組合
[self.chainRequest addRequest:batch];
//所有網(wǎng)絡執(zhí)行成功后的回調
self.chainRequest.successBlock = ^(id data, SQCombineRequestResult *result) {
NSLog(@"self.chainRequest success");
};
//開啟網(wǎng)絡調用
[self.chainRequest start];
結果
2021-08-31 16:58:56.384953+0800 SQCombineRequestDemo[59480:691163] will start a
2021-08-31 16:58:56.385118+0800 SQCombineRequestDemo[59480:691163] getParam a (null)
2021-08-31 16:58:57.027075+0800 SQCombineRequestDemo[59480:691163] success a
2021-08-31 16:58:57.027291+0800 SQCombineRequestDemo[59480:691163] will start b
2021-08-31 16:58:57.027492+0800 SQCombineRequestDemo[59480:691163] getParam b {
a = a;
}
2021-08-31 16:58:57.028726+0800 SQCombineRequestDemo[59480:691163] will start e
2021-08-31 16:58:57.028925+0800 SQCombineRequestDemo[59480:691163] getParam e {
a = a;
}
2021-08-31 16:58:57.245229+0800 SQCombineRequestDemo[59480:691163] success b
2021-08-31 16:58:57.245410+0800 SQCombineRequestDemo[59480:691163] will start c
2021-08-31 16:58:57.245549+0800 SQCombineRequestDemo[59480:691163] getParam c {
a = a;
b = b;
}
2021-08-31 16:58:57.257827+0800 SQCombineRequestDemo[59480:691163] success e
2021-08-31 16:58:57.258210+0800 SQCombineRequestDemo[59480:691163] will start f
2021-08-31 16:58:57.258544+0800 SQCombineRequestDemo[59480:691163] getParam f {
a = a;
e = e;
}
2021-08-31 16:58:57.442234+0800 SQCombineRequestDemo[59480:691163] success c
2021-08-31 16:58:57.442402+0800 SQCombineRequestDemo[59480:691163] will start d
2021-08-31 16:58:57.442552+0800 SQCombineRequestDemo[59480:691163] getParam d {
a = a;
b = b;
c = c;
}
2021-08-31 16:58:57.476281+0800 SQCombineRequestDemo[59480:691163] success f
2021-08-31 16:58:57.476442+0800 SQCombineRequestDemo[59480:691163] will start g
2021-08-31 16:58:57.476596+0800 SQCombineRequestDemo[59480:691163] getParam g {
a = a;
e = e;
f = f;
}
2021-08-31 16:58:57.634532+0800 SQCombineRequestDemo[59480:691163] success d
2021-08-31 16:58:57.634791+0800 SQCombineRequestDemo[59480:691163] bcd success
2021-08-31 16:58:57.669988+0800 SQCombineRequestDemo[59480:691163] success g
2021-08-31 16:58:57.670142+0800 SQCombineRequestDemo[59480:691163] efg success
2021-08-31 16:58:57.670261+0800 SQCombineRequestDemo[59480:691163] self.chainRequest success
pod導入方式
//自帶網(wǎng)絡請求工具、使用的是AFNetworking 4.0版本逼友,如果沖突可以使用下面方式導入
pod 'SQCombineRequest'
//不帶網(wǎng)絡工具精肃,不依賴AFNetworking,要自己設置SQCombineRequestItem的netRequestTool屬性
pod 'SQCombineRequest/SQCombineRequestCombine'