NSURLCredentialStorage和客户端证书认证 [英] NSURLCredentialStorage and client certificate authentication

查看:383
本文介绍了NSURLCredentialStorage和客户端证书认证的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

从我MPMoviewPlayerController的文档中看到,NSURLCredentialStorage可以设置为NSURLConnection的验证挑战的替代(这是从网址,但抽象NSURLConnection的路程加载资源,并且不提供委托更高级别的课程有用用于处理认证挑战)。这似乎类似于在浏览器中安装证书,并在某个地址要求时自动选择所需的证书。

From what I see in the documentation of MPMoviewPlayerController, NSURLCredentialStorage can be set up as an alternative of NSURLConnection authentication challenges (this is useful for higher level classes that load resources from URLs but abstract the NSURLConnection away and don't provide a delegate for handling authentication challenges). This seems similar to installing a certificate in the browser and having it auto select the required certificate when a certain address demands it.

要测试这个问题,我已经设置了自己的证书颁发机构,服务器证书和客户端证书(.p12文件)。我已设置了https服务器,并使用浏览器从单独的计算机成功测试了客户端证书。

To test this out I have set up my own certificate authority, server certificate and client certificate (a .p12 file). I've set up an https server and successfully tested the client certificate using a browser, from a separate machine.

现在,我需要将证书集成到我的iPhone应用程序中。

Now I need to have the certificate integrated in my iPhone app.

我已经捆绑了p12文件,并且在应用程序启动时执行此操作:

I've bundled up the p12 file and on application launch I do this:

NSString *thePath = [[NSBundle mainBundle] pathForResource:@"clientside" ofType:@"p12"];
NSData *PKCS12Data = [[NSData alloc] initWithContentsOfFile:thePath];
CFDataRef inPKCS12Data = (CFDataRef)PKCS12Data;    
SecIdentityRef identity;
SecTrustRef trust;
extractIdentityAndTrust(inPKCS12Data, &identity, &trust);

SecCertificateRef certificate = NULL;
SecIdentityCopyCertificate (identity, &certificate); 

const void *certs[] = {certificate};
CFArrayRef certArray = CFArrayCreate(kCFAllocatorDefault, certs, 1, NULL);

NSURLCredential *credential = [NSURLCredential credentialWithIdentity:identity certificates:(NSArray*)certArray persistence:NSURLCredentialPersistencePermanent];

NSURLProtectionSpace *protectionSpace = [[NSURLProtectionSpace alloc]
                                         initWithHost: @"myhostname"
                                         port: 443
                                         protocol: @"https"
                                         realm: nil
                                         authenticationMethod: NSURLAuthenticationMethodClientCertificate];

[[NSURLCredentialStorage sharedCredentialStorage]
 setDefaultCredential: credential
 forProtectionSpace: protectionSpace];

extractIdentityAndTrust函数只需从证书,密钥和Trust服务任务页面(我刚刚用自己的证书密码替换了证书密码)。

The extractIdentityAndTrust function is simply copied form the 'Certificate, Key, and Trust Services Tasks for iOS' documentation page (I just replaced the certificate password with my own).

从我可以告诉身份和证书加载得很好。如果我打印NSURLCredential对象在控制台中我得到的东西是这样的:< NSURLCredential:0x140ea0计算值:(空)(我不知道这是否是一个好兆头

From what I can tell the identity and the certificate are loaded nicely. If I print the NSURLCredential object in the console I get something like this: <NSURLCredential: 0x140ea0>: (null) (I can't tell if this is a good sign or not).

但是,当我执行setDefaultCredential时,应用程序崩溃,而没有提供太多信息。

However when I execute setDefaultCredential the app crashes without giving much information.

是这样的:

#0  0x350a41c8 in CFHash
#1  0x3515180c in __CFBasicHashStandardHashKey
#2  0x351534e4 in ___CFBasicHashFindBucket_Linear
#3  0x350a4000 in CFBasicHashFindBucket
#4  0x350a3ecc in CFDictionaryGetValue
#5  0x344a0df2 in URLCredentialStorage::setDefaultCredentialForProtectionSpace
#6  0x3446a5aa in CFURLCredentialStorageSetDefaultCredentialForProtectionSpace
#7  0x339ec79e in -[NSURLCredentialStorage setDefaultCredential:forProtectionSpace:]
#8  0x00002612 in -[AVPlayerExampleViewController awakeFromNib] at AVPlayerExampleViewController.m:84


$ b $

Looks to me like there something not set up in the credential.

有关如何解决这个问题的任何想法?

Any ideas on how to solve this?

编辑:

仅仅为了测试,我通过从Mail打开文件在iPhone上安装了证书。我可以通过https通过Safari访问页面,但不能通过我的应用程序。

Just for testing I installed the certificate on the iPhone by opening the file from Mail. I can access the pages over https through Safari, but not through my app.

唯一的工作原理是如果我打开一个NSURLConnection的任何资源在受保护的域,响应didReceiveAuthenticationChallenge(其中我加载我的凭据完全像上面的代码,只有我直接发送到NSURLAuthenticationChallenge的发件人),然后访问我真正需要使用更高级的类。

The only thing that works is if I open an NSURLConnection to any resource on the protected domain, respond to didReceiveAuthenticationChallenge (where I load up my credential exactly like in the code above, only I send it directly to NSURLAuthenticationChallenge's sender) and then access the stuff I really need using the higher level class.

推荐答案

这似乎是一个已知的问题,NSURLCredentialStorage只工作用户名&密码NSURLCredentials(不支持证书)。不幸的是,文档没有提到这一点。

It seems it's a known issue that NSURLCredentialStorage only works for username & password NSURLCredentials (certificates are not supported). Unfortunately the documentation mentions nothing about this.

这篇关于NSURLCredentialStorage和客户端证书认证的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆