iOS之AFN常用封装(三)
2017-04-19 20:37
267 查看
/**
* $description: 实际网络请求执行者
*/
#import <Foundation/Foundation.h>
#import "AFNetworking.h"
typedef void(^ProgressBlock) (NSProgress* progress);
typedef void(^SuccessBlock) (NSURLSessionDataTask *task,
id responseObject);
typedef void(^FailureBlock) (NSURLSessionDataTask *task, NSError *error);
typedef enum : NSInteger {
RequestBaseUrlDefault
} RequestBaseUrl;
typedef enum : NSInteger {
RequestMethodGet,
RequestMethodPost
} RequestMethod;
typedef enum : NSInteger {
RequestProtocolHttp,
RequestProtocolHttps
} RequestProtocol;
/**
* 通用
*/
@interface CommonDataService : NSObject
@property(assign,
nonatomic) RequestBaseUrl requestBaseUrl;
@property(assign,
nonatomic) RequestMethod requestMethod;
@property(assign,
nonatomic) RequestProtocol requestProtocol;
@property(assign,
nonatomic) BOOL isJsonResponse;//响应是否JSON格式
@property(assign,
nonatomic) BOOL isJsonRequest;//请求参数是否JSON格式
/**
* 根据方法名和参数请求网络(字典参数)
*
* @param url 完整URL
* @param params 字典参数
* @param successBlock 成功回调
* @param failureBlock 失败回调
*
* @return <#return value description#>
*/
-(NSURLSessionDataTask *)requestWithUrl:(NSString *)url
params:(NSDictionary *)params
successBlock:(SuccessBlock)successBlock
failureBlock:(FailureBlock)failureBlock;
/**
* 请求服务器基本URL
* 一个完整的URL必须包含以下三个参数
* @param m 模块
目前只有Api ,
此处固定值
* @param c 控制器
* @param a 方法
*
* @return params 返回最基本的请求参数
*/
-(NSString *)GetUrlWhitController:(NSString *)c action:(NSString *)a ;
-(NSString *)GetUrlWhitModule:(NSString *)m controller:(NSString *)c action:(NSString *)a;
/**
* 上传图片(头像上传)
*
* @param url
* @param image
* @param completion
* @param errorBlock
* @return
*/
- (NSURLSessionDataTask *)requestUploadImageWithUrl:(NSString *)url
params:(NSDictionary *)params
images:(NSArray *)images
successBlock:(SuccessBlock)successBlock
failureBlock:(FailureBlock)failureBlock;
@end
========================
/**
* $description: CommonDataService.h
*/
#import "CommonDataService.h"
@interface CommonDataService(){
}
@property(nonatomic ,
strong)NSArray* filterFunctions;
@end
@implementation CommonDataService
-(instancetype)init{
if(self = [super init]) {
self.isJsonRequest =
NO;//请求参数是否JSON格式
self.isJsonResponse =
YES;//响应是否JSON格式
}
self.filterFunctions =
@[ @"getGoodsCollect" ,
@"cartList" , @"userInfo"];
return
self;
}
/**
* 如果返回true
发送token过期通知
*/
-(BOOL)skipTokenNotification:(NSString*) url{
for (NSString* function
in _filterFunctions) {//如果url中友方法参数返回true
if ([url rangeOfString:function].location != NSNotFound) {
return
true;
}
}
return
false;
}
/**
* 请求服务器URL
* 基本参数
* 一个完整的URL必须包含以下三个参数
* @param m 模块
目前只有Api ,
此处固定值
* @param c 控制器
* @param a 方法
http://shop.lambo.com/index.php?m=Api&c=Index&a=getConfig
*/
-(NSString *)GetUrlWhitController:(NSString *)c action:(NSString *)a {
//为YES的时候程序继续执行,
否则抛出异常
NSAssert(c || a, @"请求参数异常,
将无法访问服务器!");
NSString* baseURL = [NSString stringWithFormat:BASEURL , HTTP_HOST];//BASEURL_DEFAULT(服务器URL)和DEFAULT_HTTP_HOST在SPConstants.h中宏定义
return [NSString stringWithFormat:@"%@?m=Api&c=%@&a=%@" , baseURL , c ,a];
}
/**
* 请求服务器URL
* 基本参数
* 一个完整的URL必须包含以下三个参数
* @param m 模块
目前只有Api ,
此处固定值
* @param c 控制器
* @param a 方法
*/
-(NSString *)GetUrlWhitModule:(NSString *)m controller:(NSString *)c action:(NSString *)a {
//为YES的时候程序继续执行,
否则抛出异常
NSAssert(c || a, @"请求参数异常,
将无法访问服务器!");
NSString* baseURL = [NSString stringWithFormat:BASEURL_DEFAULT , DEFAULT_HTTP_HOST];
return [NSString stringWithFormat:@"%@?m=%@&c=%@&a=%@" , baseURL , m, c ,a];
}
/**
* 根据方法名和参数请求网络(字典参数)
*
* @param url 完整URL
* @param params 字典参数
* @param successBlock 成功回调
* @param failureBlock 失败回调
*
* @return return value description
*/
-(NSURLSessionDataTask *)requestWithUrl:(NSString *)url
params:(NSDictionary *)params
successBlock:(SuccessBlock)successBlock
failureBlock:(FailureBlock)failureBlock {
//构建公共请求参数
if (!params) {
params = [NSMutableDictionary dictionary];
}else{
params = [NSMutableDictionary dictionaryWithDictionary:params];
}
if([SPMobileApplication sharedInstance].isLogined)
{
SPUser *loginUser = [SPMobileApplication sharedInstance].loginUser;
[params setValue:loginUser.userID forKey:@"user_id"];
if (loginUser.token) {
[params setValue:loginUser.token forKey:@"token"];
}
}
if ([[SPMobileApplication sharedInstance] getPhoneDeviceID]) {
[params setValue:[[SPMobileApplication sharedInstance] getPhoneDeviceID] forKey:@"unique_id"];
NSLog(@"-没签名前--%@",params);
}
/* params=@{
@"sign":@"d8ded4324c37a4b43ab4b197a78fcded",
@"time":@"1492495675",
@"unique_id":@"891F1CCA-E4A7-4F35-BA03-688CD5314686";
}
*/
params = [self configSign:params url:url];//签名后的参数
NSLog(@"-签名后params--%@",params);
AFHTTPSessionManager *manager = [AFHTTPSessionManager manager];
manager.securityPolicy = [AFSecurityPolicy policyWithPinningMode:AFSSLPinningModeNone];//安全策略
manager.securityPolicy.allowInvalidCertificates = YES;
manager.responseSerializer.acceptableContentTypes=[NSSet setWithObjects:@"application/json",
@"text/json", @"text/javascript",@"text/html",@"text/xml",
@"text/plain; charset=utf-8",
nil];
if(self.isJsonResponse) {
manager.responseSerializer = [AFJSONResponseSerializer serializer];
} else {
manager.responseSerializer = [AFHTTPResponseSerializer serializer];
}
// manager.responseSerializer = [AFHTTPResponseSerializer serializer];
//SPSaveData保存用户信息类
[SPSaveData saveDataWithData:url key:@"domain"];
if(self.requestMethod == RequestMethodGet)
{
[manager GET:url parameters:params progress:nil success:^(NSURLSessionDataTask *
_Nonnull task, id
_Nullable responseObject) {
if (successBlock) {
if ([responseObject objectForKey:@"status"]) {
NSInteger status = [[responseObject objectForKey:@"status"] integerValue];
if ((status == RESPONSE_CODE_TOKENN_LOST || status == RESPONSE_CODE_TOKENN_INALIDE || status == RESPONSE_CODE_TOKENN_EXPIRE) && ![self
skipTokenNotification:url]) {
//发送通知//token过期,失效通知
[[NSNotificationCenter defaultCenter] postNotificationName:NotificationTokenExpire object:nil];
//token过期的接口统一设置超时提示
NSMutableDictionary* dict = [NSMutableDictionary dictionaryWithDictionary:responseObject];
[dict setValue:@"登录超时,请重新登录"
forKey:@"msg"];
responseObject = dict;
}
}
successBlock(task , responseObject);
}
} failure:^(NSURLSessionDataTask * _Nullable task, NSError *
_Nonnull error) {
NSLog(@"【错误信息】:\n%@",[error description]);
[self sendErrorLog:[error description] url:url parameter:nil];
if(failureBlock){
failureBlock(task,error);
}
}];
}
else
if(self.requestMethod == RequestMethodPost)
{
//NSInteger status = [[responseObject objectForKey:@"status"] integerValue];
[manager POST:url parameters:params progress:^(NSProgress *
_Nonnull uploadProgress) {
} success:^(NSURLSessionDataTask * _Nonnull task,
id _Nullable responseObject) {
if (successBlock) {
//*********************//如果不是标准的json数据,就需要用到下面的方法;
// NSString *str=[[NSString alloc]initWithData:responseObject encoding:NSUTF8StringEncoding];//网页二进制数据转换成字符串
// NSLog(@"---responseStr---%@",str);
// NSData *data=[[NSData alloc]initWithData:[str dataUsingEncoding:NSUTF8StringEncoding]];
// NSDictionary *responseObject=[NSJSONSerialization JSONObjectWithData:data options:NSJSONReadingMutableContainers error:nil];
//*******************************
if ([responseObject objectForKey:@"status"]) {
NSInteger status = [[responseObject objectForKey:@"status"] integerValue];
if ((status == RESPONSE_CODE_TOKENN_LOST || status == RESPONSE_CODE_TOKENN_INALIDE || status == RESPONSE_CODE_TOKENN_EXPIRE) && ![self
skipTokenNotification:url]) {
//发送通知//token过期,失效通知
[[NSNotificationCenter defaultCenter] postNotificationName:NotificationTokenExpire object:nil];
//token过期的接口统一设置超时提示
NSMutableDictionary* dict = [NSMutableDictionary dictionaryWithDictionary:responseObject];
[dict setValue:@"登录超时,请重新登录"
forKey:@"msg"];
responseObject = dict;
}
}
successBlock(task , responseObject);
}
} failure:^(NSURLSessionDataTask * _Nullable task, NSError *
_Nonnull error) {
NSLog(@"【错误信息】:\n%@",[error description]);
[self sendErrorLog:[error description] url:url parameter:nil];
//发送错误日志报告到服务器
if(failureBlock){
//发送通知
failureBlock(task,error);
}
}];
}
return
nil;
}
/**
* 上传图片(头像上传)
*
* @param url url description
* @param image image description
* @param completion completion description
* @param errorBlock errorBlock description
* @return <#return value description#>
*/
- (NSURLSessionDataTask *)requestUploadImageWithUrl:(NSString *)url
params:(NSDictionary *)params
images:(NSArray *)images
successBlock:(SuccessBlock)successBlock
failureBlock:(FailureBlock)failureBlock {
//构建公共请求参数
if (!params) {
params = [NSMutableDictionary dictionary];
}else{
params = [NSMutableDictionary dictionaryWithDictionary:params];
}
if([SPMobileApplication sharedInstance].isLogined)
{
SPUser *loginUser = [SPMobileApplication sharedInstance].loginUser;
[params setValue:loginUser.userID forKey:@"user_id"];
if (loginUser.token) {
[params setValue:loginUser.token forKey:@"token"];
}
}
params = [self configSign:params url:url];
AFURLSessionManager *manager = [[AFURLSessionManager alloc] initWithSessionConfiguration:[NSURLSessionConfiguration defaultSessionConfiguration]];
manager.securityPolicy.allowInvalidCertificates = YES;
//manager.responseSerializer.acceptableContentTypes = [NSSet setWithObject:@"text/html"];//设置相应内容类型
NSMutableURLRequest *request = [[AFHTTPRequestSerializer serializer]
multipartFormRequestWithMethod:@"POST"
URLString:url
parameters:params
constructingBodyWithBlock:^(id<AFMultipartFormData> formData) {
if (images && images.count >
0) {
for (NSInteger i =0; i<images.count ; i++) {
UIImage* image = images[i];
NSData* imageData = UIImagePNGRepresentation(image);
NSString* sname = [NSString stringWithFormat:@"img_file[%ld]" , i];
NSDateFormatter *formatter = [[NSDateFormatter alloc] init];
formatter.dateFormat =
@"yyyyMMddHHmmss";
NSString *str = [formatter stringFromDate:[NSDate date]];
NSString *fileName = [NSString stringWithFormat:@"%@_%ld.png", str , i];
//
上传图片,以文件流的格式
[formData appendPartWithFileData:imageData name:sname fileName:fileName mimeType:@"image/png"];
}
}
} error:nil];
NSURLSessionUploadTask *uploadTask;
uploadTask = [manager
uploadTaskWithStreamedRequest:request
progress:^(NSProgress * _Nonnull uploadProgress) {
}
completionHandler:^(NSURLResponse * _Nonnull response,
id _Nullable responseObject, NSError *
_Nullable error) {
if (error) {
NSLog(@"Error: %@", error);
if(failureBlock){
failureBlock(uploadTask,0);
}
} else {
NSLog(@"%@ %@", response, responseObject);
if(successBlock){
successBlock(uploadTask, responseObject);
}
}
}];
[uploadTask resume];
return
nil;
}
/**
*参数签名的方法
*/
-(NSDictionary*)configSign:(NSDictionary*)params url:(NSString*)url{
if (!params) {
return params;
}
NSMutableDictionary* signParams = [NSMutableDictionary dictionaryWithDictionary:params];
long locaTime = [SPCommonUtils getCurrentTime];//本地时间
long cutTime = [SPMobileApplication sharedInstance].cutServiceTime ;//本地与服务器时间差
NSString* time = [NSString stringWithFormat:@"%ld" , (locaTime + cutTime)];
NSString* signFmt = [SPCommonUtils signParameter:signParams time:time signKey:SP_SIGN_PRIVATGE_KEY url:url];//服务器验证签名方法
[signParams setValue:signFmt forKey:@"sign"];
[signParams setValue:time forKey:@"time"];
return signParams;
}
/**
* 发送错误日志报告到服务器
*
* @param params
*/
-(void)sendErrorLog:(NSString*)error url:(NSString*)errorUrl parameter:(NSDictionary*)parameter{
NSString* url = [self GetUrlWhitController:@"User" action:@"errorLog"];
NSMutableDictionary* params = nil;
//构建公共请求参数
if (!params) {
params = [NSMutableDictionary dictionary];
}else{
params = [NSMutableDictionary dictionaryWithDictionary:parameter];
}
[params setObject:errorUrl forKey:@"errorUrl"];
[params setObject:error forKey:@"error"];
NSLog(@"pushMobileInfo -> params : %@" , params);
NSMutableArray *queryItems = [NSMutableArray array];
for(NSString* key
in params ){
NSString* param = [NSString stringWithFormat:@"%@=%@" , key , params[key]];
[queryItems addObject:param];
}
NSString* dataString = [queryItems componentsJoinedByString:@"&"];
NSData *bodyData = [[dataString stringByAddingPercentEscapesUsingEncoding:NSUTF8StringEncoding]dataUsingEncoding:NSUTF8StringEncoding];//
//NSLog(@"pushMobileInfo -> requestUrl : %@ , dataString : %@" , baseUrl , dataString);
NSMutableURLRequest * request = [[NSMutableURLRequest alloc]init];
[request setHTTPMethod:@"post"];
//指定请求方式
[request setURL:[NSURL URLWithString:url]]; //设置请求的地址
[request setHTTPBody:bodyData]; //设置请求的参数
NSURLSession *session = [NSURLSession sharedSession];
__block NSString *result =
@"";
NSURLSessionDataTask *dataTask = [session dataTaskWithRequest:request completionHandler:^(NSData *
_Nullable data, NSURLResponse *
_Nullable response, NSError *
_Nullable error) {
if (!error) {
//没有错误,返回正确;
NSLog(@"sendErrorLog success
:%@",result);
}else{
//出现错误;
NSLog(@"sendErrorLog failed
:%@",error);
}
}];
[dataTask resume];
}
@end
=====================
/**
* $description: 首页以及系统配置相关网络请求
*/
#import "SPBaseRequestManager.h"
@interface SPHomeRequestManager : SPBaseRequestManager
/**
* 查询系统配置信息
* 使用万能SQL: index.php?m=Api&c=Base&a=sqlApi
* @param success success description
* @param failure failure description
*/
+(void)getServiceConfig:(SuccessHandleBlock)success failure:(FailureHandleBlock)failure;
/**
* 查询插件配置信息
* 使用万能SQL: index.php?m=Api&c=Index&a=getPluginConfig
* @param success success description
* @param failure failure description
*/
+(void)getServicePlugin:(SuccessHandleBlock)success failure:(FailureHandleBlock)failure;
#pragma mark - 获取首页数据
/**
* 获取首页数据
* @URL index.php?m=Api&c=Index&a=homePage
* @param success success description
* @param failure failure description
*/
+(void)getHomePageData:(SuccessHandleBlock)success failure:(FailureHandleBlock)failure;
/**
* 获取首页收藏数据----猜你喜欢
* @URL index.php?m=Api&c=Index&a=favourite
* @param success success description
* @param failure failure description
*/
+(void)getFavouriteWithPage:(NSInteger)pageIndex success:(SuccessHandleBlock)success failure:(FailureHandleBlock)failure;
#pragma mark 刷新服务器时间戳
/**
* 获取服务器时间戳
* @URL index.php?m=Api&c=Base&a=getServerTime
* @param success success description
* @param failure failure description
*/
+(void)refreshServiceTime:(SuccessHandleBlock)success failure:(FailureHandleBlock)failure;
@end
================
/**
* $description: 首页以及系统配置相关网络请求
*/
#import "SPHomeRequestManager.h"
@implementation SPHomeRequestManager
/**
* 查询系统配置信息
* 使用万能SQL: index.php?m=Api&c=Index&a=getConfig
* @param success success description
* @param failure failure description
*/
+(void)getServiceConfig:(SuccessHandleBlock)success failure:(FailureHandleBlock)failure{
CommonDataService *request = [super PostRequestService];//调用父类的方法
NSString* url = [request GetUrlWhitController:@"Index" action:@"getConfig"];//请求服务器的URL
//创建请求
[request requestWithUrl:url params:nil successBlock:^(NSURLSessionDataTask *operation,
id responseObject) {
NSInteger status = [[responseObject objectForKey:@"status"] integerValue];
NSString *msg = [responseObject objectForKey:@"msg"];
if(status >
0)
{
//传递对象
if(success)
{
success(msg, configs);
}
/* End 数据结果解析区 */
}
else
{
if(failure)
{
failure(msg,-1);
}
}
} failureBlock:^(NSURLSessionDataTask *operation, NSError *error) {
NSLog(@" failureBlock :%@", [error description]);
if(failure)
{
failure(kNetworkError,-1);
}
}];
}
/**
* 查询插件配置信息
* 使用万能SQL: index.php?m=Api&c=Index&a=getPluginConfig
* @param success success description
* @param failure failure description
*/
+(void)getServicePlugin:(SuccessHandleBlock)success failure:(FailureHandleBlock)failure{
CommonDataService *request = [super PostRequestService];
NSString* url = [request GetUrlWhitController:@"Index" action:@"getPluginConfig"];
[request requestWithUrl:url params:nil successBlock:^(NSURLSessionDataTask *operation,
id responseObject) {
NSInteger status = [[responseObject objectForKey:@"status"] integerValue];
NSString *msg = [responseObject objectForKey:@"msg"];
if(status >
0)
{
}
//传递对象
if(success)
{
success(msg, dataDict);
}
/* End 数据结果解析区 */
}
else
{
if(failure)
{
failure(msg,-1);
}
}
} failureBlock:^(NSURLSessionDataTask *operation, NSError *error) {
NSLog(@" failureBlock :%@", [error description]);
if(failure)
{
failure(kNetworkError,-1);
}
}];
}
/**
* 获取首页数据-
滚动图片数据源-促销(暂时没看到)-精品推荐-新品上市-热销商品
* @URL index.php?m=Api&c=Index&a=homePage
* @param success success description
* @param failure failure description
*/
+(void)getHomePageData:(SuccessHandleBlock)success failure:(FailureHandleBlock)failure{
CommonDataService *request = [super PostRequestService];
NSString* url = [request GetUrlWhitController:@"Index" action:@"homePage"];
[request requestWithUrl:url params:nil successBlock:^(NSURLSessionDataTask *operation,
id responseObject) {
NSInteger status = [[responseObject objectForKey:@"status"] integerValue];
NSString *msg = [responseObject objectForKey:@"msg"];
if(status >
0)
{
//传递对象
if(success)
{
success(msg, 传递的数据);
}
/* End 数据结果解析区 */
}
else
{
if(failure)
{
failure(msg,-1);
}
}
} failureBlock:^(NSURLSessionDataTask *operation, NSError *error) {
NSLog(@" failureBlock :%@", [error description]);
if(failure)
{
failure(kNetworkError,-1);
}
}];
}
/**
* 获取首页收藏数据----猜你喜欢的数据
* @URL index.php?m=Api&c=Index&a=favourite
* @param success success description
* @param failure failure description
*/
+(void)getFavouriteWithPage:(NSInteger)pageIndex success:(SuccessHandleBlock)success failure:(FailureHandleBlock)failure{
CommonDataService *request = [super PostRequestService];
NSString* url = [request GetUrlWhitController:@"Index" action:@"favourite"];
NSDictionary* params = @{
@"p":[NSNumber numberWithInteger:pageIndex],
@"page_size":[NSNumber numberWithInteger:SizeOfPage]
};//表示每页显示几条数据(10条)
//在CommonDataService中根据方法名和参数请求网络(字典参数)
[request requestWithUrl:url params:params successBlock:^(NSURLSessionDataTask *operation,
id responseObject) {
NSInteger status = [[responseObject objectForKey:@"status"] integerValue];
NSString *msg = [responseObject objectForKey:@"msg"];
if(status >
0)
{
/* Begin 数据结果解析区 */
//解析对象
NSDictionary *resultData = [responseObject objectForKey:@"result"];
//传递对象
if(success)
{
success(msg, favourits);
}
/* End 数据结果解析区 */
}
else
{
if(failure)
{
failure(msg,-1);
}
}
} failureBlock:^(NSURLSessionDataTask *operation, NSError *error) {
NSLog(@" failureBlock :%@", [error description]);
if(failure)
{
failure(kNetworkError,-1);
}
}];
}
#pragma mark 刷新服务器时间戳
/**
* 获取服务器时间戳
* @URL index.php?m=Api&c=Base&a=getServerTime
* @param success success description
* @param failure failure description
*/
+(void)refreshServiceTime:(SuccessHandleBlock)success failure:(FailureHandleBlock)failure{
CommonDataService *request = [super PostRequestService];
NSString* url = [request GetUrlWhitController:@"Base" action:@"getServerTime"];
[request requestWithUrl:url params:nil successBlock:^(NSURLSessionDataTask *operation,
id responseObject) {
NSInteger status = [[responseObject objectForKey:@"status"] integerValue];
NSString *msg = [responseObject objectForKey:@"msg"];
if(status >
0)
{
long serviceTime = [[responseObject objectForKey:@"result"] longValue];
long localTime = [SPCommonUtils getCurrentTime];
long cutTime = serviceTime - localTime;
//传递对象
if(success)
{
success(msg, 传递时间差);
}
/* End 数据结果解析区 */
}
else
{
if(failure)
{
failure(msg,-1);
}
}
} failureBlock:^(NSURLSessionDataTask *operation, NSError *error) {
NSLog(@" failureBlock :%@", [error description]);
if(failure)
{
failure(kNetworkError,-1);
}
}];
}
@end
* $description: 实际网络请求执行者
*/
#import <Foundation/Foundation.h>
#import "AFNetworking.h"
typedef void(^ProgressBlock) (NSProgress* progress);
typedef void(^SuccessBlock) (NSURLSessionDataTask *task,
id responseObject);
typedef void(^FailureBlock) (NSURLSessionDataTask *task, NSError *error);
typedef enum : NSInteger {
RequestBaseUrlDefault
} RequestBaseUrl;
typedef enum : NSInteger {
RequestMethodGet,
RequestMethodPost
} RequestMethod;
typedef enum : NSInteger {
RequestProtocolHttp,
RequestProtocolHttps
} RequestProtocol;
/**
* 通用
*/
@interface CommonDataService : NSObject
@property(assign,
nonatomic) RequestBaseUrl requestBaseUrl;
@property(assign,
nonatomic) RequestMethod requestMethod;
@property(assign,
nonatomic) RequestProtocol requestProtocol;
@property(assign,
nonatomic) BOOL isJsonResponse;//响应是否JSON格式
@property(assign,
nonatomic) BOOL isJsonRequest;//请求参数是否JSON格式
/**
* 根据方法名和参数请求网络(字典参数)
*
* @param url 完整URL
* @param params 字典参数
* @param successBlock 成功回调
* @param failureBlock 失败回调
*
* @return <#return value description#>
*/
-(NSURLSessionDataTask *)requestWithUrl:(NSString *)url
params:(NSDictionary *)params
successBlock:(SuccessBlock)successBlock
failureBlock:(FailureBlock)failureBlock;
/**
* 请求服务器基本URL
* 一个完整的URL必须包含以下三个参数
* @param m 模块
目前只有Api ,
此处固定值
* @param c 控制器
* @param a 方法
*
* @return params 返回最基本的请求参数
*/
-(NSString *)GetUrlWhitController:(NSString *)c action:(NSString *)a ;
-(NSString *)GetUrlWhitModule:(NSString *)m controller:(NSString *)c action:(NSString *)a;
/**
* 上传图片(头像上传)
*
* @param url
* @param image
* @param completion
* @param errorBlock
* @return
*/
- (NSURLSessionDataTask *)requestUploadImageWithUrl:(NSString *)url
params:(NSDictionary *)params
images:(NSArray *)images
successBlock:(SuccessBlock)successBlock
failureBlock:(FailureBlock)failureBlock;
@end
========================
/**
* $description: CommonDataService.h
*/
#import "CommonDataService.h"
@interface CommonDataService(){
}
@property(nonatomic ,
strong)NSArray* filterFunctions;
@end
@implementation CommonDataService
-(instancetype)init{
if(self = [super init]) {
self.isJsonRequest =
NO;//请求参数是否JSON格式
self.isJsonResponse =
YES;//响应是否JSON格式
}
self.filterFunctions =
@[ @"getGoodsCollect" ,
@"cartList" , @"userInfo"];
return
self;
}
/**
* 如果返回true
发送token过期通知
*/
-(BOOL)skipTokenNotification:(NSString*) url{
for (NSString* function
in _filterFunctions) {//如果url中友方法参数返回true
if ([url rangeOfString:function].location != NSNotFound) {
return
true;
}
}
return
false;
}
/**
* 请求服务器URL
* 基本参数
* 一个完整的URL必须包含以下三个参数
* @param m 模块
目前只有Api ,
此处固定值
* @param c 控制器
* @param a 方法
http://shop.lambo.com/index.php?m=Api&c=Index&a=getConfig
*/
-(NSString *)GetUrlWhitController:(NSString *)c action:(NSString *)a {
//为YES的时候程序继续执行,
否则抛出异常
NSAssert(c || a, @"请求参数异常,
将无法访问服务器!");
NSString* baseURL = [NSString stringWithFormat:BASEURL , HTTP_HOST];//BASEURL_DEFAULT(服务器URL)和DEFAULT_HTTP_HOST在SPConstants.h中宏定义
return [NSString stringWithFormat:@"%@?m=Api&c=%@&a=%@" , baseURL , c ,a];
}
/**
* 请求服务器URL
* 基本参数
* 一个完整的URL必须包含以下三个参数
* @param m 模块
目前只有Api ,
此处固定值
* @param c 控制器
* @param a 方法
*/
-(NSString *)GetUrlWhitModule:(NSString *)m controller:(NSString *)c action:(NSString *)a {
//为YES的时候程序继续执行,
否则抛出异常
NSAssert(c || a, @"请求参数异常,
将无法访问服务器!");
NSString* baseURL = [NSString stringWithFormat:BASEURL_DEFAULT , DEFAULT_HTTP_HOST];
return [NSString stringWithFormat:@"%@?m=%@&c=%@&a=%@" , baseURL , m, c ,a];
}
/**
* 根据方法名和参数请求网络(字典参数)
*
* @param url 完整URL
* @param params 字典参数
* @param successBlock 成功回调
* @param failureBlock 失败回调
*
* @return return value description
*/
-(NSURLSessionDataTask *)requestWithUrl:(NSString *)url
params:(NSDictionary *)params
successBlock:(SuccessBlock)successBlock
failureBlock:(FailureBlock)failureBlock {
//构建公共请求参数
if (!params) {
params = [NSMutableDictionary dictionary];
}else{
params = [NSMutableDictionary dictionaryWithDictionary:params];
}
if([SPMobileApplication sharedInstance].isLogined)
{
SPUser *loginUser = [SPMobileApplication sharedInstance].loginUser;
[params setValue:loginUser.userID forKey:@"user_id"];
if (loginUser.token) {
[params setValue:loginUser.token forKey:@"token"];
}
}
if ([[SPMobileApplication sharedInstance] getPhoneDeviceID]) {
[params setValue:[[SPMobileApplication sharedInstance] getPhoneDeviceID] forKey:@"unique_id"];
NSLog(@"-没签名前--%@",params);
}
/* params=@{
@"sign":@"d8ded4324c37a4b43ab4b197a78fcded",
@"time":@"1492495675",
@"unique_id":@"891F1CCA-E4A7-4F35-BA03-688CD5314686";
}
*/
params = [self configSign:params url:url];//签名后的参数
NSLog(@"-签名后params--%@",params);
AFHTTPSessionManager *manager = [AFHTTPSessionManager manager];
manager.securityPolicy = [AFSecurityPolicy policyWithPinningMode:AFSSLPinningModeNone];//安全策略
manager.securityPolicy.allowInvalidCertificates = YES;
manager.responseSerializer.acceptableContentTypes=[NSSet setWithObjects:@"application/json",
@"text/json", @"text/javascript",@"text/html",@"text/xml",
@"text/plain; charset=utf-8",
nil];
if(self.isJsonResponse) {
manager.responseSerializer = [AFJSONResponseSerializer serializer];
} else {
manager.responseSerializer = [AFHTTPResponseSerializer serializer];
}
// manager.responseSerializer = [AFHTTPResponseSerializer serializer];
//SPSaveData保存用户信息类
[SPSaveData saveDataWithData:url key:@"domain"];
if(self.requestMethod == RequestMethodGet)
{
[manager GET:url parameters:params progress:nil success:^(NSURLSessionDataTask *
_Nonnull task, id
_Nullable responseObject) {
if (successBlock) {
if ([responseObject objectForKey:@"status"]) {
NSInteger status = [[responseObject objectForKey:@"status"] integerValue];
if ((status == RESPONSE_CODE_TOKENN_LOST || status == RESPONSE_CODE_TOKENN_INALIDE || status == RESPONSE_CODE_TOKENN_EXPIRE) && ![self
skipTokenNotification:url]) {
//发送通知//token过期,失效通知
[[NSNotificationCenter defaultCenter] postNotificationName:NotificationTokenExpire object:nil];
//token过期的接口统一设置超时提示
NSMutableDictionary* dict = [NSMutableDictionary dictionaryWithDictionary:responseObject];
[dict setValue:@"登录超时,请重新登录"
forKey:@"msg"];
responseObject = dict;
}
}
successBlock(task , responseObject);
}
} failure:^(NSURLSessionDataTask * _Nullable task, NSError *
_Nonnull error) {
NSLog(@"【错误信息】:\n%@",[error description]);
[self sendErrorLog:[error description] url:url parameter:nil];
if(failureBlock){
failureBlock(task,error);
}
}];
}
else
if(self.requestMethod == RequestMethodPost)
{
//NSInteger status = [[responseObject objectForKey:@"status"] integerValue];
[manager POST:url parameters:params progress:^(NSProgress *
_Nonnull uploadProgress) {
} success:^(NSURLSessionDataTask * _Nonnull task,
id _Nullable responseObject) {
if (successBlock) {
//*********************//如果不是标准的json数据,就需要用到下面的方法;
// NSString *str=[[NSString alloc]initWithData:responseObject encoding:NSUTF8StringEncoding];//网页二进制数据转换成字符串
// NSLog(@"---responseStr---%@",str);
// NSData *data=[[NSData alloc]initWithData:[str dataUsingEncoding:NSUTF8StringEncoding]];
// NSDictionary *responseObject=[NSJSONSerialization JSONObjectWithData:data options:NSJSONReadingMutableContainers error:nil];
//*******************************
if ([responseObject objectForKey:@"status"]) {
NSInteger status = [[responseObject objectForKey:@"status"] integerValue];
if ((status == RESPONSE_CODE_TOKENN_LOST || status == RESPONSE_CODE_TOKENN_INALIDE || status == RESPONSE_CODE_TOKENN_EXPIRE) && ![self
skipTokenNotification:url]) {
//发送通知//token过期,失效通知
[[NSNotificationCenter defaultCenter] postNotificationName:NotificationTokenExpire object:nil];
//token过期的接口统一设置超时提示
NSMutableDictionary* dict = [NSMutableDictionary dictionaryWithDictionary:responseObject];
[dict setValue:@"登录超时,请重新登录"
forKey:@"msg"];
responseObject = dict;
}
}
successBlock(task , responseObject);
}
} failure:^(NSURLSessionDataTask * _Nullable task, NSError *
_Nonnull error) {
NSLog(@"【错误信息】:\n%@",[error description]);
[self sendErrorLog:[error description] url:url parameter:nil];
//发送错误日志报告到服务器
if(failureBlock){
//发送通知
failureBlock(task,error);
}
}];
}
return
nil;
}
/**
* 上传图片(头像上传)
*
* @param url url description
* @param image image description
* @param completion completion description
* @param errorBlock errorBlock description
* @return <#return value description#>
*/
- (NSURLSessionDataTask *)requestUploadImageWithUrl:(NSString *)url
params:(NSDictionary *)params
images:(NSArray *)images
successBlock:(SuccessBlock)successBlock
failureBlock:(FailureBlock)failureBlock {
//构建公共请求参数
if (!params) {
params = [NSMutableDictionary dictionary];
}else{
params = [NSMutableDictionary dictionaryWithDictionary:params];
}
if([SPMobileApplication sharedInstance].isLogined)
{
SPUser *loginUser = [SPMobileApplication sharedInstance].loginUser;
[params setValue:loginUser.userID forKey:@"user_id"];
if (loginUser.token) {
[params setValue:loginUser.token forKey:@"token"];
}
}
params = [self configSign:params url:url];
AFURLSessionManager *manager = [[AFURLSessionManager alloc] initWithSessionConfiguration:[NSURLSessionConfiguration defaultSessionConfiguration]];
manager.securityPolicy.allowInvalidCertificates = YES;
//manager.responseSerializer.acceptableContentTypes = [NSSet setWithObject:@"text/html"];//设置相应内容类型
NSMutableURLRequest *request = [[AFHTTPRequestSerializer serializer]
multipartFormRequestWithMethod:@"POST"
URLString:url
parameters:params
constructingBodyWithBlock:^(id<AFMultipartFormData> formData) {
if (images && images.count >
0) {
for (NSInteger i =0; i<images.count ; i++) {
UIImage* image = images[i];
NSData* imageData = UIImagePNGRepresentation(image);
NSString* sname = [NSString stringWithFormat:@"img_file[%ld]" , i];
NSDateFormatter *formatter = [[NSDateFormatter alloc] init];
formatter.dateFormat =
@"yyyyMMddHHmmss";
NSString *str = [formatter stringFromDate:[NSDate date]];
NSString *fileName = [NSString stringWithFormat:@"%@_%ld.png", str , i];
//
上传图片,以文件流的格式
[formData appendPartWithFileData:imageData name:sname fileName:fileName mimeType:@"image/png"];
}
}
} error:nil];
NSURLSessionUploadTask *uploadTask;
uploadTask = [manager
uploadTaskWithStreamedRequest:request
progress:^(NSProgress * _Nonnull uploadProgress) {
}
completionHandler:^(NSURLResponse * _Nonnull response,
id _Nullable responseObject, NSError *
_Nullable error) {
if (error) {
NSLog(@"Error: %@", error);
if(failureBlock){
failureBlock(uploadTask,0);
}
} else {
NSLog(@"%@ %@", response, responseObject);
if(successBlock){
successBlock(uploadTask, responseObject);
}
}
}];
[uploadTask resume];
return
nil;
}
/**
*参数签名的方法
*/
-(NSDictionary*)configSign:(NSDictionary*)params url:(NSString*)url{
if (!params) {
return params;
}
NSMutableDictionary* signParams = [NSMutableDictionary dictionaryWithDictionary:params];
long locaTime = [SPCommonUtils getCurrentTime];//本地时间
long cutTime = [SPMobileApplication sharedInstance].cutServiceTime ;//本地与服务器时间差
NSString* time = [NSString stringWithFormat:@"%ld" , (locaTime + cutTime)];
NSString* signFmt = [SPCommonUtils signParameter:signParams time:time signKey:SP_SIGN_PRIVATGE_KEY url:url];//服务器验证签名方法
[signParams setValue:signFmt forKey:@"sign"];
[signParams setValue:time forKey:@"time"];
return signParams;
}
/**
* 发送错误日志报告到服务器
*
* @param params
*/
-(void)sendErrorLog:(NSString*)error url:(NSString*)errorUrl parameter:(NSDictionary*)parameter{
NSString* url = [self GetUrlWhitController:@"User" action:@"errorLog"];
NSMutableDictionary* params = nil;
//构建公共请求参数
if (!params) {
params = [NSMutableDictionary dictionary];
}else{
params = [NSMutableDictionary dictionaryWithDictionary:parameter];
}
[params setObject:errorUrl forKey:@"errorUrl"];
[params setObject:error forKey:@"error"];
NSLog(@"pushMobileInfo -> params : %@" , params);
NSMutableArray *queryItems = [NSMutableArray array];
for(NSString* key
in params ){
NSString* param = [NSString stringWithFormat:@"%@=%@" , key , params[key]];
[queryItems addObject:param];
}
NSString* dataString = [queryItems componentsJoinedByString:@"&"];
NSData *bodyData = [[dataString stringByAddingPercentEscapesUsingEncoding:NSUTF8StringEncoding]dataUsingEncoding:NSUTF8StringEncoding];//
//NSLog(@"pushMobileInfo -> requestUrl : %@ , dataString : %@" , baseUrl , dataString);
NSMutableURLRequest * request = [[NSMutableURLRequest alloc]init];
[request setHTTPMethod:@"post"];
//指定请求方式
[request setURL:[NSURL URLWithString:url]]; //设置请求的地址
[request setHTTPBody:bodyData]; //设置请求的参数
NSURLSession *session = [NSURLSession sharedSession];
__block NSString *result =
@"";
NSURLSessionDataTask *dataTask = [session dataTaskWithRequest:request completionHandler:^(NSData *
_Nullable data, NSURLResponse *
_Nullable response, NSError *
_Nullable error) {
if (!error) {
//没有错误,返回正确;
NSLog(@"sendErrorLog success
:%@",result);
}else{
//出现错误;
NSLog(@"sendErrorLog failed
:%@",error);
}
}];
[dataTask resume];
}
@end
=====================
/**
* $description: 首页以及系统配置相关网络请求
*/
#import "SPBaseRequestManager.h"
@interface SPHomeRequestManager : SPBaseRequestManager
/**
* 查询系统配置信息
* 使用万能SQL: index.php?m=Api&c=Base&a=sqlApi
* @param success success description
* @param failure failure description
*/
+(void)getServiceConfig:(SuccessHandleBlock)success failure:(FailureHandleBlock)failure;
/**
* 查询插件配置信息
* 使用万能SQL: index.php?m=Api&c=Index&a=getPluginConfig
* @param success success description
* @param failure failure description
*/
+(void)getServicePlugin:(SuccessHandleBlock)success failure:(FailureHandleBlock)failure;
#pragma mark - 获取首页数据
/**
* 获取首页数据
* @URL index.php?m=Api&c=Index&a=homePage
* @param success success description
* @param failure failure description
*/
+(void)getHomePageData:(SuccessHandleBlock)success failure:(FailureHandleBlock)failure;
/**
* 获取首页收藏数据----猜你喜欢
* @URL index.php?m=Api&c=Index&a=favourite
* @param success success description
* @param failure failure description
*/
+(void)getFavouriteWithPage:(NSInteger)pageIndex success:(SuccessHandleBlock)success failure:(FailureHandleBlock)failure;
#pragma mark 刷新服务器时间戳
/**
* 获取服务器时间戳
* @URL index.php?m=Api&c=Base&a=getServerTime
* @param success success description
* @param failure failure description
*/
+(void)refreshServiceTime:(SuccessHandleBlock)success failure:(FailureHandleBlock)failure;
@end
================
/**
* $description: 首页以及系统配置相关网络请求
*/
#import "SPHomeRequestManager.h"
@implementation SPHomeRequestManager
/**
* 查询系统配置信息
* 使用万能SQL: index.php?m=Api&c=Index&a=getConfig
* @param success success description
* @param failure failure description
*/
+(void)getServiceConfig:(SuccessHandleBlock)success failure:(FailureHandleBlock)failure{
CommonDataService *request = [super PostRequestService];//调用父类的方法
NSString* url = [request GetUrlWhitController:@"Index" action:@"getConfig"];//请求服务器的URL
//创建请求
[request requestWithUrl:url params:nil successBlock:^(NSURLSessionDataTask *operation,
id responseObject) {
NSInteger status = [[responseObject objectForKey:@"status"] integerValue];
NSString *msg = [responseObject objectForKey:@"msg"];
if(status >
0)
{
//传递对象
if(success)
{
success(msg, configs);
}
/* End 数据结果解析区 */
}
else
{
if(failure)
{
failure(msg,-1);
}
}
} failureBlock:^(NSURLSessionDataTask *operation, NSError *error) {
NSLog(@" failureBlock :%@", [error description]);
if(failure)
{
failure(kNetworkError,-1);
}
}];
}
/**
* 查询插件配置信息
* 使用万能SQL: index.php?m=Api&c=Index&a=getPluginConfig
* @param success success description
* @param failure failure description
*/
+(void)getServicePlugin:(SuccessHandleBlock)success failure:(FailureHandleBlock)failure{
CommonDataService *request = [super PostRequestService];
NSString* url = [request GetUrlWhitController:@"Index" action:@"getPluginConfig"];
[request requestWithUrl:url params:nil successBlock:^(NSURLSessionDataTask *operation,
id responseObject) {
NSInteger status = [[responseObject objectForKey:@"status"] integerValue];
NSString *msg = [responseObject objectForKey:@"msg"];
if(status >
0)
{
}
//传递对象
if(success)
{
success(msg, dataDict);
}
/* End 数据结果解析区 */
}
else
{
if(failure)
{
failure(msg,-1);
}
}
} failureBlock:^(NSURLSessionDataTask *operation, NSError *error) {
NSLog(@" failureBlock :%@", [error description]);
if(failure)
{
failure(kNetworkError,-1);
}
}];
}
/**
* 获取首页数据-
滚动图片数据源-促销(暂时没看到)-精品推荐-新品上市-热销商品
* @URL index.php?m=Api&c=Index&a=homePage
* @param success success description
* @param failure failure description
*/
+(void)getHomePageData:(SuccessHandleBlock)success failure:(FailureHandleBlock)failure{
CommonDataService *request = [super PostRequestService];
NSString* url = [request GetUrlWhitController:@"Index" action:@"homePage"];
[request requestWithUrl:url params:nil successBlock:^(NSURLSessionDataTask *operation,
id responseObject) {
NSInteger status = [[responseObject objectForKey:@"status"] integerValue];
NSString *msg = [responseObject objectForKey:@"msg"];
if(status >
0)
{
//传递对象
if(success)
{
success(msg, 传递的数据);
}
/* End 数据结果解析区 */
}
else
{
if(failure)
{
failure(msg,-1);
}
}
} failureBlock:^(NSURLSessionDataTask *operation, NSError *error) {
NSLog(@" failureBlock :%@", [error description]);
if(failure)
{
failure(kNetworkError,-1);
}
}];
}
/**
* 获取首页收藏数据----猜你喜欢的数据
* @URL index.php?m=Api&c=Index&a=favourite
* @param success success description
* @param failure failure description
*/
+(void)getFavouriteWithPage:(NSInteger)pageIndex success:(SuccessHandleBlock)success failure:(FailureHandleBlock)failure{
CommonDataService *request = [super PostRequestService];
NSString* url = [request GetUrlWhitController:@"Index" action:@"favourite"];
NSDictionary* params = @{
@"p":[NSNumber numberWithInteger:pageIndex],
@"page_size":[NSNumber numberWithInteger:SizeOfPage]
};//表示每页显示几条数据(10条)
//在CommonDataService中根据方法名和参数请求网络(字典参数)
[request requestWithUrl:url params:params successBlock:^(NSURLSessionDataTask *operation,
id responseObject) {
NSInteger status = [[responseObject objectForKey:@"status"] integerValue];
NSString *msg = [responseObject objectForKey:@"msg"];
if(status >
0)
{
/* Begin 数据结果解析区 */
//解析对象
NSDictionary *resultData = [responseObject objectForKey:@"result"];
//传递对象
if(success)
{
success(msg, favourits);
}
/* End 数据结果解析区 */
}
else
{
if(failure)
{
failure(msg,-1);
}
}
} failureBlock:^(NSURLSessionDataTask *operation, NSError *error) {
NSLog(@" failureBlock :%@", [error description]);
if(failure)
{
failure(kNetworkError,-1);
}
}];
}
#pragma mark 刷新服务器时间戳
/**
* 获取服务器时间戳
* @URL index.php?m=Api&c=Base&a=getServerTime
* @param success success description
* @param failure failure description
*/
+(void)refreshServiceTime:(SuccessHandleBlock)success failure:(FailureHandleBlock)failure{
CommonDataService *request = [super PostRequestService];
NSString* url = [request GetUrlWhitController:@"Base" action:@"getServerTime"];
[request requestWithUrl:url params:nil successBlock:^(NSURLSessionDataTask *operation,
id responseObject) {
NSInteger status = [[responseObject objectForKey:@"status"] integerValue];
NSString *msg = [responseObject objectForKey:@"msg"];
if(status >
0)
{
long serviceTime = [[responseObject objectForKey:@"result"] longValue];
long localTime = [SPCommonUtils getCurrentTime];
long cutTime = serviceTime - localTime;
//传递对象
if(success)
{
success(msg, 传递时间差);
}
/* End 数据结果解析区 */
}
else
{
if(failure)
{
failure(msg,-1);
}
}
} failureBlock:^(NSURLSessionDataTask *operation, NSError *error) {
NSLog(@" failureBlock :%@", [error description]);
if(failure)
{
failure(kNetworkError,-1);
}
}];
}
@end
相关文章推荐
- ios开发如何封装AFN第三方类库中的http请求
- iOS AFN的再次封装
- iOS - 简述二次封装AFN,设置请求头,https安全策略
- iOS开发之资讯类App常用分类控件的封装与实现(CollectionView+Swift3.0+)
- IOS 常用方法封装
- ios 基于AFN的二次封装
- iOS封装常用的方法
- ios 对于常用的NSUserDefults的封装
- iOS通用库--常用功能二之下拉选择框的封装
- iOS AFN 封装数据
- iOS常用的封装方法
- iOS AFN 封装POST网络请求(AFURLSessionManager)
- iOS常用的一些动画效果,UIView封装的动画,CALayer的动画等
- IOS常用方法封装(1)
- IOS AFN请求封装使用
- iOS中常用简单封装
- iOS 之AFN封装
- iOS开发总结之block回调以AFN为基础封装的网络请求操作类
- iOS - 利用AFN检测网络状态的类封装
- (iOS-框架封装)AFN3.x 网络请求封装