[英]SSL Pinning using AFNetworking in iOS not working
我正在使用 AFnetworking。 我的应用程序网络服务器在 TLS 1.2 中。 我想将证书固定添加到我的 iOS 应用程序。 我的代码如下:
AFHTTPSessionManager *manager=[[AFHTTPSessionManager manager] initWithBaseURL:serviceURL];
NSSet *certificates = [AFSecurityPolicy certificatesInBundle:[NSBundle mainBundle]];
AFSecurityPolicy *policy = [AFSecurityPolicy policyWithPinningMode:AFSSLPinningModeCertificate withPinnedCertificates:certificates];
policy.validatesDomainName = YES;
policy.allowInvalidCertificates = YES;
opManager.securityPolicy = policy;
我的捆绑包中有有效的服务器证书,并且使用此代码,Web 服务工作正常。 但是,当我尝试使用不正确的示例证书进行相同操作时,网络服务也在工作。 我什至尝试在捆绑中没有证书,那个时候网络服务也工作正常。 谁能解释一下? AppTransportSecurity 在我的应用程序中打开。
<key>NSAppTransportSecurity</key>
<dict>
<key>NSAllowsArbitraryLoads</key>
<false/>
</dict>
我找到了解决这个问题的方法。 请在下面找到我用来替换现有代码的代码。 它按预期工作。
AFHTTPSessionManager *opManager=[[AFHTTPSessionManager manager] initWithBaseURL:baseUrl];
opManager.requestSerializer = [AFHTTPRequestSerializer serializer];
opManager.responseSerializer = [AFHTTPResponseSerializer serializer];
// SSL Pinning
NSString *certificatePath = [[NSBundle mainBundle] pathForResource:@"xxxxxxxx.com" ofType:@"der"];
NSData *certificateData = [NSData dataWithContentsOfFile:certificatePath];
AFSecurityPolicy *securityPolicy = [AFSecurityPolicy policyWithPinningMode:AFSSLPinningModeCertificate];
[securityPolicy setAllowInvalidCertificates:YES];
[securityPolicy setPinnedCertificates:@[certificateData]];
[opManager setSecurityPolicy:securityPolicy];
以下函数将为您执行公钥证书固定:
- (AFHTTPSessionManager*) getSessionManager: (NSString *) serverUrl {
AFHTTPSessionManager * sessionManager = [[AFHTTPSessionManager alloc] initWithBaseURL:[NSURL URLWithString: serverUrl]];
if ([serverUrl hasPrefix:@"https"]) {
NSString *certificate = nil;
NSString *cerPath = [[NSBundle mainBundle] pathForResource: certificate ofType:@"der"];
if (cerPath != nil) {
NSData *certData = [NSData dataWithContentsOfFile: cerPath];
AFSecurityPolicy* policy = [AFSecurityPolicy policyWithPinningMode: AFSSLPinningModePublicKey];
policy.pinnedCertificates = [NSSet setWithArray: @[certData]];
[policy setValidatesDomainName: YES];
[policy setAllowInvalidCertificates: NO];
sessionManager.securityPolicy = policy;
}
}
return sessionManager;
}
并调用这个函数使用:
AFHTTPSessionManager * sessionManager = [self getSessionManager: @"https://example.com"];
获得证书正确的数据和格式非常重要。 您需要将以下 der 证书添加到您的项目中:
openssl s_client -connect example.com:443 </dev/null |openssl x509 -outform DER -out example.der
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.