2015-08-29 37 views
0

我使用Alamofire上雨燕2.0和實施ServerTrustPolicy我的本地服務器,你可以在這裏看到:Alamofire ServerTrustPolicy始終無效ServerTrust

let defaultManager: Alamofire.Manager = { 
    let serverTrustPolicies: [String: ServerTrustPolicy] = [ 
//  "localhost": .PinCertificates(
//   certificates: ServerTrustPolicy.certificatesInBundle(), 
//   validateCertificateChain: false, 
//   validateHost: false 
//  ) 
     "localhost": .DisableEvaluation 
    ] 

    let configuration = NSURLSessionConfiguration.defaultSessionConfiguration() 
    configuration.HTTPAdditionalHeaders = Alamofire.Manager.defaultHTTPHeaders 

    return Alamofire.Manager(
     configuration: configuration, 
     serverTrustPolicyManager: ServerTrustPolicyManager(policies: serverTrustPolicies) 
    ) 
}() 

問題是,當我一個請求我總是得到相同的錯誤不管我用.PinCertificates或.DisableEvaluation:

Error Domain=NSURLErrorDomain Code=-1200 "An SSL error has occurred and a secure connection to the server cannot be made." 
UserInfo={ 
    NSURLErrorFailingURLPeerTrustErrorKey=<SecTrustRef: 0x60c00004d980>, 
    NSLocalizedRecoverySuggestion=Would you like to connect to the server anyway?, 
    _kCFStreamErrorDomainKey=3, 
    _kCFStreamErrorCodeKey=-9802, 
    NSErrorPeerCertificateChainKey=<CFArray 0x6060001498a0 [0x10bb3c7b0]>{ 
    type = immutable, count = 1, values = (
    0 : <cert(0x61600006ed80) s: localhost i: localhost> 
    )}, 
    NSUnderlyingError=0x6040000ad750 { 
    Error Domain=kCFErrorDomainCFNetwork Code=-1200 "(null)" 
    UserInfo={ 
     _kCFStreamPropertySSLClientCertificateState=0, 
     kCFStreamPropertySSLPeerTrust=<SecTrustRef: 0x60c00004d980>, 
     _kCFNetworkCFStreamSSLErrorOriginalValue=-9802, 
     _kCFStreamErrorDomainKey=3, 
     _kCFStreamErrorCodeKey=-9802, 
     kCFStreamPropertySSLPeerCertificates=<CFArray 0x6060001498a0 [0x10bb3c7b0]>{ 
     type = immutable, count = 1, values = (
      0 : <cert(0x61600006ed80) s: localhost i: localhost> 
     )} 
    } 
    }, 
    NSLocalizedDescription=An SSL error has occurred and a secure connection to the server cannot be made., 
    NSErrorFailingURLKey=https://localhost:3000/auth/requestToken?auth_appId=d018ccd505db2cb1d5aacabb03fc2f3a, 
    NSErrorFailingURLStringKey=https://localhost:3000/auth/requestToken?auth_appId=d018ccd505db2cb1d5aacabb03fc2f3a, 
    NSErrorClientCertificateStateKey=0 
} 

我嘗試使用

curl --cacert ./ca.pem https://localhost:3000 

會拋出工程只是罰款

我用我這樣生成的自簽名證書:

  1. 創建根CA私鑰

    openssl genrsa -out ca.key.pem 2048 
    
  2. 自籤我的根CA

    openssl req -x509 -new -nodes -key ca.key.pem -days 1024 -out ca.crt.pem 
    
  3. 創建服務器證書通過生成密鑰,那麼企業社會責任,然後用CA簽署它

    openssl genrsa -out server.key.pem 2048 
    openssl req -new -key server.key.pem -out server.csr.pem 
    openssl x509 -req -in server.csr.pem -CA ca.crt.pem -CAkey ca.key.pem -CAcreateserial -out server.crt.pem -days 500 
    

我用的NodeJS的HTTPS模塊作爲我的Web服務器,我配置是這樣的:

require('ssl-root-cas') 
    .inject() 
    .addFile('./ca.crt.pem'); 

var privateKey = fs.readFileSync('./server.key.pem'); 
var certificate = fs.readFileSync('./server.crt.pem'); 
var credentials = { key: privateKey, cert: certificate }; 

var server = https.createServer(credentials, app); 
server.listen(port); 

我看看入Alamofire源代碼,結果發現,在委託方法:

public func URLSession(
     session: NSURLSession, 
     didReceiveChallenge challenge: NSURLAuthenticationChallenge, 
     completionHandler: ((NSURLSessionAuthChallengeDisposition, NSURLCredential?) -> Void)) 
{ 
    var disposition: NSURLSessionAuthChallengeDisposition = .PerformDefaultHandling 
    var credential: NSURLCredential? 

    if let sessionDidReceiveChallenge = sessionDidReceiveChallenge { 
     (disposition, credential) = sessionDidReceiveChallenge(session, challenge) 
    } else if challenge.protectionSpace.authenticationMethod == NSURLAuthenticationMethodServerTrust { 
     let host = challenge.protectionSpace.host 

     if let 
      serverTrustPolicy = session.serverTrustPolicyManager?.serverTrustPolicyForHost(host), 
      serverTrust = challenge.protectionSpace.serverTrust 
     { 
      if serverTrustPolicy.evaluateServerTrust(serverTrust, isValidForHost: host) { 
       disposition = .UseCredential 
       credential = NSURLCredential(forTrust: serverTrust) 
      } else { 
       disposition = .CancelAuthenticationChallenge 
      } 
     } 
    } 

    completionHandler(disposition, credential) 
} 

serverTrustPolicy.evaluateServerTrust(serverTrust, isValidForHost: host)呼叫實際上retur ns true。這意味着錯誤可能在completionHandler代碼中發生,對嗎?

我在處理證書的東西時做得很糟糕嗎?

PS:defaultManager不beeing釋放:)

回答

0

首先,確保你的defaultManager沒有被釋放。如果是的話,你總能得到-999。這就是說,如果您使用.DisableEvaluation,那麼我會認爲您的SSL配置服務器端存在一些更大的問題。

您是否能夠成功控制您的Web服務?

我會根據您提供的更多信息更新我的答案。

+0

我添加了一些關於如何創建證書的信息,使用curl進行測試以及如何設置我的網絡服務器:) – iMoritz

+0

我最好的猜測是你沒有與Alamofire有任何問題。你的問題是,你的服務器上的證書配置似乎沒有設置完全正確。我不是設置服務器端證書配置的專家,所以我建議您在Stack Overflow上打開一個新的問題,這個問題僅適用於設置證書配置服務器端。一旦你有這個工作,我假設Alamofire'ServerTrustPolicies'將開始工作。如果沒有,我很樂意幫你調試。祝你好運! – cnoon

+0

我得到了在curl中工作的ssl東西..事實證明,我在生成證書時犯了一個錯誤。我用新問題更新了這個問題 – iMoritz

相關問題