关于ios项目绕过证书访问https
2016-06-24 20:45
441 查看
听说苹果发布了声明,将于年底将所有iOS应用的http访问强制改为https访问。个人认为这是个好事,启用HTTPS网络连接之后,数据传输的安全性将大幅提示,不容易被黑客拦截破译。
所以得跟上形势不是,这也许就是程序员的无奈,相当一个不过是的好程序员就得不断的学习新的知识。下面就是我用NSURLSession封装好的数据请求类。
说明:请求方法结合了MD5加密,大家看代码的时候注意看NSURLSessionTaskDelegate代理方法即可
AsyncNetWorkRequest.h 中
AsyncNetWorkRequest.m 中
所以得跟上形势不是,这也许就是程序员的无奈,相当一个不过是的好程序员就得不断的学习新的知识。下面就是我用NSURLSession封装好的数据请求类。
说明:请求方法结合了MD5加密,大家看代码的时候注意看NSURLSessionTaskDelegate代理方法即可
AsyncNetWorkRequest.h 中
#import <Foundation/Foundation.h> @interface AsyncNetWorkRequest : NSObject // 定义block块属性 // 网络请求成功 @property (nonatomic, copy) void(^successBlock)(NSData *data); // 网络请求失败 @property (nonatomic, copy) void(^errorBlock)(NSError *error); + (instancetype)startRequestDataWithURLStr:(NSString *)str parameter:(NSDictionary *)parameter requestType:(NSString *)type SucessBlock:(void (^)(NSData *data))sucessBlock ErrorBlock:(void (^)(NSError *error))errorBlock; + @end
AsyncNetWorkRequest.m 中
#import "AsyncNetWorkRequest.h" #import "MD5Encryption.h" @interface AsyncNetWorkRequest () <NSURLSessionTaskDelegate> @end @implementation AsyncNetWorkRequest - (instancetype)init { self = [super init]; if (self) { } return self; } // 对外数据请求类 + (instancetype)startRequestDataWithURLStr:(NSString *)str parameter:(NSDictionary *)parameter requestType:(NSString *)type SucessBlock:(void (^)(NSData *data))sucessBlock ErrorBlock:(void (^)(NSError *error))errorBlock { AsyncNetWorkRequest *async = [[AsyncNetWorkRequest alloc] init]; async.successBlock = sucessBlock; async.errorBlock = errorBlock; // 获取加密后的数据请求字符串 NSString *urlString = [MD5Encryption startMD5EncryptionWithParameters:parameter URLString:str]; NSLog(@"打印数据请求字符串 %@", urlString); NSURL *url = [NSURL URLWithString:urlString]; NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:url]; // get请求 if ([type isEqualToString:@"GET"]) { [async requestGETWithRequest:request Async:async]; } // post请求 else { // 用 ?分割 取出要上传的数据。 NSArray *array = [urlString componentsSeparatedByString:@"?"]; NSString *stringBody = array[1]; // 将上传数据转化为data NSData *bodyData = [stringBody dataUsingEncoding:NSUTF8StringEncoding]; NSURL *urlPost = [NSURL URLWithString:str]; NSMutableURLRequest *requestPost = [NSMutableURLRequest requestWithURL:urlPost]; [async requestPOSTWithRequest:requestPost Async:async BodyData:bodyData]; } return async; } #pragma mark - post请求 - (void)requestPOSTWithRequest:(NSMutableURLRequest *)request Async:(AsyncNetWorkRequest *)async BodyData:(NSData *)bodyData { request.HTTPMethod = @"POST"; request.HTTPBody = bodyData; NSURLSessionConfiguration *configuration = [NSURLSessionConfiguration defaultSessionConfiguration]; NSURLSession *session = [NSURLSession sessionWithConfiguration:configuration]; NSURLSessionDataTask *task = [session dataTaskWithRequest:request completionHandler:^(NSData * _Nullable data, NSURLResponse * _Nullable response, NSError * _Nullable error) { if (error == nil) { NSLog(@"POST请求成功"); async.successBlock(data); } else { NSLog(@"POST请求失败"); async.errorBlock(error); } }]; [task resume]; } #pragma mark - get请求 - (void)requestGETWithRequest:(NSMutableURLRequest *)request Async:(AsyncNetWorkRequest *)async { request.HTTPMethod = @"GET"; // 创建会话 NSURLSessionConfiguration *configuration = [NSURLSessionConfiguration defaultSessionConfiguration]; configuration.TLSMaximumSupportedProtocol = kTLSProtocol1; NSURLSession *session = [NSURLSession sessionWithConfiguration:configuration delegate:self delegateQueue:[NSOperationQueue mainQueue]]; NSURLSessionDataTask *dataTask = [session dataTaskWithRequest:request completionHandler:^(NSData * _Nullable data, NSURLResponse * _Nullable response, NSError * _Nullable error) { if (error == nil) { NSLog(@"GET数据请求成功"); async.successBlock(data); } else { NSLog(@"GET数据请求失败 %@", [error description]); async.errorBlock(error); } }]; [dataTask resume]; } #if 1 - 这是第一种写法 // ios项目绕过证书访问https程序,当你向服务器请求时,服务器需要证书时会走下面的方法 - (void)URLSession:(NSURLSession *)session didReceiveChallenge:(NSURLAuthenticationChallenge *)challenge completionHandler:(void (^)(NSURLSessionAuthChallengeDisposition disposition, NSURLCredential *credential))completionHandler { // 处理认证证书的方案 NSString *method = challenge.protectionSpace.authenticationMethod; NSLog(@"%@", method); if([method isEqualToString:NSURLAuthenticationMethodServerTrust]){ NSString *host = challenge.protectionSpace.host; NSLog(@" 分割 %@", host); NSURLCredential *credential = [NSURLCredential credentialForTrust:challenge.protectionSpace.serverTrust]; completionHandler(NSURLSessionAuthChallengeUseCredential, credential); return; } NSString *thePath = [[NSBundle mainBundle] pathForResource:@"client" ofType:@"p12"]; NSData *PKCS12Data = [[NSData alloc] initWithContentsOfFile:thePath]; CFDataRef inPKCS12Data = (CFDataRef)CFBridgingRetain(PKCS12Data); SecIdentityRef identity; // 读取p12证书中的内容 OSStatus result = [self extractP12Data:inPKCS12Data toIdentity:&identity]; if(result != errSecSuccess){ completionHandler(NSURLSessionAuthChallengeCancelAuthenticationChallenge, nil); return; } SecCertificateRef certificate = NULL; SecIdentityCopyCertificate (identity, &certificate); const void *certs[] = {certificate}; CFArrayRef certArray = CFArrayCreate(kCFAllocatorDefault, certs, 1, NULL); NSURLCredential *credential = [NSURLCredential credentialWithIdentity:identity certificates:(NSArray*)CFBridgingRelease(certArray) persistence:NSURLCredentialPersistencePermanent]; completionHandler(NSURLSessionAuthChallengeUseCredential, credential); } -(OSStatus) extractP12Data:(CFDataRef)inP12Data toIdentity:(SecIdentityRef*)identity { OSStatus securityError = errSecSuccess; CFStringRef password = CFSTR("the_password"); const void *keys[] = { kSecImportExportPassphrase }; const void *values[] = { password }; CFDictionaryRef options = CFDictionaryCreate(NULL, keys, values, 1, NULL, NULL); CFArrayRef items = CFArrayCreate(NULL, 0, 0, NULL); securityError = SecPKCS12Import(inP12Data, options, &items); if (securityError == 0) { CFDictionaryRef ident = CFArrayGetValueAtIndex(items,0); const void *tempIdentity = NULL; tempIdentity = CFDictionaryGetValue(ident, kSecImportItemIdentity); *identity = (SecIdentityRef)tempIdentity; } if (options) { CFRelease(options); } return securityError; } #endif #if 0 - 这是第二种写法 #pragma mark - ios项目绕过证书访问https程序,当向服务端请求数据时,会通过该方法进行证书验证 - (void)URLSession:(NSURLSession *)session didReceiveChallenge:(NSURLAuthenticationChallenge *)challenge completionHandler:(void (^)(NSURLSessionAuthChallengeDisposition, NSURLCredential * _Nullable))completionHandler { if (challenge.protectionSpace.authenticationMethod == NSURLAuthenticationMethodServerTrust) { NSLog(@"服务端证书认证"); SecTrustRef servertrust = challenge.protectionSpace.serverTrust; SecCertificateRef certi= SecTrustGetCertificateAtIndex(servertrust, 0); NSData *certidata = CFBridgingRelease(CFBridgingRetain(CFBridgingRelease(SecCertificateCopyData(certi)))); NSString *path = [[NSBundle mainBundle] pathForResource:@"tomcat_server" ofType:@"cer"]; NSData *localCertiData = [NSData dataWithContentsOfFile:path]; if ([certidata isEqualToData:localCertiData]) { NSURLCredential *credential = [[NSURLCredential alloc] initWithTrust:servertrust]; [challenge.sender useCredential:credential forAuthenticationChallenge:challenge]; completionHandler(NSURLSessionAuthChallengeUseCredential, credential); } else { completionHandler(NSURLSessionAuthChallengeCancelAuthenticationChallenge, nil); NSLog(@"服务端认证失败"); } } } #endif @end
相关文章推荐
- HttpUtils请求XML加XListView刷新加载
- 计算机网络体系结构详解(图文)
- 130行代码实现BP神经网络原理及应用举例
- iOS每日一记————————初识HTTP协议 Socket TCP/UDP
- 【JAVA】Socket网络编程
- Volley源码解析(三)网络请求流程
- [置顶] 台湾大学机器学习笔记——Neural Network 神经网络
- 对于httpclient上传文件的封装
- Python即时网络爬虫项目启动说明
- 数据包在用户空间的状态
- Spring mvc No mapping found for HTTP request with URI
- C++ STL 文件读取和容器(转载自http://blog.sina.com.cn/s/blog_735f29100102uwwd.html)
- Exception in thread "http-bio-8080-exec-2" java.lang.OutOfMemoryError: PermGen space
- [!] /usr/bin/git clone https://github.com/CocoaPods/Specs.git master Cloning
- 网络请求
- libubox组件(2)——blob/blobmsg (转载 https://segmentfault.com/a/1190000002391970)
- CDN网络访问原理
- http状态码
- (Android)使用httpclient上传文件到服务器
- iOS开发 - Swift实现检测网络连接状态及网络类型