iOS访问https ssl和tls双向加密
2016-06-12 08:51
489 查看
转载:http://blog.csdn.net/woaifen3344/article/details/41145729
关于https和ssl的原理,请到此处查看:http://blog.163.com/magicc_love/blog/static/185853662201321423527263/
由于项目需求,访问服务是https的,并且使用的是ssl加密方式
下面说明使用MKNetworkit网络库实现的代码:
[objc] view
plain copy
print?
![](https://oscdn.geek-share.com/Uploads/Images/Content/201611/a7c8e286f463007e2a900848b93dd72c.png)
![](https://oscdn.geek-share.com/Uploads/Images/Content/201611/9e12f1d3e499fc949c886e7c9e0484f9)
- (void)testClientCertificate {
SecIdentityRef identity = NULL;
SecTrustRef trust = NULL;
NSString *p12 = [[NSBundle mainBundle] pathForResource:@"testClient" ofType:@"p12"];
NSData *PKCS12Data = [NSData dataWithContentsOfFile:p12];
[[self class] extractIdentity:&identity andTrust:&trust fromPKCS12Data:PKCS12Data];
NSString *url = @"https://218.244.131.231/ManicureShop/api/order/pay/%@";
NSDictionary *dic = @{@"request" : @{
@"orderNo" : @"1409282102222110030643",
@"type" : @(2)
}
};
_signString = nil;
NSData *postData = [NSJSONSerialization dataWithJSONObject:dic options:NSJSONWritingPrettyPrinted error:nil];
NSString *sign = [self signWithSignKey:@"test" params:dic];
NSMutableData *body = [postData mutableCopy];
NSLog(@"%@", [[NSString alloc] initWithData:body encoding:NSUTF8StringEncoding]);
url = [NSString stringWithFormat:url, sign];
MKNetworkEngine *engine = [[MKNetworkEngine alloc] initWithHostName:@"218.244.131.231"];
MKNetworkOperation *op = [engine operationWithPath:[NSString stringWithFormat:@"/ManicureShop/api/order/pay/%@", sign] params:dic httpMethod:@"POST" ssl:YES];
op.postDataEncoding = MKNKPostDataEncodingTypeJSON; // 传JOSN
// 这个是app bundle 路径下的自签证书
op.clientCertificate = [[[NSBundle mainBundle] resourcePath] stringByAppendingPathComponent:@"testClient.p12"];
// 这个是自签证书的密码
op.clientCertificatePassword = @"testHttps";
// 由于自签名的证书是需要忽略的,所以这里需要设置为YES,表示允许
op.shouldContinueWithInvalidCertificate = YES;
[op addCompletionHandler:^(MKNetworkOperation *completedOperation) {
NSLog(@"%@", completedOperation.responseJSON);
} errorHandler:^(MKNetworkOperation *completedOperation, NSError *error) {
NSLog(@"%@", [error description]);
}];
[engine enqueueOperation:op];
return;
}
// 下面这段代码是提取和校验证书的数据的
[objc] view
plain copy
print?
![](https://oscdn.geek-share.com/Uploads/Images/Content/201611/a7c8e286f463007e2a900848b93dd72c.png)
![](https://oscdn.geek-share.com/Uploads/Images/Content/201611/9e12f1d3e499fc949c886e7c9e0484f9)
+ (BOOL)extractIdentity:(SecIdentityRef *)outIdentity andTrust:(SecTrustRef*)outTrust fromPKCS12Data:(NSData *)inPKCS12Data {
OSStatus securityError = errSecSuccess;
// 证书密钥
NSDictionary *optionsDictionary = [NSDictionary dictionaryWithObject:@"testHttps"
forKey:(__bridge id)kSecImportExportPassphrase];
CFArrayRef items = CFArrayCreate(NULL, 0, 0, NULL);
securityError = SecPKCS12Import((__bridge CFDataRef)inPKCS12Data,(__bridge CFDictionaryRef)optionsDictionary,&items);
if (securityError == 0) {
CFDictionaryRef myIdentityAndTrust = CFArrayGetValueAtIndex (items, 0);
const voidvoid *tempIdentity = NULL;
tempIdentity = CFDictionaryGetValue (myIdentityAndTrust, kSecImportItemIdentity);
*outIdentity = (SecIdentityRef)tempIdentity;
const voidvoid *tempTrust = NULL;
tempTrust = CFDictionaryGetValue (myIdentityAndTrust, kSecImportItemTrust);
*outTrust = (SecTrustRef)tempTrust;
} else {
NSLog(@"Failed with error code %d",(int)securityError);
return NO;
}
return YES;
}
下面说明一下使用AFNetworking网络库访问的方式:
[objc] view
plain copy
print?
![](https://oscdn.geek-share.com/Uploads/Images/Content/201611/a7c8e286f463007e2a900848b93dd72c.png)
![](https://oscdn.geek-share.com/Uploads/Images/Content/201611/9e12f1d3e499fc949c886e7c9e0484f9)
- (void)testClientCertificate {
SecIdentityRef identity = NULL;
SecTrustRef trust = NULL;
NSString *p12 = [[NSBundle mainBundle] pathForResource:@"testClient" ofType:@"p12"];
NSData *PKCS12Data = [NSData dataWithContentsOfFile:p12];
[[self class] extractIdentity:&identity andTrust:&trust fromPKCS12Data:PKCS12Data];
NSString *url = @"https://218.244.131.231/ManicureShop/api/order/pay/%@";
NSDictionary *dic = @{@"request" : @{
@"orderNo" : @"1409282102222110030643",
@"type" : @(2)
}
};
_signString = nil;
NSData *postData = [NSJSONSerialization dataWithJSONObject:dic options:NSJSONWritingPrettyPrinted error:nil];
NSString *sign = [self signWithSignKey:@"test" params:dic];
NSMutableData *body = [postData mutableCopy];
NSLog(@"%@", [[NSString alloc] initWithData:body encoding:NSUTF8StringEncoding]);
url = [NSString stringWithFormat:url, sign];
AFHTTPRequestOperationManager *manager = [AFHTTPRequestOperationManager manager];
manager.requestSerializer = [AFJSONRequestSerializer serializer];
manager.responseSerializer = [AFJSONResponseSerializer serializer];
[manager.requestSerializer setValue:@"application/json" forHTTPHeaderField:@"Accept"];
[manager.requestSerializer setValue:@"application/json" forHTTPHeaderField:@"Content-Type"];
manager.responseSerializer.acceptableContentTypes = [NSSet setWithArray:@[@"application/json", @"text/plain"]];
manager.securityPolicy = [self customSecurityPolicy];
[manager POST:url parameters:dic success:^(AFHTTPRequestOperation *operation, id responseObject) {
NSLog(@"JSON: %@", responseObject);
} failure:^(AFHTTPRequestOperation *operation, NSError *error) {
NSLog(@"Error: %@", error);
}];
}
下面这段代码是处理SSL安全性问题的:
[objc] view
plain copy
print?
![](https://oscdn.geek-share.com/Uploads/Images/Content/201611/a7c8e286f463007e2a900848b93dd72c.png)
![](https://oscdn.geek-share.com/Uploads/Images/Content/201611/9e12f1d3e499fc949c886e7c9e0484f9)
/**** SSL Pinning ****/
- (AFSecurityPolicy*)customSecurityPolicy {
NSString *cerPath = [[NSBundle mainBundle] pathForResource:@"testClient" ofType:@"cer"];
NSData *certData = [NSData dataWithContentsOfFile:cerPath];
AFSecurityPolicy *securityPolicy = [AFSecurityPolicy defaultPolicy];
[securityPolicy setAllowInvalidCertificates:YES];
[securityPolicy setPinnedCertificates:@[certData]];
[securityPolicy setSSLPinningMode:AFSSLPinningModeCertificate];
/**** SSL Pinning ****/
return securityPolicy;
}
为了实现访问https tls加密方式,我也费了不少时间来查,这里写下此文章,希望对大家有用!
关于https和ssl的原理,请到此处查看:http://blog.163.com/magicc_love/blog/static/185853662201321423527263/
由于项目需求,访问服务是https的,并且使用的是ssl加密方式
下面说明使用MKNetworkit网络库实现的代码:
[objc] view
plain copy
print?
![](https://oscdn.geek-share.com/Uploads/Images/Content/201611/a7c8e286f463007e2a900848b93dd72c.png)
- (void)testClientCertificate {
SecIdentityRef identity = NULL;
SecTrustRef trust = NULL;
NSString *p12 = [[NSBundle mainBundle] pathForResource:@"testClient" ofType:@"p12"];
NSData *PKCS12Data = [NSData dataWithContentsOfFile:p12];
[[self class] extractIdentity:&identity andTrust:&trust fromPKCS12Data:PKCS12Data];
NSString *url = @"https://218.244.131.231/ManicureShop/api/order/pay/%@";
NSDictionary *dic = @{@"request" : @{
@"orderNo" : @"1409282102222110030643",
@"type" : @(2)
}
};
_signString = nil;
NSData *postData = [NSJSONSerialization dataWithJSONObject:dic options:NSJSONWritingPrettyPrinted error:nil];
NSString *sign = [self signWithSignKey:@"test" params:dic];
NSMutableData *body = [postData mutableCopy];
NSLog(@"%@", [[NSString alloc] initWithData:body encoding:NSUTF8StringEncoding]);
url = [NSString stringWithFormat:url, sign];
MKNetworkEngine *engine = [[MKNetworkEngine alloc] initWithHostName:@"218.244.131.231"];
MKNetworkOperation *op = [engine operationWithPath:[NSString stringWithFormat:@"/ManicureShop/api/order/pay/%@", sign] params:dic httpMethod:@"POST" ssl:YES];
op.postDataEncoding = MKNKPostDataEncodingTypeJSON; // 传JOSN
// 这个是app bundle 路径下的自签证书
op.clientCertificate = [[[NSBundle mainBundle] resourcePath] stringByAppendingPathComponent:@"testClient.p12"];
// 这个是自签证书的密码
op.clientCertificatePassword = @"testHttps";
// 由于自签名的证书是需要忽略的,所以这里需要设置为YES,表示允许
op.shouldContinueWithInvalidCertificate = YES;
[op addCompletionHandler:^(MKNetworkOperation *completedOperation) {
NSLog(@"%@", completedOperation.responseJSON);
} errorHandler:^(MKNetworkOperation *completedOperation, NSError *error) {
NSLog(@"%@", [error description]);
}];
[engine enqueueOperation:op];
return;
}
// 下面这段代码是提取和校验证书的数据的
[objc] view
plain copy
print?
![](https://oscdn.geek-share.com/Uploads/Images/Content/201611/a7c8e286f463007e2a900848b93dd72c.png)
+ (BOOL)extractIdentity:(SecIdentityRef *)outIdentity andTrust:(SecTrustRef*)outTrust fromPKCS12Data:(NSData *)inPKCS12Data {
OSStatus securityError = errSecSuccess;
// 证书密钥
NSDictionary *optionsDictionary = [NSDictionary dictionaryWithObject:@"testHttps"
forKey:(__bridge id)kSecImportExportPassphrase];
CFArrayRef items = CFArrayCreate(NULL, 0, 0, NULL);
securityError = SecPKCS12Import((__bridge CFDataRef)inPKCS12Data,(__bridge CFDictionaryRef)optionsDictionary,&items);
if (securityError == 0) {
CFDictionaryRef myIdentityAndTrust = CFArrayGetValueAtIndex (items, 0);
const voidvoid *tempIdentity = NULL;
tempIdentity = CFDictionaryGetValue (myIdentityAndTrust, kSecImportItemIdentity);
*outIdentity = (SecIdentityRef)tempIdentity;
const voidvoid *tempTrust = NULL;
tempTrust = CFDictionaryGetValue (myIdentityAndTrust, kSecImportItemTrust);
*outTrust = (SecTrustRef)tempTrust;
} else {
NSLog(@"Failed with error code %d",(int)securityError);
return NO;
}
return YES;
}
下面说明一下使用AFNetworking网络库访问的方式:
[objc] view
plain copy
print?
![](https://oscdn.geek-share.com/Uploads/Images/Content/201611/a7c8e286f463007e2a900848b93dd72c.png)
- (void)testClientCertificate {
SecIdentityRef identity = NULL;
SecTrustRef trust = NULL;
NSString *p12 = [[NSBundle mainBundle] pathForResource:@"testClient" ofType:@"p12"];
NSData *PKCS12Data = [NSData dataWithContentsOfFile:p12];
[[self class] extractIdentity:&identity andTrust:&trust fromPKCS12Data:PKCS12Data];
NSString *url = @"https://218.244.131.231/ManicureShop/api/order/pay/%@";
NSDictionary *dic = @{@"request" : @{
@"orderNo" : @"1409282102222110030643",
@"type" : @(2)
}
};
_signString = nil;
NSData *postData = [NSJSONSerialization dataWithJSONObject:dic options:NSJSONWritingPrettyPrinted error:nil];
NSString *sign = [self signWithSignKey:@"test" params:dic];
NSMutableData *body = [postData mutableCopy];
NSLog(@"%@", [[NSString alloc] initWithData:body encoding:NSUTF8StringEncoding]);
url = [NSString stringWithFormat:url, sign];
AFHTTPRequestOperationManager *manager = [AFHTTPRequestOperationManager manager];
manager.requestSerializer = [AFJSONRequestSerializer serializer];
manager.responseSerializer = [AFJSONResponseSerializer serializer];
[manager.requestSerializer setValue:@"application/json" forHTTPHeaderField:@"Accept"];
[manager.requestSerializer setValue:@"application/json" forHTTPHeaderField:@"Content-Type"];
manager.responseSerializer.acceptableContentTypes = [NSSet setWithArray:@[@"application/json", @"text/plain"]];
manager.securityPolicy = [self customSecurityPolicy];
[manager POST:url parameters:dic success:^(AFHTTPRequestOperation *operation, id responseObject) {
NSLog(@"JSON: %@", responseObject);
} failure:^(AFHTTPRequestOperation *operation, NSError *error) {
NSLog(@"Error: %@", error);
}];
}
下面这段代码是处理SSL安全性问题的:
[objc] view
plain copy
print?
![](https://oscdn.geek-share.com/Uploads/Images/Content/201611/a7c8e286f463007e2a900848b93dd72c.png)
/**** SSL Pinning ****/
- (AFSecurityPolicy*)customSecurityPolicy {
NSString *cerPath = [[NSBundle mainBundle] pathForResource:@"testClient" ofType:@"cer"];
NSData *certData = [NSData dataWithContentsOfFile:cerPath];
AFSecurityPolicy *securityPolicy = [AFSecurityPolicy defaultPolicy];
[securityPolicy setAllowInvalidCertificates:YES];
[securityPolicy setPinnedCertificates:@[certData]];
[securityPolicy setSSLPinningMode:AFSSLPinningModeCertificate];
/**** SSL Pinning ****/
return securityPolicy;
}
为了实现访问https tls加密方式,我也费了不少时间来查,这里写下此文章,希望对大家有用!
相关文章推荐
- Android官方开发文档Training系列课程中文版:网络操作之网络管理
- Kali进行web渗透笔记(十一)
- Kali进行web渗透笔记(十)
- Kali进行web渗透笔记(九)
- Kali进行web渗透笔记(六)
- 网络监控nagios小结
- Kali进行web渗透笔记(五)
- okhttp
- Kali进行web渗透笔记(四)
- Kali进行web渗透笔记(三)
- Kali进行web渗透笔记(二)
- Kali进行web渗透笔记(一)
- 私有地址和网络地址转换
- 重构Minot's应用——ios网络通信中的设计模式与架构设计
- bzoj4538【HNOI2016】网络
- nginx和httpd反向代理和负载均衡tomcat集群
- HTTP之URL
- cogs_396_魔术球问题_(最小路径覆盖+二分图匹配,网络流24题#4)
- 网络IO模型(同步异步,阻塞非阻塞)
- nginx 编写简单HTTP模块 hello world