2012-09-18 122 views
3

我在试图让AFNetworking工作,因为这是我的第一个应用程序,它不得不处理客户端/服务器,我试图从需要用户名/密码的HTTPS服务器获取JSON。我有点迷上了应用程序,但它一直抛出一个401错误,我把它看成基本身份验证问题。AFNetworking NTLM身份验证?

我基本上采用了AFNetworking的twitter示例,并将其改编为我的项目。在AFHTTPClient的子类中,我在initWithBaseURL中添加了另一行,它仍然会抛出错误。我加入的直线是setAuthorizationHeaderWithUsername

- (id)initWithBaseURL:(NSURL *)url { 
self = [super initWithBaseURL:url]; 
if (!self) { 
    return nil; 
} 

[self registerHTTPOperationClass:[AFJSONRequestOperation class]]; 

// Accept HTTP Header; see http://www.w3.org/Protocols/rfc2616/rfc2616-sec14.html#sec14.1 
[self setDefaultHeader:@"Accept" value:@"application/json"]; 
[self setAuthorizationHeaderWithUsername:@"myusername" password:@"my password"]; 

return self; 
} 
+0

我与基于会话的定制身份验证方案专门工作;但我想知道是否最好通过确保HTTP验证与AFNetworking位单独工作来诊断。有一些OS X应用程序可以让你做到这一点,例如[可可其余客户端(http://code.google.com/p/cocoa-rest-client/)。一旦您确信端点身份验证正在运行,您可以返回到处理iOS应用程序中的AFNetworking部分。 – FluffulousChimp

+2

我刚刚意识到服务器不支持基本身份验证,而是NTLM ......这是否意味着AFNetworking不适用于我的目的?我对网络很陌生,我正在学习。非常感谢您回复此主题! – Alan

回答

5

如果你想使用NTLM身份验证与AFNetworking你可以尝试以下方法:

AFNetworking并提供支持NTLM身份验证(或基本上任何身份验证方法)通过一般来说,对认证挑战的基于块的响应。

下面是一个代码示例(假设operationAFHTTPRequestOperation,AFJSONRequestOperation等)。在开始操作之前,设置如下认证质询模块:

[operation setAuthenticationChallengeBlock: 
^(NSURLConnection* connection, NSURLAuthenticationChallenge* challenge) 
{ 
    if([[challenge protectionSpace] authenticationMethod] == NSURLAuthenticationMethodNTLM) 
    { 
     if([challenge previousFailureCount] > 0) 
     { 
     // Avoid too many failed authentication attempts which could lock out the user 
     [[challenge sender] cancelAuthenticationChallenge:challenge]; 
     } 
     else 
     { 
     [[challenge sender] useCredential:[NSURLCredential credentialWithUser:@"username" password:@"password" persistence:NSURLCredentialPersistenceForSession] forAuthenticationChallenge:challenge]; 
     } 
    } 
    else 
    { 
     // Authenticate in other ways than NTLM if desired or cancel the auth like this: 
     [[challenge sender] cancelAuthenticationChallenge:challenge]; 
    } 
}]; 

像往常一样启动或排队操作,并且应该这样做。

这基本上是韦恩哈特曼describes in his blog方法适用于AFNetworking。

4

我找不到接受答案的所有者提到的setAuthenticationChallengeBlock:方法(也许它被删除了一个较新的版本?)但是,我想出了NTLM身份验证的非基于块的解决方案,如图所示下面。 (这是写在斯威夫特实际,但它不应该是将其转换为目标C的一个问题),您只需设置您的凭据对象在AFHTTPRequestOperation例如:

var reqSerializer:AFHTTPRequestSerializer = AFHTTPRequestSerializer() 
var request = reqSerializer.requestWithMethod("GET", URLString: "<URL>", parameters: nil, error: nil) 
var oper = AFHTTPRequestOperation(request: request) 

var respSerializer = AFXMLParserResponseSerializer() 
oper.responseSerializer = respSerializer 

var creds:NSURLCredential = NSURLCredential(user: "<DOMAIN\\USER>", password: "<PASSWORD>", persistence: NSURLCredentialPersistence.None) 
oper.credential = creds 

oper.setCompletionBlockWithSuccess({ (oper:AFHTTPRequestOperation!, obj:AnyObject!) -> Void in 
     //handle success 

    }, failure: { (oper:AFHTTPRequestOperation!, err:NSError!) -> Void in 
     //handle failure 
}) 

oper.start() 
+0

在这里工作完美。我想要使​​用Swift。谢谢! – rsc

+0

嘿,最新的Alamofire和Swift可能的答案是什么? – Hemang